diff --git a/README.md b/README.md index 6981bdb..6f4d47e 100644 --- a/README.md +++ b/README.md @@ -42,6 +42,7 @@ Press `?` to view a variety of keyboard shortcuts. - Edit→Color By→Material : Change plot settings to be colored by material, apply changes, and reload plot. - Edit→Enable Masking : Enable/Disable masking, apply changes, and reload plot. - Edit→Enable Highlighting : Enable/Disable highlighting, apply changes, and reload plot. + - Edit→Enable Overlap Coloring : Enable/Disable display of geometry overlaps, apply changes, and reload plot. - View→Hide[Show] Dock : Hide/Show Dock. - View→Zoom... : Open dialog to input new zoom value. @@ -92,6 +93,8 @@ Press `?` to view a variety of keyboard shortcuts. - Edit Background Color... : Select a new color for plot background, apply changes, and reload plot image. See menu bar for other context menu options. + - Right-Click on plot overlap region → activate context menu: + - Edit Overlap Color... : Select a new color for overlap regions, apply changes, and reload plot image. - Right-click on plot cell/material : Activate context menu: - Displays cell/material ID and name (if defined). @@ -99,6 +102,7 @@ Press `?` to view a variety of keyboard shortcuts. - Mask Cell/Material : Mask/Unmask selected cell/material, apply changes, and reload plot image. - Highlight Cell/Material : Highlight/Unhighlight selected cell/material, apply changes, and reload plot image. + See menu bar for other context menu options. ## Color Options Dialog @@ -113,6 +117,8 @@ Press `?` to view a variety of keyboard shortcuts. - Highlight Alpha : Set alpha transparency level of non-highlighted color overlay. - Highlight Seed : Select seed for randomized colorization of cells/materials when highlighting is enabled. - Background Color : Select color of plot background for active plot. + - Show Overlaps : Display overlap regions on the plot. + - Overlap Color : Customize the displayed color of overlap regions. - Color Plot By : Select how the active plot is to be colored. ### Cells/Materials Tabs: diff --git a/openmc-plotter b/openmc-plotter index 75a37b9..7f2a4e6 100755 --- a/openmc-plotter +++ b/openmc-plotter @@ -290,6 +290,16 @@ class MainWindow(QMainWindow): self.highlightingAct.toggled.connect(highlight_connector) self.editMenu.addAction(self.highlightingAct) + self.overlapAct = QAction('Enable Overlap Coloring', self) + self.overlapAct.setShortcut('Ctrl+P') + self.overlapAct.setCheckable(True) + self.overlapAct.setToolTip('Toggle overlapping regions') + self.overlapAct.setStatusTip('Toggle display of overlapping ' + 'regions when enabled') + overlap_connector = partial(self.toggleOverlaps, apply=True) + self.overlapAct.toggled.connect(overlap_connector) + self.editMenu.addAction(self.overlapAct) + # View Menu self.dockAction = QAction('Hide &Dock', self) self.dockAction.setShortcut("Ctrl+D") @@ -440,8 +450,6 @@ class MainWindow(QMainWindow): message = 'Error loading plot settings. Incompatible model.' self.statusBar().showMessage(message, 5000) - return super().event(event) - def applyChanges(self): if self.model.activeView != self.model.currentView: self.statusBar().showMessage('Generating Plot...') @@ -512,6 +520,12 @@ class MainWindow(QMainWindow): if apply: self.applyChanges() + def toggleOverlaps(self, state, apply=False): + self.model.activeView.color_overlaps = bool(state) + self.colorDialog.updateOverlap() + if apply: + self.applyChanges() + def editColorMap(self, colormap_name, property_type, apply=False): self.model.activeView.colormaps[property_type] = colormap_name self.plotIm.updateColorMap(colormap_name, property_type) @@ -672,6 +686,18 @@ class MainWindow(QMainWindow): def editSeed(self, value): self.model.activeView.highlightSeed = value + def editOverlapColor(self, apply=False): + current_color = self.model.activeView.overlap_color + dlg = QColorDialog(self) + dlg.setCurrentColor(QtGui.QColor.fromRgb(*current_color)) + if dlg.exec_(): + new_color = dlg.currentColor().getRgb()[:3] + self.model.activeView.overlap_color = new_color + self.colorDialog.updateOverlapColor() + + if apply: + self.applyChanges() + def editBackgroundColor(self, apply=False): current_color = self.model.activeView.plotBackground dlg = QColorDialog(self) @@ -768,6 +794,14 @@ class MainWindow(QMainWindow): with open('plot_settings.pkl', 'rb') as file: model = pickle.load(file) + # do not replace model if the version is out of date + if model.version != self.model.version: + print("WARNING: previous plot settings are for a different " + "version of the GUI. They will be ignored.") + wrn_msg = "Existing version: {}, Current GUI version: {}" + print(wrn_msg.format(model.version, self.model.version)) + return + self.model.currentView = model.currentView self.model.activeView = copy.deepcopy(model.currentView) self.model.previousViews = model.previousViews diff --git a/overlays.py b/overlays.py index b4e1864..e3199d6 100644 --- a/overlays.py +++ b/overlays.py @@ -27,6 +27,7 @@ class ShortcutsOverlay(QWidget): ("Zoom", "Shift+Scroll"), ("Toggle Masking", c_key + "+M"), ("Toggle Highlighting", c_key + "+L"), + ("Toggle Overlap Coloring", c_key + "+P"), ("Set XY Basis", "Alt+X"), ("Set YZ Basis", "Alt+Y"), ("Set XZ Basis", "Alt+Z"), diff --git a/plotgui.py b/plotgui.py index bb57ce6..f24f121 100644 --- a/plotgui.py +++ b/plotgui.py @@ -5,7 +5,7 @@ from plot_colors import rgb_normalize, invert_rgb from plotmodel import DomainDelegate -from plotmodel import _NOT_FOUND, _VOID_REGION, _MODEL_PROPERTIES +from plotmodel import _NOT_FOUND, _VOID_REGION, _OVERLAP, _MODEL_PROPERTIES from PySide2 import QtCore, QtGui from PySide2.QtWidgets import (QWidget, QPushButton, QHBoxLayout, QVBoxLayout, @@ -198,6 +198,8 @@ def mouseMoveEvent(self, event): if id == str(_VOID_REGION): domainInfo = ("VOID") + elif id == str(_OVERLAP): + domainInfo = ("OVERLAP") elif id != str(_NOT_FOUND) and domain[id].name: domainInfo = ("{} {}: \"{}\"\t Density: {} g/cc\t" "Temperature: {} K".format(domain_kind, @@ -285,7 +287,8 @@ def contextMenuEvent(self, event): self.menu.addAction(self.mw.redoAction) self.menu.addSeparator() - if id != str(_NOT_FOUND) and cv.colorby not in _MODEL_PROPERTIES: + if int(id) not in (_NOT_FOUND, _OVERLAP) and \ + cv.colorby not in _MODEL_PROPERTIES: # Domain ID if domain[id].name: @@ -332,11 +335,18 @@ def contextMenuEvent(self, event): if cv.colorby not in _MODEL_PROPERTIES: self.menu.addSeparator() - bgColorAction = self.menu.addAction('Edit Background Color...') - bgColorAction.setToolTip('Edit background color') - bgColorAction.setStatusTip('Edit plot background color') - connector = partial(self.mw.editBackgroundColor, apply=True) - bgColorAction.triggered.connect(connector) + if int(id) == _NOT_FOUND: + bgColorAction = self.menu.addAction('Edit Background Color...') + bgColorAction.setToolTip('Edit background color') + bgColorAction.setStatusTip('Edit plot background color') + connector = partial(self.mw.editBackgroundColor, apply=True) + bgColorAction.triggered.connect(connector) + elif int(id) == _OVERLAP: + olapColorAction = self.menu.addAction('Edit Overlap Color...') + olapColorAction.setToolTip('Edit overlap color') + olapColorAction.setStatusTip('Edit plot overlap color') + connector = partial(self.mw.editOverlapColor, apply=True) + olapColorAction.triggered.connect(connector) self.menu.addSeparator() self.menu.addAction(self.mw.saveImageAction) @@ -349,11 +359,13 @@ def contextMenuEvent(self, event): if domain_kind.lower() not in ('density', 'temperature'): self.menu.addAction(self.mw.maskingAction) self.menu.addAction(self.mw.highlightingAct) + self.menu.addAction(self.mw.overlapAct) self.menu.addSeparator() self.menu.addAction(self.mw.dockAction) self.mw.maskingAction.setChecked(cv.masking) self.mw.highlightingAct.setChecked(cv.highlighting) + self.mw.overlapAct.setChecked(cv.color_overlaps) if self.mw.dock.isVisible(): self.mw.dockAction.setText('Hide &Dock') @@ -812,6 +824,17 @@ def createGeneralTab(self): self.colorbyBox.addItem("temperature") self.colorbyBox.addItem("density") + # Overlap plotting + self.overlapCheck = QCheckBox('', self) + overlap_connector = partial(self.mw.toggleOverlaps) + self.overlapCheck.stateChanged.connect(overlap_connector) + + self.overlapColorButton = QPushButton() + self.overlapColorButton.setCursor(QtCore.Qt.PointingHandCursor) + self.overlapColorButton.setFixedWidth(self.FM.width("XXXXXXXXXX")) + self.overlapColorButton.setFixedHeight(self.FM.height() * 1.5) + self.overlapColorButton.clicked.connect(self.mw.editOverlapColor) + self.colorbyBox.currentTextChanged[str].connect(self.mw.editColorBy) formLayout = QFormLayout() @@ -828,6 +851,10 @@ def createGeneralTab(self): formLayout.addRow('Highlight Seed:', self.seedBox) formLayout.addRow(HorizontalLine()) formLayout.addRow('Background Color: ', self.bgButton) + formLayout.addRow(HorizontalLine()) + formLayout.addRow('Show Overlaps:', self.overlapCheck) + formLayout.addRow('OVerlap Color:', self.overlapColorButton) + formLayout.addRow(HorizontalLine()) formLayout.addRow('Color Plot By:', self.colorbyBox) generalLayout = QHBoxLayout() @@ -984,6 +1011,8 @@ def updateDialogValues(self): self.updateBackgroundColor() self.updateColorBy() self.updateDomainTabs() + self.updateOverlap() + self.updateOverlapColor() def updateMasking(self): masking = self.model.activeView.masking @@ -1042,8 +1071,21 @@ def updateBackgroundColor(self): self.bgButton.setStyleSheet("border-radius: 8px;" "background-color: rgb%s" % (str(color))) + def updateOverlapColor(self): + color = self.model.activeView.overlap_color + self.overlapColorButton.setStyleSheet("border-radius: 8px;" + "background-color: rgb%s" % (str(color))) + + def updateOverlap(self): + colorby = self.model.activeView.colorby + overlap_val = self.model.activeView.color_overlaps + if colorby in ('cell', 'material'): + self.overlapCheck.setChecked(overlap_val) + def updateColorBy(self): - self.colorbyBox.setCurrentText(self.model.activeView.colorby) + colorby = self.model.activeView.colorby + self.colorbyBox.setCurrentText(colorby) + self.overlapCheck.setEnabled(colorby in ("cell", "material")) def updateDomainTabs(self): self.cellTable.setModel(self.mw.cellsModel) diff --git a/plotmodel.py b/plotmodel.py index 8e74901..4ac1476 100644 --- a/plotmodel.py +++ b/plotmodel.py @@ -17,10 +17,11 @@ ID, NAME, COLOR, COLORLABEL, MASK, HIGHLIGHT = tuple(range(0, 6)) -__VERSION__ = "0.1.0" +__VERSION__ = "0.1.1" _VOID_REGION = -1 _NOT_FOUND = -2 +_OVERLAP = -3 _MODEL_PROPERTIES = ('temperature', 'density') _PROPERTY_INDICES = {'temperature': 0, 'density': 1} @@ -157,6 +158,8 @@ def makePlot(self): for id in unique_ids: if id == _NOT_FOUND: image[self.ids == id] = cv.plotBackground + elif id == _OVERLAP: + image[self.ids == id] = cv.overlap_color else: image[self.ids == id] = domain[str(id)].color @@ -253,6 +256,10 @@ class PlotView(_PlotBase): is active plotBackground : 3-tuple of int RGB color to apply to plot background + color_overlaps : bool + Indicator of whether or not overlaps will be shown + overlap_color : 3-tuple of int + RGB color to apply for cell overlap regions cells : Dict of DomainView instances Dictionary of cell view settings by ID materials : Dict of DomainView instances @@ -285,6 +292,7 @@ def __init__(self, origin, width, height): self.highlightAlpha = 0.5 self.highlightSeed = 1 self.plotBackground = (50, 50, 50) + self.overlap_color = (255, 0, 0) self.plotAlpha = 1.0