mirror of
https://github.com/openmc-dev/openmc.git
synced 2026-07-28 14:15:42 -04:00
Merge remote-tracking branch 'upstream/develop' into outer-product
This commit is contained in:
commit
e2d2f90c5b
3 changed files with 217 additions and 43 deletions
|
|
@ -53,6 +53,8 @@ class Library(object):
|
|||
The types of cross sections in the library (e.g., ['total', 'scatter'])
|
||||
domain_type : {'material', 'cell', 'distribcell', 'universe'}
|
||||
Domain type for spatial homogenization
|
||||
domains : Iterable of Material, Cell or Universe
|
||||
The spatial domain(s) for which MGXS in the Library are computed
|
||||
correction : 'P0' or None
|
||||
Apply the P0 correction to scattering matrices if set to 'P0'
|
||||
energy_groups : EnergyGroups
|
||||
|
|
@ -80,6 +82,7 @@ class Library(object):
|
|||
self._by_nuclide = None
|
||||
self._mgxs_types = []
|
||||
self._domain_type = None
|
||||
self._domains = 'all'
|
||||
self._correction = 'P0'
|
||||
self._energy_groups = None
|
||||
self._tally_trigger = None
|
||||
|
|
@ -105,6 +108,7 @@ class Library(object):
|
|||
clone._by_nuclide = self.by_nuclide
|
||||
clone._mgxs_types = self.mgxs_types
|
||||
clone._domain_type = self.domain_type
|
||||
clone._domains = self.domains
|
||||
clone._correction = self.correction
|
||||
clone._energy_groups = copy.deepcopy(self.energy_groups, memo)
|
||||
clone._tally_trigger = copy.deepcopy(self.tally_trigger, memo)
|
||||
|
|
@ -153,22 +157,24 @@ class Library(object):
|
|||
def by_nuclide(self):
|
||||
return self._by_nuclide
|
||||
|
||||
@property
|
||||
def domains(self):
|
||||
if self.domain_type is None:
|
||||
raise ValueError('Unable to get all domains without a domain type')
|
||||
|
||||
if self.domain_type == 'material':
|
||||
return self.openmc_geometry.get_all_materials()
|
||||
elif self.domain_type == 'cell' or self.domain_type == 'distribcell':
|
||||
return self.openmc_geometry.get_all_material_cells()
|
||||
elif self.domain_type == 'universe':
|
||||
return self.openmc_geometry.get_all_universes()
|
||||
|
||||
@property
|
||||
def domain_type(self):
|
||||
return self._domain_type
|
||||
|
||||
@property
|
||||
def domains(self):
|
||||
if self._domains == 'all':
|
||||
if self.domain_type == 'material':
|
||||
return self.openmc_geometry.get_all_materials()
|
||||
elif self.domain_type in ['cell', 'distribcell']:
|
||||
return self.openmc_geometry.get_all_material_cells()
|
||||
elif self.domain_type == 'universe':
|
||||
return self.openmc_geometry.get_all_universes()
|
||||
else:
|
||||
raise ValueError('Unable to get domains without a domain type')
|
||||
else:
|
||||
return self._domains
|
||||
|
||||
@property
|
||||
def correction(self):
|
||||
return self._correction
|
||||
|
|
@ -223,6 +229,38 @@ class Library(object):
|
|||
cv.check_value('domain type', domain_type, tuple(openmc.mgxs.DOMAIN_TYPES))
|
||||
self._domain_type = domain_type
|
||||
|
||||
@domains.setter
|
||||
def domains(self, domains):
|
||||
|
||||
# Use all materials, cells or universes in the geometry as domains
|
||||
if domains == 'all':
|
||||
self._domains = domains
|
||||
|
||||
# User specified a list of material, cell or universe domains
|
||||
else:
|
||||
if self.domain_type == 'material':
|
||||
cv.check_iterable_type('domain', domains, openmc.Material)
|
||||
all_domains = self.openmc_geometry.get_all_materials()
|
||||
elif self.domain_type in ['cell', 'distribcell']:
|
||||
cv.check_iterable_type('domain', domains, openmc.Cell)
|
||||
all_domains = self.openmc_geometry.get_all_material_cells()
|
||||
elif self.domain_type == 'universe':
|
||||
cv.check_iterable_type('domain', domains, openmc.Universe)
|
||||
all_domains = self.openmc_geometry.get_all_universes()
|
||||
else:
|
||||
msg = 'Unable to set domains with ' \
|
||||
'domain type "{}"'.format(self.domain_type)
|
||||
raise ValueError(msg)
|
||||
|
||||
# Check that each domain can be found in the geometry
|
||||
for domain in domains:
|
||||
if domain not in all_domains:
|
||||
msg = 'Domain "{}" could not be found in the ' \
|
||||
'geometry.'.format(domain)
|
||||
raise ValueError(msg)
|
||||
|
||||
self._domains = domains
|
||||
|
||||
@correction.setter
|
||||
def correction(self, correction):
|
||||
cv.check_value('correction', correction, ('P0', None))
|
||||
|
|
|
|||
196
openmc/plots.py
196
openmc/plots.py
|
|
@ -5,9 +5,9 @@ import sys
|
|||
|
||||
import numpy as np
|
||||
|
||||
import openmc
|
||||
import openmc.checkvalue as cv
|
||||
from openmc.clean_xml import *
|
||||
from openmc.checkvalue import (check_type, check_value, check_length,
|
||||
check_greater_than, check_less_than)
|
||||
|
||||
if sys.version_info[0] >= 3:
|
||||
basestring = str
|
||||
|
|
@ -143,70 +143,70 @@ class Plot(object):
|
|||
self._id = AUTO_PLOT_ID
|
||||
AUTO_PLOT_ID += 1
|
||||
else:
|
||||
check_type('plot ID', plot_id, Integral)
|
||||
check_greater_than('plot ID', plot_id, 0, equality=True)
|
||||
cv.check_type('plot ID', plot_id, Integral)
|
||||
cv.check_greater_than('plot ID', plot_id, 0, equality=True)
|
||||
self._id = plot_id
|
||||
|
||||
@name.setter
|
||||
def name(self, name):
|
||||
check_type('plot name', name, basestring)
|
||||
cv.check_type('plot name', name, basestring)
|
||||
self._name = name
|
||||
|
||||
@width.setter
|
||||
def width(self, width):
|
||||
check_type('plot width', width, Iterable, Real)
|
||||
check_length('plot width', width, 2, 3)
|
||||
cv.check_type('plot width', width, Iterable, Real)
|
||||
cv.check_length('plot width', width, 2, 3)
|
||||
self._width = width
|
||||
|
||||
@origin.setter
|
||||
def origin(self, origin):
|
||||
check_type('plot origin', origin, Iterable, Real)
|
||||
check_length('plot origin', origin, 3)
|
||||
cv.check_type('plot origin', origin, Iterable, Real)
|
||||
cv.check_length('plot origin', origin, 3)
|
||||
self._origin = origin
|
||||
|
||||
@pixels.setter
|
||||
def pixels(self, pixels):
|
||||
check_type('plot pixels', pixels, Iterable, Integral)
|
||||
check_length('plot pixels', pixels, 2, 3)
|
||||
cv.check_type('plot pixels', pixels, Iterable, Integral)
|
||||
cv.check_length('plot pixels', pixels, 2, 3)
|
||||
for dim in pixels:
|
||||
check_greater_than('plot pixels', dim, 0)
|
||||
cv.check_greater_than('plot pixels', dim, 0)
|
||||
self._pixels = pixels
|
||||
|
||||
@filename.setter
|
||||
def filename(self, filename):
|
||||
check_type('filename', filename, basestring)
|
||||
cv.check_type('filename', filename, basestring)
|
||||
self._filename = filename
|
||||
|
||||
@color.setter
|
||||
def color(self, color):
|
||||
check_type('plot color', color, basestring)
|
||||
check_value('plot color', color, ['cell', 'mat'])
|
||||
cv.check_type('plot color', color, basestring)
|
||||
cv.check_value('plot color', color, ['cell', 'mat'])
|
||||
self._color = color
|
||||
|
||||
@type.setter
|
||||
def type(self, plottype):
|
||||
check_type('plot type', plottype, basestring)
|
||||
check_value('plot type', plottype, ['slice', 'voxel'])
|
||||
cv.check_type('plot type', plottype, basestring)
|
||||
cv.check_value('plot type', plottype, ['slice', 'voxel'])
|
||||
self._type = plottype
|
||||
|
||||
@basis.setter
|
||||
def basis(self, basis):
|
||||
check_type('plot basis', basis, basestring)
|
||||
check_value('plot basis', basis, ['xy', 'xz', 'yz'])
|
||||
cv.check_type('plot basis', basis, basestring)
|
||||
cv.check_value('plot basis', basis, ['xy', 'xz', 'yz'])
|
||||
self._basis = basis
|
||||
|
||||
@background.setter
|
||||
def background(self, background):
|
||||
check_type('plot background', background, Iterable, Integral)
|
||||
check_length('plot background', background, 3)
|
||||
cv.check_type('plot background', background, Iterable, Integral)
|
||||
cv.check_length('plot background', background, 3)
|
||||
for rgb in background:
|
||||
check_greater_than('plot background',rgb, 0, True)
|
||||
check_less_than('plot background', rgb, 256)
|
||||
cv.check_greater_than('plot background',rgb, 0, True)
|
||||
cv.check_less_than('plot background', rgb, 256)
|
||||
self._background = background
|
||||
|
||||
@col_spec.setter
|
||||
def col_spec(self, col_spec):
|
||||
check_type('plot col_spec parameter', col_spec, dict, Integral)
|
||||
cv.check_type('plot col_spec parameter', col_spec, dict, Integral)
|
||||
|
||||
for key in col_spec:
|
||||
if key < 0:
|
||||
|
|
@ -229,18 +229,18 @@ class Plot(object):
|
|||
|
||||
@mask_componenets.setter
|
||||
def mask_components(self, mask_components):
|
||||
check_type('plot mask_components', mask_components, Iterable, Integral)
|
||||
cv.check_type('plot mask_components', mask_components, Iterable, Integral)
|
||||
for component in mask_components:
|
||||
check_greater_than('plot mask_components', component, 0, True)
|
||||
cv.check_greater_than('plot mask_components', component, 0, True)
|
||||
self._mask_components = mask_components
|
||||
|
||||
@mask_background.setter
|
||||
def mask_background(self, mask_background):
|
||||
check_type('plot mask background', mask_background, Iterable, Integral)
|
||||
check_length('plot mask background', mask_background, 3)
|
||||
cv.check_type('plot mask background', mask_background, Iterable, Integral)
|
||||
cv.check_length('plot mask background', mask_background, 3)
|
||||
for rgb in mask_background:
|
||||
check_greater_than('plot mask background', rgb, 0, True)
|
||||
check_less_than('plot mask background', rgb, 256)
|
||||
cv.check_greater_than('plot mask background', rgb, 0, True)
|
||||
cv.check_less_than('plot mask background', rgb, 256)
|
||||
self._mask_background = mask_background
|
||||
|
||||
def __repr__(self):
|
||||
|
|
@ -261,6 +261,97 @@ class Plot(object):
|
|||
string += '{0: <16}{1}{2}\n'.format('\tCol Spec', '=\t', self._col_spec)
|
||||
return string
|
||||
|
||||
def colorize(self, geometry, seed=1):
|
||||
"""Generate a color scheme for each domain in the plot.
|
||||
|
||||
This routine may be used to generate random, reproducible color schemes.
|
||||
The colors generated are based upon cell/material IDs in the geometry.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
geometry : openmc.Geometry
|
||||
The geometry for which the plot is defined
|
||||
seed : Integral
|
||||
The random number seed used to generate the color scheme
|
||||
|
||||
"""
|
||||
|
||||
cv.check_type('geometry', geometry, openmc.Geometry)
|
||||
cv.check_type('seed', seed, Integral)
|
||||
cv.check_greater_than('seed', seed, 1, equality=True)
|
||||
|
||||
# Get collections of the domains which will be plotted
|
||||
if self.color is 'mat':
|
||||
domains = geometry.get_all_materials()
|
||||
else:
|
||||
domains = geometry.get_all_cells()
|
||||
|
||||
# Set the seed for the random number generator
|
||||
np.random.seed(seed)
|
||||
|
||||
# Generate random colors for each feature
|
||||
self.col_spec = {}
|
||||
for domain in domains:
|
||||
r = np.random.randint(0, 256)
|
||||
g = np.random.randint(0, 256)
|
||||
b = np.random.randint(0, 256)
|
||||
self.col_spec[domain] = (r, g, b)
|
||||
|
||||
def highlight_domains(self, geometry, domains, seed=1,
|
||||
alpha=0.5, background='gray'):
|
||||
"""Use alpha compositing to highlight one or more domains in the plot.
|
||||
|
||||
This routine generates a color scheme and applies alpha compositing
|
||||
to make all domains except the highlighted ones appear partially
|
||||
transparent.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
geometry : openmc.Geometry
|
||||
The geometry for which the plot is defined
|
||||
domains : Iterable of Integral
|
||||
A collection of the domain IDs to highlight in the plot
|
||||
seed : Integral
|
||||
The random number seed used to generate the color scheme
|
||||
alpha : Real in [0,1]
|
||||
The value to apply in alpha compisiting
|
||||
background : 3-tuple of Integral or 'white' or 'black' or 'gray'
|
||||
The background color to apply in alpha compisiting
|
||||
|
||||
"""
|
||||
|
||||
cv.check_iterable_type('domains', domains, Integral)
|
||||
cv.check_type('alpha', alpha, Real)
|
||||
cv.check_greater_than('alpha', alpha, 0., equality=True)
|
||||
cv.check_less_than('alpha', alpha, 1., equality=True)
|
||||
|
||||
# Get a background (R,G,B) tuple to apply in alpha compositing
|
||||
if isinstance(background, basestring):
|
||||
if background == 'white':
|
||||
background = (255, 255, 255)
|
||||
elif background == 'black':
|
||||
background = (0, 0, 0)
|
||||
elif background == 'gray':
|
||||
background = (160, 160, 160)
|
||||
else:
|
||||
msg = 'The background "{}" is not defined'.format(background)
|
||||
raise ValueError(msg)
|
||||
|
||||
cv.check_iterable_type('background', background, Integral)
|
||||
|
||||
# Generate a color scheme
|
||||
self.colorize(geometry, seed)
|
||||
|
||||
# Apply alpha compositing to the colors for all domains
|
||||
# other than those the user wishes to highlight
|
||||
for domain_id in self.col_spec:
|
||||
if domain_id not in domains:
|
||||
r, g, b = self.col_spec[domain_id]
|
||||
r = int(((1-alpha) * background[0]) + (alpha * r))
|
||||
g = int(((1-alpha) * background[1]) + (alpha * g))
|
||||
b = int(((1-alpha) * background[2]) + (alpha * b))
|
||||
self._col_spec[domain_id] = (r, g, b)
|
||||
|
||||
def get_plot_xml(self):
|
||||
"""Return XML representation of the plot
|
||||
|
||||
|
|
@ -349,6 +440,51 @@ class PlotsFile(object):
|
|||
|
||||
self._plots.remove(plot)
|
||||
|
||||
def colorize(self, geometry, seed=1):
|
||||
"""Generate a consistent color scheme for each domain in each plot.
|
||||
|
||||
This routine may be used to generate random, reproducible color schemes.
|
||||
The colors generated are based upon cell/material IDs in the geometry.
|
||||
The color schemes will be consistent for all plots in "plots.xml".
|
||||
|
||||
Parameters
|
||||
----------
|
||||
geometry : openmc.Geometry
|
||||
The geometry for which the plots are defined
|
||||
seed : Integral
|
||||
The random number seed used to generate the color scheme
|
||||
|
||||
"""
|
||||
|
||||
for plot in self._plots:
|
||||
plot.colorize(geometry, seed)
|
||||
|
||||
|
||||
def highlight_domains(self, geometry, domains, seed=1,
|
||||
alpha=0.5, background='gray'):
|
||||
"""Use alpha compositing to highlight one or more domains in the plot.
|
||||
|
||||
This routine generates a color scheme and applies alpha compositing
|
||||
to make all domains except the highlighted ones partially transparent.
|
||||
|
||||
Parameters
|
||||
----------
|
||||
geometry : openmc.Geometry
|
||||
The geometry for which the plot is defined
|
||||
domains : Iterable of Integral
|
||||
A collection of the domain IDs to highlight in the plot
|
||||
seed : Integral
|
||||
The random number seed used to generate the color scheme
|
||||
alpha : Real in [0,1]
|
||||
The value to apply in alpha compisiting
|
||||
background : 3-tuple of Integral or 'white' or 'black' or 'gray'
|
||||
The background color to apply in alpha compisiting
|
||||
|
||||
"""
|
||||
|
||||
for plot in self._plots:
|
||||
plot.highlight_domains(geometry, domains, seed, alpha, background)
|
||||
|
||||
def _create_plot_subelements(self):
|
||||
for plot in self._plots:
|
||||
xml_element = plot.get_plot_xml()
|
||||
|
|
|
|||
|
|
@ -994,7 +994,7 @@ contains
|
|||
logical :: boundary_exists
|
||||
character(MAX_LINE_LEN) :: filename
|
||||
character(MAX_WORD_LEN) :: word
|
||||
character(MAX_LINE_LEN) :: region_spec
|
||||
character(1000) :: region_spec
|
||||
type(Cell), pointer :: c
|
||||
class(Surface), pointer :: s
|
||||
class(Lattice), pointer :: lat
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue