class PreferencesWindow(PyDialog): """ +-------------+ | Preferences | +---------------------------------+ | Text Size ______ Default | | Annotation Color ______ | | Annotation Size ______ | | Picker Size ______ | | Back Color ______ | | Text Color ______ | | | | Apply OK Cancel | +---------------------------------+ """ def __init__(self, data, win_parent=None): """ Saves the data members from data and performs type checks """ PyDialog.__init__(self, data, win_parent) self._updated_preference = False self._default_font_size = data['font_size'] self._default_text_size = 14 self._default_annotation_size = 18 self._default_coord_scale = 0.05 * 100. self._default_coord_text_scale = 0.5 * 100. self._default_clipping_min = data['min_clip'] self._default_clipping_max = data['max_clip'] #self._default_annotation_size = data['annotation_size'] # int #self.default_magnify = data['magnify'] self.dim_max = data['dim_max'] self._use_gradient_background = data['use_gradient_background'] # bool self._show_corner_coord = data['show_corner_coord'] self._annotation_size = data['annotation_size'] # int #self.out_data = data self._picker_size = data['picker_size'] * 100. self._coord_scale = data['coord_scale'] * 100. self._coord_text_scale = data['coord_text_scale'] * 100. self._magnify = data['magnify'] self._text_size = data['text_size'] self._highlight_opacity = data['highlight_opacity'] self.annotation_color_float, self.annotation_color_int = _check_color( data['annotation_color']) self.background_color_float, self.background_color_int = _check_color( data['background_color']) self.background_color2_float, self.background_color2_int = _check_color( data['background_color2']) self.text_color_float, self.text_color_int = _check_color( data['text_color']) self.highlight_color_float, self.highlight_color_int = _check_color( data['highlight_color']) self._nastran_is_element_quality = data['nastran_is_element_quality'] self._nastran_is_properties = data['nastran_is_properties'] self._nastran_is_3d_bars = data['nastran_is_3d_bars'] self._nastran_is_3d_bars_update = data['nastran_is_3d_bars_update'] self._nastran_is_bar_axes = data['nastran_is_bar_axes'] self._nastran_create_coords = data['nastran_create_coords'] self.setWindowTitle('Preferences') self.create_widgets() self.create_layout() self.set_connections() self.on_font(self._default_font_size) self.on_gradient_scale() #self.show() def create_widgets(self): """creates the display window""" # Text Size self.font_size_label = QLabel("Font Size:") self.font_size_edit = QSpinBox(self) self.font_size_edit.setValue(self._default_font_size) self.font_size_edit.setRange(7, 20) self.font_size_button = QPushButton("Default") #----------------------------------------------------------------------- # Annotation Color self.annotation_color_label = QLabel("Annotation Color:") self.annotation_color_edit = QPushButtonColor( self.annotation_color_int) self.annotation_color_label.hide() self.annotation_color_edit.hide() #----------------------------------------------------------------------- # Text Color self.text_size_label = QLabel("Text Size:") self.text_size_edit = QSpinBox(self) self.text_size_edit.setValue(self._default_text_size) self.text_size_edit.setRange(7, 30) self.text_size_button = QPushButton("Default") # Text Color self.text_color_label = QLabel("Text Color:") self.text_color_edit = QPushButtonColor(self.text_color_int) #----------------------------------------------------------------------- # Highlight Color self.highlight_opacity_label = QLabel("Highlight Opacity:") self.highlight_opacity_edit = QDoubleSpinBox(self) self.highlight_opacity_edit.setValue(self._highlight_opacity) self.highlight_opacity_edit.setRange(0.1, 1.0) self.highlight_opacity_edit.setDecimals(1) self.highlight_opacity_edit.setSingleStep(0.1) self.highlight_opacity_button = QPushButton("Default") # Text Color self.highlight_color_label = QLabel("Highlight Color:") self.highlight_color_edit = QPushButtonColor(self.highlight_color_int) #----------------------------------------------------------------------- # Background Color self.background_color_label = QLabel("Btm Background Color:") self.background_color_edit = QPushButtonColor( self.background_color_int) # Background Color2 self.gradient_scale_label = QLabel("Gradient Background:") self.gradient_scale_checkbox = QCheckBox() self.gradient_scale_checkbox.setChecked(self._use_gradient_background) self.background_color2_label = QLabel("Top Background Color:") self.background_color2_edit = QPushButtonColor( self.background_color2_int) #----------------------------------------------------------------------- # Annotation Size self.annotation_size_label = QLabel("Annotation Size:") self.annotation_size_edit = QSpinBox(self) self.annotation_size_edit.setRange(1, 500) self.annotation_size_edit.setValue(self._annotation_size) self.annotation_size_button = QPushButton("Default") #----------------------------------------------------------------------- # Picker Size self.picker_size_label = QLabel("Picker Size (% of Screen):") self.picker_size_edit = QDoubleSpinBox(self) self.picker_size_edit.setRange(0., 10.) log_dim = log10(self.dim_max) decimals = int(ceil(abs(log_dim))) decimals = max(6, decimals) self.picker_size_edit.setDecimals(decimals) self.picker_size_edit.setSingleStep(10. / 5000.) self.picker_size_edit.setValue(self._picker_size) #----------------------------------------------------------------------- # Clipping Min self.clipping_min_label = QLabel("Clipping Min:") self.clipping_min_edit = QLineEdit(str(self._default_clipping_min)) self.clipping_min_button = QPushButton("Default") # Clipping Max self.clipping_max_label = QLabel("Clipping Max:") self.clipping_max_edit = QLineEdit(str(self._default_clipping_max)) self.clipping_max_button = QPushButton("Default") #----------------------------------------------------------------------- self.coord_scale_label = QLabel('Coordinate System Scale:') self.coord_scale_button = QPushButton("Default") self.coord_scale_edit = QDoubleSpinBox(self) self.coord_scale_edit.setRange(0.1, 1000.) self.coord_scale_edit.setDecimals(3) self.coord_scale_edit.setSingleStep(2.5) self.coord_scale_edit.setValue(self._coord_scale) self.coord_text_scale_label = QLabel('Coordinate System Text Scale:') self.coord_text_scale_button = QPushButton("Default") self.coord_text_scale_edit = QDoubleSpinBox(self) self.coord_text_scale_edit.setRange(0.1, 2000.) self.coord_text_scale_edit.setDecimals(3) self.coord_text_scale_edit.setSingleStep(2.5) self.coord_text_scale_edit.setValue(self._coord_text_scale) # Show corner coord self.corner_coord_label = QLabel("Show Corner Coordinate System:") self.corner_coord_checkbox = QCheckBox() self.corner_coord_checkbox.setChecked(self._show_corner_coord) #----------------------------------------------------------------------- self.magnify_label = QLabel('Screenshot Magnify:') self.magnify_edit = QSpinBox(self) self.magnify_edit.setMinimum(1) self.magnify_edit.setMaximum(10) self.magnify_edit.setValue(self._magnify) #----------------------------------------------------------------------- self.nastran_is_element_quality_checkbox = QCheckBox('Element Quality') self.nastran_is_properties_checkbox = QCheckBox('Properties') self.nastran_is_3d_bars_checkbox = QCheckBox('3D Bars') self.nastran_is_3d_bars_update_checkbox = QCheckBox('Update 3D Bars') self.nastran_create_coords_checkbox = QCheckBox('Coords') self.nastran_is_bar_axes_checkbox = QCheckBox('Bar Axes') self.nastran_is_3d_bars_checkbox.setDisabled(True) self.nastran_is_3d_bars_update_checkbox.setDisabled(True) #self.nastran_is_bar_axes_checkbox.setDisabled(True) self.nastran_is_element_quality_checkbox.setChecked( self._nastran_is_element_quality) self.nastran_is_properties_checkbox.setChecked( self._nastran_is_properties) self.nastran_is_3d_bars_checkbox.setChecked(self._nastran_is_3d_bars) #self.nastran_is_3d_bars_update_checkbox.setChecked(self._nastran_is_3d_bars_update) self.nastran_is_3d_bars_update_checkbox.setChecked(False) self.nastran_is_bar_axes_checkbox.setChecked(self._nastran_is_bar_axes) self.nastran_create_coords_checkbox.setChecked( self._nastran_create_coords) #----------------------------------------------------------------------- # closing self.apply_button = QPushButton("Apply") self.ok_button = QPushButton("OK") self.cancel_button = QPushButton("Cancel") #def create_legend_widgets(self): #""" #Creates the widgets for the legend control #Name Itailic Bold Font #==== ======= ===== ======== #Title check check pulldown #Label check check pulldown #""" #self.name_label = QLabel("Name:") #self.italic_label = QLabel("Italic:") #self.bold_label = QLabel("Bold:") #self.font_label = QLabel("Font:") #self.legend_label = QLabel("Legend:") #self.legend_title_name = QLabel("Title") #self.legend_title_italic_check = QCheckBox() #self.legend_title_bold_check = QCheckBox() #self.legend_title_font_edit = QComboBox() #self.legend_title_font_edit.addItems(['cat', 'dog', 'frog']) #self.legend_label_italic_name = QLabel("Label") #self.legend_label_italic_check = QCheckBox() #self.legend_label_bold_check = QCheckBox() #self.legend_label_font_edit = QComboBox() #self.legend_label_font_edit.addItems(['cat2', 'dog2', 'frog2']) #def create_legend_layout(self): #""" #Creates the layout for the legend control #Name Itailic Bold Font #==== ======= ===== ======== #Title check check pulldown #Label check check pulldown #""" #grid2 = QGridLayout() #grid2.addWidget(self.legend_label, 0, 0) #grid2.addWidget(self.name_label, 1, 0) #grid2.addWidget(self.italic_label, 1, 1) #grid2.addWidget(self.bold_label, 1, 2) #grid2.addWidget(self.font_label, 1, 3) #grid2.addWidget(self.legend_title_name, 2, 0) #grid2.addWidget(self.legend_title_italic_check, 2, 1) #grid2.addWidget(self.legend_title_bold_check, 2, 2) #grid2.addWidget(self.legend_title_font_edit, 2, 3) #grid2.addWidget(self.legend_label_italic_name, 3, 0) #grid2.addWidget(self.legend_label_italic_check, 3, 1) #grid2.addWidget(self.legend_label_bold_check, 3, 2) #grid2.addWidget(self.legend_label_font_edit, 3, 3) #return grid2 def create_layout(self): grid = QGridLayout() irow = 0 grid.addWidget(self.font_size_label, irow, 0) grid.addWidget(self.font_size_edit, irow, 1) grid.addWidget(self.font_size_button, irow, 2) irow += 1 grid.addWidget(self.gradient_scale_label, irow, 0) grid.addWidget(self.gradient_scale_checkbox, irow, 1) irow += 1 grid.addWidget(self.background_color2_label, irow, 0) grid.addWidget(self.background_color2_edit, irow, 1) irow += 1 grid.addWidget(self.background_color_label, irow, 0) grid.addWidget(self.background_color_edit, irow, 1) irow += 1 grid.addWidget(self.highlight_color_label, irow, 0) grid.addWidget(self.highlight_color_edit, irow, 1) irow += 1 grid.addWidget(self.highlight_opacity_label, irow, 0) grid.addWidget(self.highlight_opacity_edit, irow, 1) irow += 1 grid.addWidget(self.text_color_label, irow, 0) grid.addWidget(self.text_color_edit, irow, 1) irow += 1 grid.addWidget(self.text_size_label, irow, 0) grid.addWidget(self.text_size_edit, irow, 1) grid.addWidget(self.text_size_button, irow, 2) irow += 1 grid.addWidget(self.annotation_color_label, irow, 0) grid.addWidget(self.annotation_color_edit, irow, 1) irow += 1 grid.addWidget(self.annotation_size_label, irow, 0) grid.addWidget(self.annotation_size_edit, irow, 1) grid.addWidget(self.annotation_size_button, irow, 2) irow += 1 #grid.addWidget(self.clipping_min_label, irow, 0) #grid.addWidget(self.clipping_min_edit, irow, 1) #grid.addWidget(self.clipping_min_button, irow, 2) #irow += 1 #grid.addWidget(self.clipping_max_label, irow, 0) #grid.addWidget(self.clipping_max_edit, irow, 1) #grid.addWidget(self.clipping_max_button, irow, 2) #irow += 1 grid.addWidget(self.corner_coord_label, irow, 0) grid.addWidget(self.corner_coord_checkbox, irow, 1) irow += 1 grid.addWidget(self.coord_scale_label, irow, 0) grid.addWidget(self.coord_scale_edit, irow, 1) grid.addWidget(self.coord_scale_button, irow, 2) irow += 1 grid.addWidget(self.coord_text_scale_label, irow, 0) grid.addWidget(self.coord_text_scale_edit, irow, 1) grid.addWidget(self.coord_text_scale_button, irow, 2) irow += 1 #----------------------------------------------- grid.addWidget(self.magnify_label, irow, 0) grid.addWidget(self.magnify_edit, irow, 1) irow += 1 grid.addWidget(self.picker_size_label, irow, 0) grid.addWidget(self.picker_size_edit, irow, 1) irow += 1 #-------------------------------------------------- grid_nastran = QGridLayout() irow = 0 grid_nastran.addWidget(self.nastran_create_coords_checkbox, irow, 0) irow += 1 grid_nastran.addWidget(self.nastran_is_element_quality_checkbox, irow, 0) grid_nastran.addWidget(self.nastran_is_properties_checkbox, irow, 1) irow += 1 grid_nastran.addWidget(self.nastran_is_bar_axes_checkbox, irow, 0) irow += 1 grid_nastran.addWidget(self.nastran_is_3d_bars_checkbox, irow, 0) grid_nastran.addWidget(self.nastran_is_3d_bars_update_checkbox, irow, 1) irow += 1 #bold_font = make_font(self._default_font_size, is_bold=True) vbox_nastran = QVBoxLayout() self.nastran_label = QLabel('Nastran:') vbox_nastran.addWidget(self.nastran_label) vbox_nastran.addLayout(grid_nastran) #self.create_legend_widgets() #grid2 = self.create_legend_layout() ok_cancel_box = QHBoxLayout() ok_cancel_box.addWidget(self.apply_button) ok_cancel_box.addWidget(self.ok_button) ok_cancel_box.addWidget(self.cancel_button) vbox = QVBoxLayout() vbox.addLayout(grid) vbox.addLayout(vbox_nastran) #vbox.addStretch() #vbox.addLayout(grid2) vbox.addStretch() vbox.addLayout(ok_cancel_box) self.setLayout(vbox) def set_connections(self): """creates the actions for the menu""" self.font_size_button.clicked.connect(self.on_default_font_size) self.font_size_edit.valueChanged.connect(self.on_font) self.annotation_size_edit.editingFinished.connect( self.on_annotation_size) self.annotation_size_edit.valueChanged.connect(self.on_annotation_size) self.annotation_color_edit.clicked.connect(self.on_annotation_color) self.annotation_size_button.clicked.connect( self.on_default_annotation_size) self.background_color_edit.clicked.connect(self.on_background_color) self.background_color2_edit.clicked.connect(self.on_background_color2) self.gradient_scale_checkbox.clicked.connect(self.on_gradient_scale) self.highlight_color_edit.clicked.connect(self.on_highlight_color) self.highlight_opacity_edit.valueChanged.connect( self.on_highlight_opacity) self.text_color_edit.clicked.connect(self.on_text_color) self.text_size_edit.valueChanged.connect(self.on_text_size) self.text_size_button.clicked.connect(self.on_default_text_size) self.picker_size_edit.valueChanged.connect(self.on_picker_size) self.picker_size_edit.editingFinished.connect(self.on_picker_size) self.coord_scale_edit.valueChanged.connect(self.on_coord_scale) self.coord_scale_edit.editingFinished.connect(self.on_coord_scale) self.coord_scale_button.clicked.connect(self.on_default_coord_scale) self.corner_coord_checkbox.clicked.connect(self.on_corner_coord) self.coord_text_scale_edit.valueChanged.connect( self.on_coord_text_scale) self.coord_text_scale_edit.editingFinished.connect( self.on_coord_text_scale) self.coord_text_scale_button.clicked.connect( self.on_default_coord_text_scale) self.magnify_edit.valueChanged.connect(self.on_magnify) self.magnify_edit.editingFinished.connect(self.on_magnify) self.clipping_min_button.clicked.connect(self.on_default_clipping_min) self.clipping_max_button.clicked.connect(self.on_default_clipping_max) #------------------------------------ # format-specific self.nastran_is_element_quality_checkbox.clicked.connect( self.on_nastran_is_element_quality) self.nastran_is_properties_checkbox.clicked.connect( self.on_nastran_is_properties) self.nastran_is_3d_bars_checkbox.clicked.connect( self.on_nastran_is_3d_bars) self.nastran_is_3d_bars_update_checkbox.clicked.connect( self.on_nastran_is_3d_bars) self.nastran_is_bar_axes_checkbox.clicked.connect( self.on_nastran_is_bar_axes) self.nastran_create_coords_checkbox.clicked.connect( self.on_nastran_create_coords) #------------------------------------ self.apply_button.clicked.connect(self.on_apply) self.ok_button.clicked.connect(self.on_ok) self.cancel_button.clicked.connect(self.on_cancel) # closeEvent def on_nastran_is_element_quality(self): """set the nastran element quality preferences""" is_checked = self.nastran_is_element_quality_checkbox.isChecked() if self.win_parent is not None: self.win_parent.settings.nastran_is_element_quality = is_checked def on_nastran_is_properties(self): """set the nastran properties preferences""" is_checked = self.nastran_is_properties_checkbox.isChecked() if self.win_parent is not None: self.win_parent.settings.nastran_is_properties = is_checked def on_nastran_is_3d_bars(self): """set the nastran properties preferences""" is_checked = self.nastran_is_3d_bars_checkbox.isChecked() if self.win_parent is not None: self.win_parent.settings.nastran_is_3d_bars = is_checked def on_nastran_is_3d_bars_update(self): """set the nastran properties preferences""" is_checked = self.nastran_is_3d_bars_update_checkbox.isChecked() if self.win_parent is not None: self.win_parent.settings.nastran_is_3d_bars_update = is_checked def on_nastran_is_bar_axes(self): """set the nastran properties preferences""" is_checked = self.nastran_is_bar_axes_checkbox.isChecked() if self.win_parent is not None: self.win_parent.settings.nastran_is_bar_axes = is_checked def on_nastran_create_coords(self): """set the nastran properties preferences""" is_checked = self.nastran_create_coords_checkbox.isChecked() if self.win_parent is not None: self.win_parent.settings.nastran_create_coords = is_checked def on_font(self, value=None): """update the font for the current window""" if value is None: value = self.font_size_edit.value() font = QtGui.QFont() font.setPointSize(value) self.setFont(font) bold_font = make_font(value, is_bold=True) self.nastran_label.setFont(bold_font) def on_annotation_size(self, value=None): """update the annotation size""" if value is None: value = int(self.annotation_size_edit.text()) self._annotation_size = value #self.on_apply(force=True) #self.min_edit.setText(str(self._default_min)) #self.min_edit.setStyleSheet("QLineEdit{background: white;}") self.update_annotation_size_color() def update_annotation_size_color(self): if self.win_parent is not None: self.win_parent.settings.set_annotation_size_color( size=self._annotation_size) def on_gradient_scale(self): is_checked = self.gradient_scale_checkbox.isChecked() self.background_color2_label.setEnabled(is_checked) self.background_color2_edit.setEnabled(is_checked) if self.win_parent is not None: self.win_parent.settings.set_gradient_background( use_gradient_background=is_checked) def on_corner_coord(self): is_checked = self.corner_coord_checkbox.isChecked() if self.win_parent is not None: self.win_parent.set_corner_axis_visiblity(is_checked, render=True) def on_annotation_color(self): rgb_color_ints = self.annotation_color_int title = "Choose an annotation color" passed, rgb_color_ints, rgb_color_floats = self.on_color( self.annotation_color_edit, rgb_color_ints, title) if passed: self.annotation_color_int = rgb_color_ints self.annotation_color_float = rgb_color_floats self.update_annotation_size_color() def on_background_color(self): """ Choose a background color""" title = "Choose a primary background color" rgb_color_ints = self.background_color_int color_edit = self.background_color_edit func_name = 'set_background_color' passed, rgb_color_ints, rgb_color_floats = self._background_color( title, color_edit, rgb_color_ints, func_name) if passed: self.background_color_int = rgb_color_ints self.background_color_float = rgb_color_floats def on_background_color2(self): """ Choose a background color""" title = "Choose a secondary background color" rgb_color_ints = self.background_color2_int color_edit = self.background_color2_edit func_name = 'set_background_color2' passed, rgb_color_ints, rgb_color_floats = self._background_color( title, color_edit, rgb_color_ints, func_name) if passed: self.background_color2_int = rgb_color_ints self.background_color2_float = rgb_color_floats def on_highlight_color(self): """ Choose a highlight color""" title = "Choose a highlight color" rgb_color_ints = self.highlight_color_int color_edit = self.highlight_color_edit func_name = 'set_highlight_color' passed, rgb_color_ints, rgb_color_floats = self._background_color( title, color_edit, rgb_color_ints, func_name) if passed: self.highlight_color_int = rgb_color_ints self.highlight_color_float = rgb_color_floats def on_highlight_opacity(self, value=None): if value is None: value = self.highlight_opacity_edit.value() self._highlight_opacity = value if self.win_parent is not None: self.win_parent.settings.set_highlight_opacity(value) def _background_color(self, title, color_edit, rgb_color_ints, func_name): """helper method for ``on_background_color`` and ``on_background_color2``""" passed, rgb_color_ints, rgb_color_floats = self.on_color( color_edit, rgb_color_ints, title) if passed: if self.win_parent is not None: settings = self.win_parent.settings func_background_color = getattr(settings, func_name) func_background_color(rgb_color_floats) return passed, rgb_color_ints, rgb_color_floats def on_text_color(self): """ Choose a text color """ rgb_color_ints = self.text_color_int title = "Choose a text color" passed, rgb_color_ints, rgb_color_floats = self.on_color( self.text_color_edit, rgb_color_ints, title) if passed: self.text_color_int = rgb_color_ints self.text_color_float = rgb_color_floats if self.win_parent is not None: self.win_parent.settings.set_text_color(rgb_color_floats) def on_default_text_size(self): self.text_size_edit.setValue(self._default_text_size) self.on_text_size(self._default_text_size) def on_text_size(self, value=None): if value is None: value = self.text_size_edit.value() self._text_size = value if self.win_parent is not None: self.win_parent.settings.set_text_size(value) def on_color(self, color_edit, rgb_color_ints, title): """pops a color dialog""" col = QColorDialog.getColor(QtGui.QColor(*rgb_color_ints), self, title) if not col.isValid(): return False, rgb_color_ints, None color_float = col.getRgbF()[:3] # floats color_int = [int(colori * 255) for colori in color_float] assert isinstance(color_float[0], float), color_float assert isinstance(color_int[0], int), color_int color_edit.setStyleSheet("QPushButton {" "background-color: rgb(%s, %s, %s);" % tuple(color_int) + #"border:1px solid rgb(255, 170, 255); " "}") return True, color_int, color_float def on_picker_size(self): self._picker_size = float(self.picker_size_edit.text()) if self.win_parent is not None: self.win_parent.element_picker_size = self._picker_size / 100. #self.on_apply(force=True) def on_magnify(self, value=None): if value is None: value = self.magnify_edit.value() self._magnify = value if self.win_parent is not None: self.win_parent.settings.set_magnify(value) #--------------------------------------------------------------------------- def on_coord_scale(self, value=None): if value is None: value = self.coord_scale_edit.value() self._coord_scale = value if self.win_parent is not None: self.win_parent.settings.set_coord_scale(value / 100.) def on_default_coord_scale(self): self.coord_scale_edit.setValue(self._default_coord_scale) self.on_coord_scale(self._default_coord_scale) def on_coord_text_scale(self, value=None): if value is None: value = self.coord_text_scale_edit.value() self._coord_text_scale = value if self.win_parent is not None: self.win_parent.settings.set_coord_text_scale(value / 100.) def on_default_coord_text_scale(self): self.coord_text_scale_edit.setValue(self._default_coord_text_scale) self.on_coord_text_scale(self._default_coord_text_scale) #--------------------------------------------------------------------------- def on_default_font_size(self): self.font_size_edit.setValue(self._default_font_size) self.on_font(self._default_font_size) def on_default_annotation_size(self): self.annotation_size_edit.setValue(self._default_annotation_size) self.on_annotation_size(self._default_annotation_size) def on_default_clipping_min(self): self.clipping_min_edit.setText(str(self._default_clipping_min)) self.clipping_min_edit.setStyleSheet("QLineEdit{background: white;}") def on_default_clipping_max(self): self.clipping_max_edit.setText(str(self._default_clipping_max)) self.clipping_max_edit.setStyleSheet("QLineEdit{background: white;}") def on_validate(self): font_size_value, flag0 = check_float(self.font_size_edit) annotation_size_value, flag1 = check_float(self.annotation_size_edit) assert isinstance(self.annotation_color_float[0], float), self.annotation_color_float assert isinstance(self.annotation_color_int[0], int), self.annotation_color_int picker_size_value, flag2 = check_float(self.picker_size_edit) clipping_min_value, flag3 = check_label_float(self.clipping_min_edit) clipping_max_value, flag4 = check_label_float(self.clipping_max_edit) if all([flag0, flag1, flag2, flag3, flag4]): self._annotation_size = annotation_size_value self._picker_size = picker_size_value self.out_data['font_size'] = int(font_size_value) self.out_data['min_clip'] = min(clipping_min_value, clipping_max_value) self.out_data['max_clip'] = max(clipping_min_value, clipping_max_value) self.out_data['clicked_ok'] = True return True return False def on_apply(self, force=False): passed = self.on_validate() if (passed or force) and self.win_parent is not None: self.win_parent.settings.on_set_font_size( self.out_data['font_size']) #self.win_parent.settings.set_annotation_size_color(self._annotation_size) #self.win_parent.element_picker_size = self._picker_size / 100. if passed and self.win_parent is not None: self.win_parent.clipping_obj.apply_clipping(self.out_data) return passed def on_ok(self): passed = self.on_apply() if passed: self.close() #self.destroy() def on_cancel(self): self.out_data['close'] = True self.close()
class ChannelPreview(QWidget): """ class for preview single colormap. Witch checkbox for change selection. :param colormap: colormap to show :param accepted: if checkbox should be checked :param name: name which will be emitted in all signals as firs argument """ selection_changed = Signal(str, bool) """checkbox selection changed (name)""" edit_request = Signal([str], [Colormap]) """send after pressing edit signal (name) (ColorMap object)""" remove_request = Signal(str) """Signal with name of colormap (name)""" def __init__(self, colormap: Colormap, accepted: bool, name: str, removable: bool = False, used: bool = False): super().__init__() self.image = convert_colormap_to_image(colormap) self.name = name self.removable = removable self.checked = QCheckBox() self.checked.setChecked(accepted) self.checked.setDisabled(used) self.label = QLabel(name) self.label.setFixedWidth(150) self.setMinimumWidth(80) metrics = QFontMetrics(QFont()) layout = QHBoxLayout() layout.addWidget(self.checked) layout.addStretch(1) self.remove_btn = QToolButton() self.remove_btn.setIcon(_icon_selector.close_icon) if removable: self.remove_btn.setToolTip("Remove colormap") else: self.remove_btn.setToolTip("This colormap is protected") self.remove_btn.setEnabled(not accepted and self.removable) self.edit_btn = QToolButton() self.edit_btn.setIcon(_icon_selector.edit_icon) layout.addWidget(self.remove_btn) layout.addWidget(self.edit_btn) layout.addWidget(self.label) self.setLayout(layout) self.checked.stateChanged.connect(self._selection_changed) self.edit_btn.clicked.connect(partial(self.edit_request.emit, name)) if len(colormap.controls) < 20: self.edit_btn.clicked.connect(partial(self.edit_request[Colormap].emit, colormap)) self.edit_btn.setToolTip("Create colormap base on this") else: self.edit_btn.setDisabled(True) self.edit_btn.setToolTip("This colormap is not editable") self.remove_btn.clicked.connect(partial(self.remove_request.emit, name)) self.setMinimumHeight(max(metrics.height(), self.edit_btn.minimumHeight(), self.checked.minimumHeight()) + 20) self.setToolTip(self.name) def _selection_changed(self, _=None): chk = self.checked.isChecked() self.selection_changed.emit(self.name, chk) self.remove_btn.setEnabled(not chk and self.removable) def set_blocked(self, block): """Set if block possibility of remove or uncheck""" self.checked.setDisabled(block) if self.removable and not block: self.remove_btn.setToolTip("Remove colormap") else: self.remove_btn.setToolTip("This colormap is protected") self.remove_btn.setDisabled(True) @property def state_changed(self): """Inner checkbox stateChanged signal""" return self.checked.stateChanged @property def is_checked(self): """If colormap is selected""" return self.checked.isChecked() def set_chosen(self, state: bool): """Set selection of check box.""" self.checked.setChecked(state) def paintEvent(self, event: QPaintEvent): painter = QPainter(self) start = 2 * self.checked.x() + self.checked.width() end = self.remove_btn.x() - self.checked.x() rect = self.rect() rect.setX(start) rect.setWidth(end - start) painter.drawImage(rect, self.image) super().paintEvent(event)
class PluginListItem(QFrame): def __init__( self, package_name: str, version: str = '', url: str = '', summary: str = '', author: str = '', license: str = "UNKNOWN", *, plugin_name: str = None, parent: QWidget = None, enabled: bool = True, ): super().__init__(parent) self.setup_ui() if plugin_name: self.plugin_name.setText(plugin_name) self.package_name.setText(f"{package_name} {version}") self.summary.setText(summary) self.package_author.setText(author) self.action_button.setText(trans._("remove")) self.action_button.setObjectName("remove_button") self.enabled_checkbox.setChecked(enabled) if PluginError.get(plugin_name=plugin_name): def _show_error(): rep = QtPluginErrReporter(parent=self._get_dialog(), initial_plugin=plugin_name) rep.setWindowFlags(Qt.Sheet) close = QPushButton(trans._("close"), rep) rep.layout.addWidget(close) rep.plugin_combo.hide() close.clicked.connect(rep.close) rep.open() self.error_indicator.clicked.connect(_show_error) self.error_indicator.show() self.summary.setIndent(18) else: self.summary.setIndent(38) else: self.plugin_name.setText(package_name) self.package_name.setText(version) self.summary.setText(summary) self.package_author.setText(author) self.action_button.setText(trans._("install")) self.enabled_checkbox.hide() def _get_dialog(self) -> QDialog: p = self.parent() while not isinstance(p, QDialog) and p.parent(): p = p.parent() return p def setup_ui(self): self.v_lay = QVBoxLayout(self) self.v_lay.setContentsMargins(-1, 8, -1, 8) self.v_lay.setSpacing(0) self.row1 = QHBoxLayout() self.row1.setSpacing(8) self.enabled_checkbox = QCheckBox(self) self.enabled_checkbox.setChecked(True) self.enabled_checkbox.setDisabled(True) self.enabled_checkbox.setToolTip(trans._("enable/disable")) sizePolicy = QSizePolicy(QSizePolicy.Fixed, QSizePolicy.Fixed) sizePolicy.setHorizontalStretch(0) sizePolicy.setVerticalStretch(0) sizePolicy.setHeightForWidth( self.enabled_checkbox.sizePolicy().hasHeightForWidth()) self.enabled_checkbox.setSizePolicy(sizePolicy) self.enabled_checkbox.setMinimumSize(QSize(20, 0)) self.enabled_checkbox.setText("") self.row1.addWidget(self.enabled_checkbox) self.plugin_name = QLabel(self) sizePolicy = QSizePolicy(QSizePolicy.Preferred, QSizePolicy.Minimum) sizePolicy.setHorizontalStretch(0) sizePolicy.setVerticalStretch(0) sizePolicy.setHeightForWidth( self.plugin_name.sizePolicy().hasHeightForWidth()) self.plugin_name.setSizePolicy(sizePolicy) font16 = QFont() font16.setPointSize(16) self.plugin_name.setFont(font16) self.row1.addWidget(self.plugin_name) self.package_name = QLabel(self) self.package_name.setAlignment(Qt.AlignRight | Qt.AlignTrailing | Qt.AlignVCenter) self.row1.addWidget(self.package_name) self.action_button = QPushButton(self) sizePolicy = QSizePolicy(QSizePolicy.Fixed, QSizePolicy.Fixed) sizePolicy.setHorizontalStretch(0) sizePolicy.setVerticalStretch(0) sizePolicy.setHeightForWidth( self.action_button.sizePolicy().hasHeightForWidth()) self.action_button.setSizePolicy(sizePolicy) self.row1.addWidget(self.action_button) self.v_lay.addLayout(self.row1) self.row2 = QHBoxLayout() self.error_indicator = QPushButton() self.error_indicator.setObjectName("warning_icon") self.error_indicator.setCursor(Qt.PointingHandCursor) self.error_indicator.hide() self.row2.addWidget(self.error_indicator) self.row2.setContentsMargins(-1, 4, 0, -1) self.summary = ElidingLabel(parent=self) sizePolicy = QSizePolicy(QSizePolicy.MinimumExpanding, QSizePolicy.Preferred) sizePolicy.setHorizontalStretch(0) sizePolicy.setVerticalStretch(0) sizePolicy.setHeightForWidth( self.summary.sizePolicy().hasHeightForWidth()) self.summary.setSizePolicy(sizePolicy) self.summary.setObjectName("small_text") self.row2.addWidget(self.summary) self.package_author = QLabel(self) sizePolicy = QSizePolicy(QSizePolicy.Preferred, QSizePolicy.Preferred) sizePolicy.setHorizontalStretch(0) sizePolicy.setVerticalStretch(0) sizePolicy.setHeightForWidth( self.package_author.sizePolicy().hasHeightForWidth()) self.package_author.setSizePolicy(sizePolicy) self.package_author.setObjectName("small_text") self.row2.addWidget(self.package_author) self.v_lay.addLayout(self.row2)
class Options(QWidget): def __init__( self, settings: PartSettings, channel_control2: ChannelProperty, left_image: ResultImageView, synchronize: SynchronizeView, ): super().__init__() self._settings = settings self.left_panel = left_image self._ch_control2 = channel_control2 self.synchronize_val = False self.hide_left_panel_chk = QCheckBox("Hide left panel") self.hide_left_panel_chk.stateChanged.connect(self.hide_left_panel) self.synchronize_checkbox = QCheckBox("Synchronize view") self.synchronize_checkbox.stateChanged.connect( synchronize.set_synchronize) self.interactive_use = QCheckBox("Interactive use") self.execute_btn = QPushButton("Execute") self.execute_btn.clicked.connect(self.execute_algorithm) self.execute_btn.setStyleSheet("QPushButton{font-weight: bold;}") self.save_pipe_btn = QPushButton("Save pipeline") self.save_pipe_btn.clicked.connect(self.save_pipeline) self.save_pipe_btn.setToolTip( "Save current pipeline. Last element is last executed algorithm") self.choose_pipe = SearchComboBox() self.choose_pipe.addItem("<none>") # self.choose_pipe.addItems(list(self._settings.roi_pipelines.keys())) self.choose_pipe.textActivated.connect(self.choose_pipeline) self.choose_pipe.setToolTip("Execute chosen pipeline") self.save_profile_btn = QPushButton("Save profile") self.save_profile_btn.setToolTip("Save values from current view") self.save_profile_btn.clicked.connect(self.save_profile) self.choose_profile = SearchComboBox() self.choose_profile.addItem("<none>") # self.choose_profile.addItems(list(self._settings.roi_profiles.keys())) self.choose_profile.setToolTip( "Select profile to restore its settings. Execute if interactive is checked" ) # image state self.compare_btn = QPushButton("Compare") self.compare_btn.setDisabled(True) self.compare_btn.clicked.connect(self.compare_action) left_image.hide_signal.connect(self.compare_btn.setHidden) self.update_tooltips() self.choose_profile.textActivated.connect(self.change_profile) self.interactive_use.stateChanged.connect(self.execute_btn.setDisabled) self.interactive_use.stateChanged.connect(self.interactive_change) self.algorithm_choose_widget = AlgorithmChoose( settings, algorithm_description.analysis_algorithm_dict) self.algorithm_choose_widget.result.connect(self.execution_done) self.algorithm_choose_widget.finished.connect( self.calculation_finished) self.algorithm_choose_widget.value_changed.connect( self.interactive_algorithm_execute) self.algorithm_choose_widget.algorithm_changed.connect( self.interactive_algorithm_execute) self._settings.roi_profiles_changed.connect(self._update_profiles) self._settings.roi_pipelines_changed.connect(self._update_pipelines) self._update_pipelines() self._update_profiles() self.label = TextShow() layout = QVBoxLayout() layout2 = QHBoxLayout() layout2.setSpacing(1) layout2.setContentsMargins(0, 0, 0, 0) layout3 = QHBoxLayout() layout3.setContentsMargins(0, 0, 0, 0) layout.setContentsMargins(0, 0, 0, 0) layout5 = QHBoxLayout() layout5.setContentsMargins(0, 0, 0, 0) layout5.addWidget(self.save_pipe_btn) layout5.addWidget(self.choose_pipe) layout4 = QHBoxLayout() layout4.setContentsMargins(0, 0, 0, 0) layout4.addWidget(self.save_profile_btn) layout4.addWidget(self.choose_profile) layout3.addWidget(self.interactive_use) layout3.addWidget(self.execute_btn) layout.addLayout(layout5) layout.addLayout(layout4) layout.addLayout(layout3) layout.addWidget(self.algorithm_choose_widget, 1) # layout.addLayout(self.stack_layout) layout.addWidget(self.label) # layout.addStretch(1) layout2.addWidget(self.hide_left_panel_chk) layout2.addWidget(self.synchronize_checkbox) layout.addLayout(layout2) layout.addWidget(self._ch_control2) # layout.setSpacing(0) self.setLayout(layout) @ensure_main_thread def _update_profiles(self): self.update_combo_box(self.choose_profile, self._settings.roi_profiles) self.update_tooltips() @ensure_main_thread def _update_pipelines(self): self.update_combo_box(self.choose_pipe, self._settings.roi_pipelines) self.update_tooltips() def compare_action(self): if self.compare_btn.text() == "Compare": self._settings.set_segmentation_to_compare(self._settings.roi_info) self.compare_btn.setText("Remove") else: self._settings.set_segmentation_to_compare(ROIInfo(None)) self.compare_btn.setText("Compare") def calculation_finished(self): self.execute_btn.setDisabled(self.interactive_use.isChecked()) self.interactive_use.setEnabled(True) def save_pipeline(self): history = self._settings.get_history() if not history: QMessageBox.information(self, "No mask created", "There is no new mask created", QMessageBox.Ok) return mask_history = [] for el in history: mask = el.mask_property segmentation = ROIExtractionProfile( name="Unknown", algorithm=el.roi_extraction_parameters["algorithm_name"], values=el.roi_extraction_parameters["values"], ) new_el = SegmentationPipelineElement(mask_property=mask, segmentation=segmentation) mask_history.append(new_el) name = self._settings.last_executed_algorithm if not name: QMessageBox.information(self, "No segmentation", "No segmentation executed", QMessageBox.Ok) return values = self._settings.get(f"algorithms.{name}", {}) if len(values) == 0: QMessageBox.information(self, "Some problem", "Pleas run execution again", QMessageBox.Ok) return current_segmentation = ROIExtractionProfile(name="Unknown", algorithm=name, values=values) while True: text, ok = QInputDialog.getText(self, "Pipeline name", "Input pipeline name here") if not ok: return if text in self._settings.roi_pipelines and QMessageBox.No == QMessageBox.warning( self, "Already exists", "Profile with this name already exist. Overwrite?", QMessageBox.Yes | QMessageBox.No, QMessageBox.No, ): continue profile = SegmentationPipeline(name=text, segmentation=current_segmentation, mask_history=mask_history) self._settings.roi_pipelines[text] = profile self._settings.dump() self.choose_pipe.addItem(text) break def choose_pipeline(self, text): if text == "<none>": return pipeline = self._settings.roi_pipelines[text] process_thread = CalculatePipelineThread(self._settings.image, self._settings.mask, pipeline) dial = WaitingDialog(process_thread) if dial.exec_() and process_thread.result: pipeline_result = process_thread.result self._settings.mask = pipeline_result.mask self._settings.roi = pipeline_result.roi_info.roi self._settings.set_history(pipeline_result.history) self.label.setText(pipeline_result.description) self.algorithm_choose_widget.change_algorithm( pipeline.segmentation.algorithm, pipeline.segmentation.values) self.choose_pipe.setCurrentIndex(0) def update_tooltips(self): for i in range(1, self.choose_profile.count()): if self.choose_profile.itemData(i, Qt.ToolTipRole) is not None: continue text = self.choose_profile.itemText(i) profile: ROIExtractionProfile = self._settings.roi_profiles[text] tool_tip_text = str(profile) self.choose_profile.setItemData(i, tool_tip_text, Qt.ToolTipRole) for i in range(1, self.choose_pipe.count()): if self.choose_pipe.itemData(i, Qt.ToolTipRole) is not None: continue text = self.choose_pipe.itemText(i) profile: SegmentationPipeline = self._settings.roi_pipelines[text] tool_tip_text = str(profile) self.choose_pipe.setItemData(i, tool_tip_text, Qt.ToolTipRole) @staticmethod def update_combo_box(combo_box: QComboBox, dkt: dict): current_names = set(dkt.keys()) prev_names = { combo_box.itemText(i) for i in range(1, combo_box.count()) } new_names = current_names - prev_names delete_names = prev_names - current_names if len(delete_names) > 0: i = 1 while i < combo_box.count(): if combo_box.itemText(i) in delete_names: combo_box.removeItem(i) else: i += 1 if len(new_names) > 0: combo_box.addItems(list(sorted(new_names))) def keyPressEvent(self, event: QKeyEvent): if event.key() in [Qt.Key_Enter, Qt.Key_Return ] and event.modifiers() == Qt.ControlModifier: self.execute_btn.click() def save_profile(self): widget: InteractiveAlgorithmSettingsWidget = self.algorithm_choose_widget.current_widget( ) while True: text, ok = QInputDialog.getText(self, "Profile Name", "Input profile name here") if not ok: return if text in self._settings.roi_profiles and QMessageBox.No == QMessageBox.warning( self, "Already exists", "Profile with this name already exist. Overwrite?", QMessageBox.Yes | QMessageBox.No, QMessageBox.No, ): continue resp = ROIExtractionProfile(text, widget.name, widget.get_values()) self._settings.roi_profiles[text] = resp self._settings.dump() break def change_profile(self, val): self.choose_profile.setToolTip("") if val == "<none>": return interactive = self.interactive_use.isChecked() self.interactive_use.setChecked(False) profile = self._settings.roi_profiles[val] self.algorithm_choose_widget.change_algorithm(profile.algorithm, profile.values) self.choose_profile.blockSignals(True) self.choose_profile.setCurrentIndex(0) self.choose_profile.blockSignals(False) self.interactive_use.setChecked(interactive) @property def segmentation(self): return self._settings.roi @property def interactive(self): return self.interactive_use.isChecked() def hide_left_panel(self, val): self._settings.set_in_profile("hide_left_panel", val) if val: self.synchronize_val = self.synchronize_checkbox.isChecked() self.synchronize_checkbox.setChecked(False) else: self.synchronize_checkbox.setChecked(self.synchronize_val) self.synchronize_checkbox.setDisabled(val) self.left_panel.parent().setHidden(val) def interactive_change(self, val): if val: self.execute_algorithm() def algorithm_change(self, val): self._settings.set("current_algorithm", val) if self.interactive: self.execute_algorithm() def interactive_algorithm_execute(self): if self.interactive: self.execute_algorithm() def execute_algorithm(self): widget: InteractiveAlgorithmSettingsWidget = self.algorithm_choose_widget.current_widget( ) if self._settings.image.is_time and not widget.algorithm.support_time( ): QMessageBox.information( self, "Not supported", "This algorithm do not support time data. You can convert it in image adjust" ) return if self._settings.image.is_stack and not widget.algorithm.support_z(): QMessageBox.information( self, "Not supported", "This algorithm do not support stack data. You can convert it in image adjust" ) return self._settings.last_executed_algorithm = widget.name self.execute_btn.setDisabled(True) self.interactive_use.setDisabled(True) widget.execute() def execution_done(self, segmentation: ROIExtractionResult): if segmentation.info_text != "": QMessageBox.information(self, "Algorithm info", segmentation.info_text) self._settings.set_segmentation_result(segmentation) self.compare_btn.setEnabled( isinstance(segmentation.roi, np.ndarray) and np.any(segmentation.roi)) self.label.setText(self.sender().get_info_text()) def showEvent(self, _event): self.hide_left_panel_chk.setChecked( self._settings.get_from_profile("hide_left_panel", False))