def __init__(self, page, parent=None): super(HelpForm, self).__init__(parent) self.setAttribute(Qt.WA_DeleteOnClose) self.setAttribute(Qt.WA_GroupLeader) backAction = QAction(QIcon(":/back.png"), "&Back", self) backAction.setShortcut(QKeySequence.Back) homeAction = QAction(QIcon(":/home.png"), "&Home", self) homeAction.setShortcut("Home") self.pageLabel = QLabel() toolBar = QToolBar() toolBar.addAction(backAction) toolBar.addAction(homeAction) toolBar.addWidget(self.pageLabel) self.textBrowser = QTextBrowser() layout = QVBoxLayout() layout.addWidget(toolBar) layout.addWidget(self.textBrowser, 1) self.setLayout(layout) backAction.triggered.connect(self.tbackward) homeAction.triggered.connect(self.thome) self.textBrowser.sourceChanged.connect(self.updatePageTitle) self.textBrowser.setSearchPaths([":/help"]) self.textBrowser.setSource(QUrl(page)) self.resize(400, 600) self.setWindowTitle("{0} Help".format(QApplication.applicationName()))
def init_ui(self): self.text_edit = QTextEdit(self) self.setCentralWidget(self.text_edit) font = QFont("Menlo", 12) # TODO: Create a layout and change the line spacing #spacing = QFontMetrics(font).lineSpacing() self.text_edit.setFont(font) self.highlighter = Highlighter(self.text_edit.document(), DEFAULT_RULES, DEFAULT_STYLE) #print("Highlighter doc: {}".format(self.text_edit.document())) menu_bar = self.menuBar() m_file = menu_bar.addMenu("File") i_open = QAction("Open", self) i_open.setShortcut('Ctrl+O') i_open.triggered.connect(self.on_open) m_file.addAction(i_open) self.setGeometry(300, 300, 350, 300) self.setWindowTitle("tea")
def _build_ui(self): layout = QFormLayout() self.cone_option = QComboBox() self.cone_option.addItems(["Tolman (Unsymmetrical)", "Exact"]) ndx = self.cone_option.findText(self.settings.cone_option, Qt.MatchExactly) self.cone_option.setCurrentIndex(ndx) layout.addRow("method:", self.cone_option) self.radii_option = QComboBox() self.radii_option.addItems(["Bondi", "UMN"]) ndx = self.radii_option.findText(self.settings.radii, Qt.MatchExactly) self.radii_option.setCurrentIndex(ndx) layout.addRow("radii:", self.radii_option) self.display_cone = QCheckBox() self.display_cone.setChecked(self.settings.display_cone) layout.addRow("show cone:", self.display_cone) self.display_radii = QCheckBox() self.display_radii.setChecked(self.settings.display_radii) layout.addRow("show radii:", self.display_radii) set_ligand_button = QPushButton("set ligand to current selection") set_ligand_button.clicked.connect(self.set_ligand) layout.addRow(set_ligand_button) self.set_ligand_button = set_ligand_button calc_cone_button = QPushButton( "calculate cone angle for ligand on selected center") calc_cone_button.clicked.connect(self.calc_cone) layout.addRow(calc_cone_button) self.calc_cone_button = calc_cone_button remove_cone_button = QPushButton("remove cone visualizations") remove_cone_button.clicked.connect(self.del_cone) layout.addRow(remove_cone_button) self.remove_cone_button = remove_cone_button self.table = QTableWidget() self.table.setColumnCount(3) self.table.setHorizontalHeaderLabels([ 'model', 'center', 'cone angle (°)', ]) self.table.setSelectionBehavior(QTableWidget.SelectRows) self.table.setEditTriggers(QTableWidget.NoEditTriggers) self.table.resizeColumnToContents(0) self.table.resizeColumnToContents(1) self.table.resizeColumnToContents(2) self.table.horizontalHeader().setSectionResizeMode( 2, QHeaderView.Stretch) layout.addRow(self.table) menu = QMenuBar() export = menu.addMenu("&Export") clear = QAction("Clear data table", self.tool_window.ui_area) clear.triggered.connect(self.clear_table) export.addAction(clear) copy = QAction("&Copy CSV to clipboard", self.tool_window.ui_area) copy.triggered.connect(self.copy_csv) shortcut = QKeySequence(Qt.CTRL + Qt.Key_C) copy.setShortcut(shortcut) export.addAction(copy) save = QAction("&Save CSV...", self.tool_window.ui_area) save.triggered.connect(self.save_csv) #this shortcut interferes with main window's save shortcut #I've tried different shortcut contexts to no avail #thanks Qt... #shortcut = QKeySequence(Qt.CTRL + Qt.Key_S) #save.setShortcut(shortcut) #save.setShortcutContext(Qt.WidgetShortcut) export.addAction(save) delimiter = export.addMenu("Delimiter") comma = QAction("comma", self.tool_window.ui_area, checkable=True) comma.setChecked(self.settings.delimiter == "comma") comma.triggered.connect(lambda *args, delim="comma": self.settings. __setattr__("delimiter", delim)) delimiter.addAction(comma) tab = QAction("tab", self.tool_window.ui_area, checkable=True) tab.setChecked(self.settings.delimiter == "tab") tab.triggered.connect(lambda *args, delim="tab": self.settings. __setattr__("delimiter", delim)) delimiter.addAction(tab) space = QAction("space", self.tool_window.ui_area, checkable=True) space.setChecked(self.settings.delimiter == "space") space.triggered.connect(lambda *args, delim="space": self.settings. __setattr__("delimiter", delim)) delimiter.addAction(space) semicolon = QAction("semicolon", self.tool_window.ui_area, checkable=True) semicolon.setChecked(self.settings.delimiter == "semicolon") semicolon.triggered.connect(lambda *args, delim="semicolon": self. settings.__setattr__("delimiter", delim)) delimiter.addAction(semicolon) add_header = QAction("&Include CSV header", self.tool_window.ui_area, checkable=True) add_header.setChecked(self.settings.include_header) add_header.triggered.connect(self.header_check) export.addAction(add_header) comma.triggered.connect( lambda *args, action=tab: action.setChecked(False)) comma.triggered.connect( lambda *args, action=space: action.setChecked(False)) comma.triggered.connect( lambda *args, action=semicolon: action.setChecked(False)) tab.triggered.connect( lambda *args, action=comma: action.setChecked(False)) tab.triggered.connect( lambda *args, action=space: action.setChecked(False)) tab.triggered.connect( lambda *args, action=semicolon: action.setChecked(False)) space.triggered.connect( lambda *args, action=comma: action.setChecked(False)) space.triggered.connect( lambda *args, action=tab: action.setChecked(False)) space.triggered.connect( lambda *args, action=semicolon: action.setChecked(False)) semicolon.triggered.connect( lambda *args, action=comma: action.setChecked(False)) semicolon.triggered.connect( lambda *args, action=tab: action.setChecked(False)) semicolon.triggered.connect( lambda *args, action=space: action.setChecked(False)) menu.setNativeMenuBar(False) self._menu = menu layout.setMenuBar(menu) menu.setVisible(True) self.tool_window.ui_area.setLayout(layout) self.tool_window.manage(None)
def _build_ui(self): #each group has an empty widget at the bottom so they resize the way I want while also having the #labels where I want them layout = QGridLayout() self.tab_widget = QTabWidget() layout.addWidget(self.tab_widget) #layout for absolute thermo stuff absolute_widget = QWidget() absolute_layout = QGridLayout(absolute_widget) #box for sp sp_area_widget = QGroupBox("Single-point") sp_layout = QFormLayout(sp_area_widget) self.sp_selector = FilereaderComboBox(self.session, otherItems=['energy']) self.sp_selector.currentIndexChanged.connect(self.set_sp) sp_layout.addRow(self.sp_selector) self.sp_table = QTableWidget() self.sp_table.setColumnCount(3) self.sp_table.setShowGrid(False) self.sp_table.horizontalHeader().hide() self.sp_table.verticalHeader().hide() self.sp_table.setFrameShape(QTableWidget.NoFrame) self.sp_table.setSelectionMode(QTableWidget.NoSelection) self.sp_table.insertRow(0) sp_layout.addRow(self.sp_table) #box for thermo therm_area_widget = QGroupBox("Thermal corrections") thermo_layout = QFormLayout(therm_area_widget) self.thermo_selector = FilereaderComboBox(self.session, otherItems=['frequency']) self.thermo_selector.currentIndexChanged.connect(self.set_thermo_mdl) thermo_layout.addRow(self.thermo_selector) self.temperature_line = QDoubleSpinBox() self.temperature_line.setMaximum(2**31 - 1) self.temperature_line.setValue(298.15) self.temperature_line.setSingleStep(10) self.temperature_line.setSuffix(" K") self.temperature_line.setMinimum(0) self.temperature_line.valueChanged.connect(self.set_thermo) thermo_layout.addRow("T =", self.temperature_line) self.v0_edit = QDoubleSpinBox() self.v0_edit.setMaximum(4000) self.v0_edit.setValue(self.settings.w0) self.v0_edit.setSingleStep(25) self.v0_edit.setSuffix(" cm\u207b\u00b9") self.v0_edit.valueChanged.connect(self.set_thermo) self.v0_edit.setMinimum(0) self.v0_edit.setToolTip( "frequency parameter for quasi treatments of entropy") thermo_layout.addRow("𝜔<sub>0</sub> =", self.v0_edit) self.thermo_table = QTableWidget() self.thermo_table.setColumnCount(3) self.thermo_table.setShowGrid(False) self.thermo_table.horizontalHeader().hide() self.thermo_table.verticalHeader().hide() self.thermo_table.setFrameShape(QTableWidget.NoFrame) self.thermo_table.setSelectionMode(QTableWidget.NoSelection) thermo_layout.addRow(self.thermo_table) # for for total sum_area_widget = QGroupBox("Thermochemistry") sum_layout = QFormLayout(sum_area_widget) self.sum_table = QTableWidget() self.sum_table.setColumnCount(3) self.sum_table.setShowGrid(False) self.sum_table.horizontalHeader().hide() self.sum_table.verticalHeader().hide() self.sum_table.setFrameShape(QTableWidget.NoFrame) self.sum_table.setSelectionMode(QTableWidget.NoSelection) sum_layout.addRow(self.sum_table) splitter = QSplitter(Qt.Horizontal) splitter.setChildrenCollapsible(False) splitter.addWidget(sp_area_widget) splitter.addWidget(therm_area_widget) splitter.addWidget(sum_area_widget) absolute_layout.addWidget(splitter) self.status = QStatusBar() self.status.setSizeGripEnabled(False) self.status.setStyleSheet("color: red") absolute_layout.addWidget(self.status, 1, 0, 1, 1, Qt.AlignTop) self.tab_widget.addTab(absolute_widget, "absolute") relative_widget = QWidget() relative_layout = QGridLayout(relative_widget) size = [self.settings.ref_col_1, self.settings.ref_col_2] self.ref_group = ThermoGroup("reference group", self.session, self.nrg_fr, self.thermo_co, size) self.ref_group.changes.connect(self.calc_relative_thermo) relative_layout.addWidget(self.ref_group, 0, 0, 1, 3, Qt.AlignTop) size = [self.settings.other_col_1, self.settings.other_col_2] self.other_group = ThermoGroup("other group", self.session, self.nrg_fr, self.thermo_co, size) self.other_group.changes.connect(self.calc_relative_thermo) relative_layout.addWidget(self.other_group, 0, 3, 1, 3, Qt.AlignTop) self.relative_temperature = QDoubleSpinBox() self.relative_temperature.setMaximum(2**31 - 1) self.relative_temperature.setValue(self.settings.rel_temp) self.relative_temperature.setSingleStep(10) self.relative_temperature.setSuffix(" K") self.relative_temperature.setMinimum(0) self.relative_temperature.valueChanged.connect( self.calc_relative_thermo) relative_layout.addWidget(QLabel("T ="), 1, 0, 1, 1, Qt.AlignRight | Qt.AlignVCenter) relative_layout.addWidget(self.relative_temperature, 1, 1, 1, 5, Qt.AlignLeft | Qt.AlignVCenter) self.relative_v0 = QDoubleSpinBox() self.relative_v0.setMaximum(2**31 - 1) self.relative_v0.setValue(self.settings.w0) self.relative_v0.setSingleStep(25) self.relative_v0.setSuffix(" cm\u207b\u00b9") self.relative_v0.setMinimum(0) self.relative_v0.setToolTip( "frequency parameter for quasi treatments of entropy") self.relative_v0.valueChanged.connect(self.calc_relative_thermo) relative_layout.addWidget(QLabel("𝜔<sub>0</sub> ="), 2, 0, 1, 1, Qt.AlignRight | Qt.AlignVCenter) relative_layout.addWidget(self.relative_v0, 2, 1, 1, 5, Qt.AlignLeft | Qt.AlignVCenter) relative_layout.addWidget( QLabel("Boltzmann-weighted relative energies in kcal/mol:"), 3, 0, 1, 6, Qt.AlignVCenter | Qt.AlignLeft) self.relative_table = QTextBrowser() self.relative_table.setMaximumHeight( 4 * self.relative_table.fontMetrics().boundingRect("Q").height()) relative_layout.addWidget(self.relative_table, 4, 0, 1, 6, Qt.AlignTop) relative_layout.setRowStretch(0, 1) relative_layout.setRowStretch(1, 0) relative_layout.setRowStretch(2, 0) relative_layout.setRowStretch(3, 0) relative_layout.setRowStretch(4, 0) self.tab_widget.addTab(relative_widget, "relative") #menu stuff menu = QMenuBar() export = menu.addMenu("&Export") copy = QAction("&Copy CSV to clipboard", self.tool_window.ui_area) copy.triggered.connect(self.copy_csv) shortcut = QKeySequence(Qt.CTRL + Qt.Key_C) copy.setShortcut(shortcut) export.addAction(copy) self.copy = copy save = QAction("&Save CSV...", self.tool_window.ui_area) save.triggered.connect(self.save_csv) #this shortcut interferes with main window's save shortcut #I've tried different shortcut contexts to no avail #thanks Qt... #shortcut = QKeySequence(Qt.CTRL + Qt.Key_S) #save.setShortcut(shortcut) #save.setShortcutContext(Qt.WidgetShortcut) export.addAction(save) delimiter = export.addMenu("Delimiter") comma = QAction("comma", self.tool_window.ui_area, checkable=True) comma.setChecked(self.settings.delimiter == "comma") comma.triggered.connect(lambda *args, delim="comma": self.settings. __setattr__("delimiter", delim)) delimiter.addAction(comma) tab = QAction("tab", self.tool_window.ui_area, checkable=True) tab.setChecked(self.settings.delimiter == "tab") tab.triggered.connect(lambda *args, delim="tab": self.settings. __setattr__("delimiter", delim)) delimiter.addAction(tab) space = QAction("space", self.tool_window.ui_area, checkable=True) space.setChecked(self.settings.delimiter == "space") space.triggered.connect(lambda *args, delim="space": self.settings. __setattr__("delimiter", delim)) delimiter.addAction(space) semicolon = QAction("semicolon", self.tool_window.ui_area, checkable=True) semicolon.setChecked(self.settings.delimiter == "semicolon") semicolon.triggered.connect(lambda *args, delim="semicolon": self. settings.__setattr__("delimiter", delim)) delimiter.addAction(semicolon) add_header = QAction("&Include CSV header", self.tool_window.ui_area, checkable=True) add_header.setChecked(self.settings.include_header) add_header.triggered.connect(self.header_check) export.addAction(add_header) comma.triggered.connect( lambda *args, action=tab: action.setChecked(False)) comma.triggered.connect( lambda *args, action=space: action.setChecked(False)) comma.triggered.connect( lambda *args, action=semicolon: action.setChecked(False)) tab.triggered.connect( lambda *args, action=comma: action.setChecked(False)) tab.triggered.connect( lambda *args, action=space: action.setChecked(False)) tab.triggered.connect( lambda *args, action=semicolon: action.setChecked(False)) space.triggered.connect( lambda *args, action=comma: action.setChecked(False)) space.triggered.connect( lambda *args, action=tab: action.setChecked(False)) space.triggered.connect( lambda *args, action=semicolon: action.setChecked(False)) semicolon.triggered.connect( lambda *args, action=comma: action.setChecked(False)) semicolon.triggered.connect( lambda *args, action=tab: action.setChecked(False)) semicolon.triggered.connect( lambda *args, action=space: action.setChecked(False)) menu.setNativeMenuBar(False) self._menu = menu layout.setMenuBar(menu) menu.setVisible(True) self.tool_window.ui_area.setLayout(layout) self.tool_window.manage(None)
class ScriptEditorView(window.BaseWindow, object): lastTabClosed = Signal() scriptSaved = Signal(str) def __init__(self, model, controller, parent=None): self._model = model or script_model.ScriptEditorModel() self._controller = controller or script_controller.ScriptEditorController( model=self._model) super(ScriptEditorView, self).__init__(parent=parent) self._controller.update_namespace( {'self_output': self._output_console}) # self._load_settings() self.refresh() # self._process_args() # ================================================================================================================= # OVERRIDES # ================================================================================================================= @property def model(self): return self._model # ================================================================================================================= # OVERRIDES # ================================================================================================================= def ui(self): super(ScriptEditorView, self).ui() self._stack = stack.SlidingOpacityStackedWidget(parent=self) main_splitter = QSplitter(Qt.Vertical, parent=self) self._output_console = console.OutputConsole(parent=self) # NOTE: Scripts Tab MUST pass ScriptEditor as parent because internally some ScriptEditor functions # NOTE: are connected to some signals. If we don't do this Maya will crash when opening new Script Editors :) self._scripts_tab = script.ScriptsTab(controller=self._controller, parent=self) main_splitter.addWidget(self._output_console) main_splitter.addWidget(self._scripts_tab) self._menu_bar = self._setup_menubar() self._tool_bar = self._setup_toolbar() self._tool_bar_divider = dividers.Divider() # Empty widget empty_widget = QWidget(self) empty_layout = layouts.HorizontalLayout(spacing=5, margins=(5, 5, 5, 5)) empty_widget.setLayout(empty_layout) main_empty_layout = layouts.VerticalLayout(spacing=5, margins=(5, 5, 5, 5)) self._empty_label = label.BaseLabel('No Scripts Opened', parent=self).h4().strong() self._empty_label.setAlignment(Qt.AlignCenter) main_empty_layout.addStretch() main_empty_layout.addWidget(self._empty_label) main_empty_layout.addStretch() empty_layout.addStretch() empty_layout.addLayout(main_empty_layout) empty_layout.addStretch() self._stack.addWidget(empty_widget) self._stack.addWidget(main_splitter) self.main_layout.addWidget(self._menu_bar) self.main_layout.addWidget(self._tool_bar) self.main_layout.addWidget(self._tool_bar_divider) self.main_layout.addWidget(self._stack) def setup_signals(self): self._scripts_tab.lastTabClosed.connect(self.lastTabClosed.emit) self._output_console.outputTextChanged.connect( self._controller.set_output_text) self._scripts_tab.currentChanged.connect(self._on_current_tab_changed) self._scripts_tab.selectionChanged.connect(self._on_selection_changed) self._scripts_tab.scriptTextChanged.connect( self._on_script_text_changed) self._model.consoleVisibleChanged.connect( self._on_console_visible_changed) self._model.toolbarVisibleChanged.connect( self._on_toolbar_visible_changed) self._model.menubarVisibleChanged.connect( self._on_menubar_visible_changed) self._model.sessionPathChanged.connect(self._on_session_changed) self._model.currentScriptChanged.connect( self._on_current_script_changed) self._model.currentTextChanged.connect(self._on_current_text_changed) self._model.outputTextChanged.connect(self._on_output_text_changed) self._model.scriptOpened.connect(self._on_script_opened) self._model.scriptSaved.connect(self._on_script_saved) self._model.scriptClosed.connect(self._on_script_closed) def eventFilter(self, obj, event): if event.type() in (QEvent.Move, QEvent.Resize): self._adjust_completers() return super(ScriptEditorView, self).eventFilter(obj, event) def closeEvent(self, event): # self.save_current_session() # self._save_settings() super(ScriptEditorView, self).closeEvent(event) # ================================================================================================================= # BASE # ================================================================================================================= def refresh(self): self._update_session() self._execute_selected_action.setEnabled( bool(self._model.selected_text)) self._output_console.setVisible(self._model.console_visible) self._tool_bar.setVisible(self._model.toolbar_visible) self._tool_bar_divider.setVisible(self._model.toolbar_visible) self._menu_bar.setVisible(self._model.menubar_visible) self._refresh_stack() # ================================================================================================================= # INTERNAL # ================================================================================================================= def _setup_menubar(self): """ Internal function that setups menu bar for the widget :return: """ menubar = self.menuBar() save_icon = resources.icon('save') load_icon = resources.icon('open_folder') play_icon = resources.icon('play') clear_icon = resources.icon('delete') resume_icon = resources.icon('resume') undo_icon = resources.icon('undo') redo_icon = resources.icon('redo') copy_icon = resources.icon('copy') cut_icon = resources.icon('cut') paste_icon = resources.icon('paste') tab_icon = resources.icon('tab') quote_icon = resources.icon('quote') rename_icon = resources.icon('rename') keyboard_icon = resources.icon('keyboard') help_icon = resources.icon('help') file_menu = QMenu('File', menubar) menubar.addMenu(file_menu) save_session_action = QAction(save_icon, 'Save Session', file_menu) load_script_action = QAction(load_icon, 'Load Script', file_menu) save_script_action = QAction(save_icon, 'Save Script', file_menu) file_menu.addAction(save_session_action) file_menu.addAction(load_script_action) file_menu.addAction(save_script_action) load_script_action.setShortcut('Ctrl+O') # load_script_action.setShortcutContext(Qt.WidgetShortcut) save_script_action.setShortcut('Ctrl+S') # save_script_action.setShortcutContext(Qt.WidgetShortcut) edit_menu = QMenu('Edit', self) menubar.addMenu(edit_menu) undo_action = QAction(undo_icon, 'Undo', edit_menu) redo_action = QAction(redo_icon, 'Redo', edit_menu) copy_action = QAction(copy_icon, 'Copy', edit_menu) cut_action = QAction(cut_icon, 'Cut', edit_menu) paste_action = QAction(paste_icon, 'Paste', edit_menu) tab_to_spaces_action = QAction(tab_icon, 'Tab to Spaces', edit_menu) comment_action = QAction(quote_icon, 'Comment', edit_menu) find_and_replace = QAction(rename_icon, 'Find and Replace', edit_menu) edit_menu.addAction(undo_action) edit_menu.addAction(redo_action) edit_menu.addSeparator() edit_menu.addAction(copy_action) edit_menu.addAction(cut_action) edit_menu.addAction(paste_action) edit_menu.addSeparator() edit_menu.addAction(tab_to_spaces_action) edit_menu.addAction(comment_action) edit_menu.addAction(find_and_replace) run_menu = QMenu('Run', self) menubar.addMenu(run_menu) self._execute_all_action = QAction(play_icon, 'Execute All', run_menu) self._execute_all_action.setShortcut('Ctrl+Shift+Return') self._execute_all_action.setShortcutContext(Qt.ApplicationShortcut) self._execute_selected_action = QAction(resume_icon, 'Execute Selected', run_menu) self._execute_selected_action.setShortcut('Ctrl+Return') self._execute_selected_action.setShortcutContext( Qt.WidgetWithChildrenShortcut) self._clear_output_action = QAction(clear_icon, 'Clear Output', run_menu) run_menu.addAction(self._execute_all_action) run_menu.addAction(self._execute_selected_action) run_menu.addAction(self._clear_output_action) help_menu = QMenu('Help', self) menubar.addMenu(help_menu) show_shortcuts_action = QAction(keyboard_icon, 'Show Shortcuts', help_menu) print_help_action = QAction(help_icon, 'Print Help', help_menu) help_menu.addAction(show_shortcuts_action) help_menu.addSeparator() help_menu.addAction(print_help_action) undo_action.setShortcut('Ctrl+Z') undo_action.setShortcutContext(Qt.WidgetShortcut) redo_action.setShortcut('Ctrl+Y') redo_action.setShortcutContext(Qt.WidgetShortcut) copy_action.setShortcut('Ctrl+C') copy_action.setShortcutContext(Qt.WidgetShortcut) cut_action.setShortcut('Ctrl+X') cut_action.setShortcutContext(Qt.WidgetShortcut) paste_action.setShortcut('Ctrl+V') paste_action.setShortcutContext(Qt.WidgetShortcut) comment_action.setShortcut(QKeySequence(Qt.ALT + Qt.Key_Q)) comment_action.setShortcutContext(Qt.WidgetShortcut) self._execute_all_action.triggered.connect( self._controller.execute_script) self._execute_selected_action.triggered.connect( partial(self._controller.execute_script, True)) self._clear_output_action.triggered.connect( partial(self._controller.set_output_text, '')) # open_settings_folder_action.triggered.connect(self._open_settings) # show_shortcuts_action.triggered.connect(self._open_shortcuts) # print_help_action.triggered.connect(self.editor_help) save_session_action.triggered.connect( self._controller.save_current_session) save_script_action.triggered.connect(self._controller.save_script) load_script_action.triggered.connect(self._controller.load_script) undo_action.triggered.connect(self._scripts_tab.undo) redo_action.triggered.connect(self._scripts_tab.redo) copy_action.triggered.connect(self._scripts_tab.copy) cut_action.triggered.connect(self._scripts_tab.cut) paste_action.triggered.connect(self._scripts_tab.paste) tab_to_spaces_action.triggered.connect( self._controller.convert_tab_to_spaces) # find_and_replace.triggered.connect(self._open_find_replace) comment_action.triggered.connect(self._scripts_tab.comment) return menubar def _setup_toolbar(self): """ Internal function that setups script editor toolbar """ toolbar = QToolBar('Script Editor ToolBar', parent=self) toolbar.setIconSize(QSize(16, 16)) execute_btn = buttons.BaseToolButton(parent=self) execute_btn.setToolButtonStyle(Qt.ToolButtonTextUnderIcon) execute_selected_btn = buttons.BaseToolButton(parent=self) execute_selected_btn.setToolButtonStyle(Qt.ToolButtonTextUnderIcon) clear_output_btn = buttons.BaseToolButton(parent=self) clear_output_btn.setToolButtonStyle(Qt.ToolButtonTextUnderIcon) toolbar.addWidget(execute_btn) toolbar.addWidget(execute_selected_btn) toolbar.addWidget(clear_output_btn) execute_btn.setDefaultAction(self._execute_all_action) execute_selected_btn.setDefaultAction(self._execute_selected_action) clear_output_btn.setDefaultAction(self._clear_output_action) return toolbar def _update_session(self): """ Internal function that updates ui taking into account the current active session """ current_session = self._controller.get_session() if not current_session: self._scripts_tab.add_new_tab() else: sessions = current_session.read() self._scripts_tab.clear() active = 0 if sessions: for i, s in enumerate(sessions): script_file = s.get('file', None) script_name = s.get('name', '') script_text = s.get('text', '') if script_file and os.path.isfile(script_file): script_editor = self._scripts_tab.add_new_tab( script_name, script_file) else: script_editor = self._scripts_tab.add_new_tab( script_name, script_text) if s.get('active', False): active = i script_editor.set_font_size(s.get('size', None)) else: self._scripts_tab.add_new_tab() self._scripts_tab.setCurrentIndex(active) def _adjust_completers(self): """ Internal callback function that updates the size of the completers depending on its visiblity """ for i in range(self._scripts_tab.count()): script_widget = self._scripts_tab.widget(i) if not script_widget: continue if script_widget.editor.completer.isVisible(): script_widget.editor.move_completer() def _refresh_stack(self): """ Internal function that updates stack status """ total_scripts = len(list(self._model.scripts.items())) if total_scripts <= 0: self._stack.setCurrentIndex(0) else: self._stack.setCurrentIndex(1) # self._scripts_tab.widget(0).editor.setFocus() def _process_args(self): """ Internal function that adds processes given args If file path is given in sys.argv, we tyr to open it ... :return: """ if sys.argv: f = sys.argv[-1] if os.path.exists(f): if not os.path.basename(f) == os.path.basename(__file__): if os.path.splitext(f)[-1] in ['.txt', '.py']: self._output_console.show_message( os.path.splitext(f)[-1]) self._output_console.show_message('Open File: ' + f) self._scripts_tab.add_new_tab(os.path.basename(f), f) if self._scripts_tab.count() == 2: self._scripts_tab.removeTab(0) # ================================================================================================================= # CALLBACKS # ================================================================================================================= def _on_console_visible_changed(self, flag): """ Internal callback function that is called when console visibility is changed in the model :param flag: bool """ self._output_console.setVisible(flag) def _on_toolbar_visible_changed(self, flag): """ Internal callback function that is called when toolbar visibility is changed in the model :param flag: bool """ self._tool_bar.setVisible(flag) self._tool_bar_divider.setVisible(flag) def _on_menubar_visible_changed(self, flag): """ Internal callback function that is called when menubar visibility is changed in the model :param flag: bool """ self._menu_bar.setVisible(flag) def _on_current_tab_changed(self, index): """ Internal callback function that is called when current user selects a new script tab :param index: int """ script_widget = self._scripts_tab.widget(index) if not script_widget: return script_path = script_widget.file_path all_text = self._scripts_tab.get_current_text() with qt_contexts.block_signals(self._model): self._controller.set_current_script(script_path) self._controller.set_current_text( all_text.strip() if all_text else '') def _on_selection_changed(self, text): """ Internal callback function that is called when user selects new script text :param text: str """ with qt_contexts.block_signals(self._model): self._controller.set_selected_text(text) self._execute_selected_action.setEnabled( bool(self._model.selected_text)) def _on_script_text_changed(self, text): """ Internal callback function that is called when script text changes :param text: str """ with qt_contexts.block_signals(self._model): self._controller.set_current_text(text) def _on_session_changed(self): """ Internal callback function that is called when current session is changed in the model """ self._update_session() def _on_current_script_changed(self, script_path): """ Internal callback function that is called each time current selected script is updated in the model :param script_path: str :return: """ script_path = path_utils.clean_path(script_path) for i in range(self._scripts_tab.count()): script_widget = self._scripts_tab.widget(i) if not script_widget: continue if path_utils.clean_path(script_widget.file_path) == script_path: self._scripts_tab.setCurrentIndex(i) return def _on_current_text_changed(self, script_text): """ Internal callback function that is called when current script text is updated by the model :param script_text: str """ script_widget = self._scripts_tab.currentWidget() if not script_widget: return with qt_contexts.block_signals(self._model): script_widget.editor.setPlainText(script_text) def _on_output_text_changed(self, output_text): """ Internal callback function that is called when output text is updated in the model :param output_text: str """ with qt_contexts.block_signals(self._model): self._output_console.setText(output_text) self._output_console.move_cursor_to_line_end() def _on_script_opened(self, script_path): """ Internal callback function that is called when a new script is opened by the model :param script_path: str """ if not script_path or not os.path.isfile(script_path): return self._scripts_tab.add_new_tab(os.path.basename(script_path), script_path, skip_if_exists=True) self._refresh_stack() def _on_script_saved(self, script_path): """ Internal callback function that is called when a script is saved :param script_path: str """ script_widget = self._scripts_tab.currentWidget() if not script_widget: return with qt_contexts.block_signals(self._model): script_path = path_utils.clean_path(script_path) current_file_path = path_utils.clean_path(script_widget.file_path) if script_path != current_file_path: script_widget.file_path = script_path self._scripts_tab.set_current_tab_name( os.path.basename(script_widget.file_path)) self._controller.set_current_script(script_widget.file_path) self._controller.set_current_text( self._scripts_tab.get_current_text()) self._controller.set_selected_text( self._scripts_tab.get_current_selected_text()) def _on_script_closed(self, script_path): """ Internal callback function that is called when a script is closed by model :param script_path: str """ if not script_path: return script_path = path_utils.clean_path(script_path) for i in range(self._scripts_tab.count()): script_widget = self._scripts_tab.widget(i) if not script_widget: continue if path_utils.clean_path(script_widget.file_path) == script_path: self._scripts_tab.removeTab(i, force=True) break self._refresh_stack()
def _setup_menubar(self): """ Internal function that setups menu bar for the widget :return: """ menubar = self.menuBar() save_icon = resources.icon('save') load_icon = resources.icon('open_folder') play_icon = resources.icon('play') clear_icon = resources.icon('delete') resume_icon = resources.icon('resume') undo_icon = resources.icon('undo') redo_icon = resources.icon('redo') copy_icon = resources.icon('copy') cut_icon = resources.icon('cut') paste_icon = resources.icon('paste') tab_icon = resources.icon('tab') quote_icon = resources.icon('quote') rename_icon = resources.icon('rename') keyboard_icon = resources.icon('keyboard') help_icon = resources.icon('help') file_menu = QMenu('File', menubar) menubar.addMenu(file_menu) save_session_action = QAction(save_icon, 'Save Session', file_menu) load_script_action = QAction(load_icon, 'Load Script', file_menu) save_script_action = QAction(save_icon, 'Save Script', file_menu) file_menu.addAction(save_session_action) file_menu.addAction(load_script_action) file_menu.addAction(save_script_action) load_script_action.setShortcut('Ctrl+O') # load_script_action.setShortcutContext(Qt.WidgetShortcut) save_script_action.setShortcut('Ctrl+S') # save_script_action.setShortcutContext(Qt.WidgetShortcut) edit_menu = QMenu('Edit', self) menubar.addMenu(edit_menu) undo_action = QAction(undo_icon, 'Undo', edit_menu) redo_action = QAction(redo_icon, 'Redo', edit_menu) copy_action = QAction(copy_icon, 'Copy', edit_menu) cut_action = QAction(cut_icon, 'Cut', edit_menu) paste_action = QAction(paste_icon, 'Paste', edit_menu) tab_to_spaces_action = QAction(tab_icon, 'Tab to Spaces', edit_menu) comment_action = QAction(quote_icon, 'Comment', edit_menu) find_and_replace = QAction(rename_icon, 'Find and Replace', edit_menu) edit_menu.addAction(undo_action) edit_menu.addAction(redo_action) edit_menu.addSeparator() edit_menu.addAction(copy_action) edit_menu.addAction(cut_action) edit_menu.addAction(paste_action) edit_menu.addSeparator() edit_menu.addAction(tab_to_spaces_action) edit_menu.addAction(comment_action) edit_menu.addAction(find_and_replace) run_menu = QMenu('Run', self) menubar.addMenu(run_menu) self._execute_all_action = QAction(play_icon, 'Execute All', run_menu) self._execute_all_action.setShortcut('Ctrl+Shift+Return') self._execute_all_action.setShortcutContext(Qt.ApplicationShortcut) self._execute_selected_action = QAction(resume_icon, 'Execute Selected', run_menu) self._execute_selected_action.setShortcut('Ctrl+Return') self._execute_selected_action.setShortcutContext( Qt.WidgetWithChildrenShortcut) self._clear_output_action = QAction(clear_icon, 'Clear Output', run_menu) run_menu.addAction(self._execute_all_action) run_menu.addAction(self._execute_selected_action) run_menu.addAction(self._clear_output_action) help_menu = QMenu('Help', self) menubar.addMenu(help_menu) show_shortcuts_action = QAction(keyboard_icon, 'Show Shortcuts', help_menu) print_help_action = QAction(help_icon, 'Print Help', help_menu) help_menu.addAction(show_shortcuts_action) help_menu.addSeparator() help_menu.addAction(print_help_action) undo_action.setShortcut('Ctrl+Z') undo_action.setShortcutContext(Qt.WidgetShortcut) redo_action.setShortcut('Ctrl+Y') redo_action.setShortcutContext(Qt.WidgetShortcut) copy_action.setShortcut('Ctrl+C') copy_action.setShortcutContext(Qt.WidgetShortcut) cut_action.setShortcut('Ctrl+X') cut_action.setShortcutContext(Qt.WidgetShortcut) paste_action.setShortcut('Ctrl+V') paste_action.setShortcutContext(Qt.WidgetShortcut) comment_action.setShortcut(QKeySequence(Qt.ALT + Qt.Key_Q)) comment_action.setShortcutContext(Qt.WidgetShortcut) self._execute_all_action.triggered.connect( self._controller.execute_script) self._execute_selected_action.triggered.connect( partial(self._controller.execute_script, True)) self._clear_output_action.triggered.connect( partial(self._controller.set_output_text, '')) # open_settings_folder_action.triggered.connect(self._open_settings) # show_shortcuts_action.triggered.connect(self._open_shortcuts) # print_help_action.triggered.connect(self.editor_help) save_session_action.triggered.connect( self._controller.save_current_session) save_script_action.triggered.connect(self._controller.save_script) load_script_action.triggered.connect(self._controller.load_script) undo_action.triggered.connect(self._scripts_tab.undo) redo_action.triggered.connect(self._scripts_tab.redo) copy_action.triggered.connect(self._scripts_tab.copy) cut_action.triggered.connect(self._scripts_tab.cut) paste_action.triggered.connect(self._scripts_tab.paste) tab_to_spaces_action.triggered.connect( self._controller.convert_tab_to_spaces) # find_and_replace.triggered.connect(self._open_find_replace) comment_action.triggered.connect(self._scripts_tab.comment) return menubar
def _build_ui(self): layout = QFormLayout() self.radii_option = QComboBox() self.radii_option.addItems(["Bondi", "UMN"]) ndx = self.radii_option.findText(self.settings.radii, Qt.MatchExactly) self.radii_option.setCurrentIndex(ndx) layout.addRow("radii:", self.radii_option) self.L_option = QComboBox() self.L_option.addItems([ "to centroid of coordinating atoms", "bisect angle between coordinating atoms" ]) ndx = self.L_option.findText(self.settings.L_option, Qt.MatchExactly) self.L_option.setCurrentIndex(ndx) layout.addRow("L axis:", self.L_option) self.sterimol2vec = QGroupBox("Sterimol2Vec") sterimol2vec_layout = QFormLayout(self.sterimol2vec) self.at_L = QDoubleSpinBox() self.at_L.setRange(-10, 30) self.at_L.setDecimals(2) self.at_L.setSingleStep(0.25) self.at_L.setValue(self.settings.at_L) sterimol2vec_layout.addRow("L value:", self.at_L) layout.addRow(self.sterimol2vec) self.sterimol2vec.setCheckable(True) self.sterimol2vec.toggled.connect(lambda x: self.at_L.setEnabled(x)) self.sterimol2vec.setChecked(self.settings.sterimol2vec) self.display_vectors = QCheckBox() self.display_vectors.setChecked(self.settings.display_vectors) layout.addRow("show vectors:", self.display_vectors) self.display_radii = QCheckBox() self.display_radii.setChecked(self.settings.display_radii) layout.addRow("show radii:", self.display_radii) calc_sterimol_button = QPushButton( "calculate parameters for selected ligands") calc_sterimol_button.clicked.connect(self.calc_sterimol) layout.addRow(calc_sterimol_button) self.calc_sterimol_button = calc_sterimol_button remove_sterimol_button = QPushButton("remove Sterimol visualizations") remove_sterimol_button.clicked.connect(self.del_sterimol) layout.addRow(remove_sterimol_button) self.remove_sterimol_button = remove_sterimol_button self.table = QTableWidget() self.table.setColumnCount(8) self.table.setHorizontalHeaderLabels([ 'model', 'coord. atoms', 'B\u2081', 'B\u2082', 'B\u2083', 'B\u2084', 'B\u2085', 'L', ]) self.table.setSelectionBehavior(QTableWidget.SelectRows) self.table.setEditTriggers(QTableWidget.NoEditTriggers) self.table.resizeColumnToContents(0) self.table.resizeColumnToContents(1) self.table.resizeColumnToContents(2) self.table.resizeColumnToContents(3) self.table.resizeColumnToContents(4) self.table.resizeColumnToContents(5) self.table.resizeColumnToContents(6) self.table.resizeColumnToContents(7) self.table.horizontalHeader().setSectionResizeMode( 2, QHeaderView.Stretch) self.table.horizontalHeader().setSectionResizeMode( 3, QHeaderView.Stretch) self.table.horizontalHeader().setSectionResizeMode( 4, QHeaderView.Stretch) self.table.horizontalHeader().setSectionResizeMode( 5, QHeaderView.Stretch) self.table.horizontalHeader().setSectionResizeMode( 6, QHeaderView.Stretch) self.table.horizontalHeader().setSectionResizeMode( 7, QHeaderView.Stretch) layout.addRow(self.table) menu = QMenuBar() export = menu.addMenu("&Export") clear = QAction("Clear data table", self.tool_window.ui_area) clear.triggered.connect(self.clear_table) export.addAction(clear) copy = QAction("&Copy CSV to clipboard", self.tool_window.ui_area) copy.triggered.connect(self.copy_csv) shortcut = QKeySequence(Qt.CTRL + Qt.Key_C) copy.setShortcut(shortcut) export.addAction(copy) save = QAction("&Save CSV...", self.tool_window.ui_area) save.triggered.connect(self.save_csv) #this shortcut interferes with main window's save shortcut #I've tried different shortcut contexts to no avail #thanks Qt... #shortcut = QKeySequence(Qt.CTRL + Qt.Key_S) #save.setShortcut(shortcut) #save.setShortcutContext(Qt.WidgetShortcut) export.addAction(save) delimiter = export.addMenu("Delimiter") comma = QAction("comma", self.tool_window.ui_area, checkable=True) comma.setChecked(self.settings.delimiter == "comma") comma.triggered.connect(lambda *args, delim="comma": self.settings. __setattr__("delimiter", delim)) delimiter.addAction(comma) tab = QAction("tab", self.tool_window.ui_area, checkable=True) tab.setChecked(self.settings.delimiter == "tab") tab.triggered.connect(lambda *args, delim="tab": self.settings. __setattr__("delimiter", delim)) delimiter.addAction(tab) space = QAction("space", self.tool_window.ui_area, checkable=True) space.setChecked(self.settings.delimiter == "space") space.triggered.connect(lambda *args, delim="space": self.settings. __setattr__("delimiter", delim)) delimiter.addAction(space) semicolon = QAction("semicolon", self.tool_window.ui_area, checkable=True) semicolon.setChecked(self.settings.delimiter == "semicolon") semicolon.triggered.connect(lambda *args, delim="semicolon": self. settings.__setattr__("delimiter", delim)) delimiter.addAction(semicolon) add_header = QAction("&Include CSV header", self.tool_window.ui_area, checkable=True) add_header.setChecked(self.settings.include_header) add_header.triggered.connect(self.header_check) export.addAction(add_header) comma.triggered.connect( lambda *args, action=tab: action.setChecked(False)) comma.triggered.connect( lambda *args, action=space: action.setChecked(False)) comma.triggered.connect( lambda *args, action=semicolon: action.setChecked(False)) tab.triggered.connect( lambda *args, action=comma: action.setChecked(False)) tab.triggered.connect( lambda *args, action=space: action.setChecked(False)) tab.triggered.connect( lambda *args, action=semicolon: action.setChecked(False)) space.triggered.connect( lambda *args, action=comma: action.setChecked(False)) space.triggered.connect( lambda *args, action=tab: action.setChecked(False)) space.triggered.connect( lambda *args, action=semicolon: action.setChecked(False)) semicolon.triggered.connect( lambda *args, action=comma: action.setChecked(False)) semicolon.triggered.connect( lambda *args, action=tab: action.setChecked(False)) semicolon.triggered.connect( lambda *args, action=space: action.setChecked(False)) menu.setNativeMenuBar(False) self._menu = menu layout.setMenuBar(menu) menu.setVisible(True) self.tool_window.ui_area.setLayout(layout) self.tool_window.manage(None)
def _build_ui(self): layout = QVBoxLayout() self.file_selector = FilereaderComboBox(self.session) self.file_selector.currentIndexChanged.connect(self.fill_table) layout.insertWidget(0, self.file_selector, 0) tabs = QTabWidget() self.tabs = tabs layout.insertWidget(1, self.tabs, 1) general_info = QWidget() general_layout = QVBoxLayout(general_info) tabs.addTab(general_info, "general") self.table = QTableWidget() self.table.setColumnCount(2) self.table.setHorizontalHeaderLabels(['Data', 'Value']) self.table.horizontalHeader().setStretchLastSection(False) self.table.horizontalHeader().setSectionResizeMode( 0, QHeaderView.Interactive) self.table.setEditTriggers(QTableWidget.NoEditTriggers) self.table.horizontalHeader().setSectionResizeMode( 1, QHeaderView.Stretch) self.table.setSizePolicy(QSizePolicy.MinimumExpanding, QSizePolicy.MinimumExpanding) general_layout.insertWidget(1, self.table, 1) self.filter = QLineEdit() self.filter.setPlaceholderText("filter data") self.filter.textChanged.connect(self.apply_filter) self.filter.setClearButtonEnabled(True) general_layout.insertWidget(2, self.filter, 0) freq_info = QWidget() freq_layout = QVBoxLayout(freq_info) tabs.addTab(freq_info, "harmonic frequencies") self.freq_table = QTableWidget() self.freq_table.setColumnCount(4) self.freq_table.setHorizontalHeaderLabels([ "Frequency (cm\u207b\u00b9)", "symmetry", "IR intensity", "force constant (mDyne/\u212B)", ]) self.freq_table.setSortingEnabled(True) self.freq_table.setEditTriggers(QTableWidget.NoEditTriggers) for i in range(0, 4): self.freq_table.resizeColumnToContents(i) self.freq_table.horizontalHeader().setStretchLastSection(False) self.freq_table.horizontalHeader().setSectionResizeMode( 0, QHeaderView.Fixed) self.freq_table.horizontalHeader().setSectionResizeMode( 1, QHeaderView.Fixed) self.freq_table.horizontalHeader().setSectionResizeMode( 2, QHeaderView.Fixed) self.freq_table.horizontalHeader().setSectionResizeMode( 3, QHeaderView.Stretch) self.freq_table.setSizePolicy(QSizePolicy.MinimumExpanding, QSizePolicy.MinimumExpanding) freq_layout.insertWidget(1, self.freq_table, 1) anharm_info = QWidget() anharm_layout = QVBoxLayout(anharm_info) tabs.addTab(anharm_info, "anharmonic frequencies") anharm_layout.insertWidget(0, QLabel("fundamentals:"), 0) self.fundamental_table = QTableWidget() self.fundamental_table.setColumnCount(3) self.fundamental_table.setHorizontalHeaderLabels([ "Fundamental (cm\u207b\u00b9)", "Δ\u2090\u2099\u2095 (cm\u207b\u00b9)", "IR intensity", ]) self.fundamental_table.setSortingEnabled(True) self.fundamental_table.setEditTriggers(QTableWidget.NoEditTriggers) for i in range(0, 3): self.fundamental_table.resizeColumnToContents(i) self.fundamental_table.horizontalHeader().setStretchLastSection(False) self.fundamental_table.horizontalHeader().setSectionResizeMode( 0, QHeaderView.Fixed) self.fundamental_table.horizontalHeader().setSectionResizeMode( 1, QHeaderView.Fixed) self.fundamental_table.horizontalHeader().setSectionResizeMode( 2, QHeaderView.Stretch) self.fundamental_table.setSizePolicy(QSizePolicy.MinimumExpanding, QSizePolicy.MinimumExpanding) anharm_layout.insertWidget(1, self.fundamental_table, 1) # self.overtone_table = QTableWidget() # self.overtone_table.setColumnCount(3) # self.overtone_table.setHorizontalHeaderLabels( # [ # "Fundamental (cm\u207b\u00b9)", # "Overtone (cm\u207b\u00b9)", # "IR intensity", # ] # ) # self.overtone_table.setSortingEnabled(True) # self.overtone_table.setEditTriggers(QTableWidget.NoEditTriggers) # for i in range(0, 3): # self.overtone_table.resizeColumnToContents(i) # # self.overtone_table.horizontalHeader().setStretchLastSection(False) # self.overtone_table.horizontalHeader().setSectionResizeMode(0, QHeaderView.Fixed) # self.overtone_table.horizontalHeader().setSectionResizeMode(1, QHeaderView.Fixed) # self.overtone_table.horizontalHeader().setSectionResizeMode(2, QHeaderView.Stretch) # # self.overtone_table.setSizePolicy(QSizePolicy.MinimumExpanding, QSizePolicy.MinimumExpanding) # anharm_layout.insertWidget(2, self.overtone_table, 1) anharm_layout.insertWidget(2, QLabel("combinations and overtones:"), 0) self.combo_table = QTableWidget() self.combo_table.setColumnCount(4) self.combo_table.setHorizontalHeaderLabels([ "Fundamental (cm\u207b\u00b9)", "Fundamental (cm\u207b\u00b9)", "Combination (cm\u207b\u00b9)", "IR intensity", ]) self.combo_table.setSortingEnabled(True) self.combo_table.setEditTriggers(QTableWidget.NoEditTriggers) for i in range(0, 3): self.combo_table.resizeColumnToContents(i) self.combo_table.horizontalHeader().setStretchLastSection(False) self.combo_table.horizontalHeader().setSectionResizeMode( 0, QHeaderView.Fixed) self.combo_table.horizontalHeader().setSectionResizeMode( 1, QHeaderView.Fixed) self.combo_table.horizontalHeader().setSectionResizeMode( 2, QHeaderView.Fixed) self.combo_table.horizontalHeader().setSectionResizeMode( 3, QHeaderView.Stretch) self.combo_table.setSizePolicy(QSizePolicy.MinimumExpanding, QSizePolicy.MinimumExpanding) anharm_layout.insertWidget(3, self.combo_table, 1) menu = QMenuBar() export = menu.addMenu("&Export") copy = QAction("&Copy CSV to clipboard", self.tool_window.ui_area) copy.triggered.connect(self.copy_csv) shortcut = QKeySequence(Qt.CTRL + Qt.Key_C) copy.setShortcut(shortcut) export.addAction(copy) self.copy = copy save = QAction("&Save CSV...", self.tool_window.ui_area) save.triggered.connect(self.save_csv) export.addAction(save) delimiter = export.addMenu("Delimiter") comma = QAction("comma", self.tool_window.ui_area, checkable=True) comma.setChecked(self.settings.delimiter == "comma") comma.triggered.connect(lambda *args, delim="comma": self.settings. __setattr__("delimiter", delim)) delimiter.addAction(comma) tab = QAction("tab", self.tool_window.ui_area, checkable=True) tab.setChecked(self.settings.delimiter == "tab") tab.triggered.connect(lambda *args, delim="tab": self.settings. __setattr__("delimiter", delim)) delimiter.addAction(tab) # space = QAction("space", self.tool_window.ui_area, checkable=True) # space.setChecked(self.settings.delimiter == "space") # space.triggered.connect(lambda *args, delim="space": self.settings.__setattr__("delimiter", delim)) # delimiter.addAction(space) semicolon = QAction("semicolon", self.tool_window.ui_area, checkable=True) semicolon.setChecked(self.settings.delimiter == "semicolon") semicolon.triggered.connect(lambda *args, delim="semicolon": self. settings.__setattr__("delimiter", delim)) delimiter.addAction(semicolon) add_header = QAction("&Include CSV header", self.tool_window.ui_area, checkable=True) add_header.setChecked(self.settings.include_header) add_header.triggered.connect(self.header_check) export.addAction(add_header) tab.triggered.connect( lambda *args, action=semicolon: action.setChecked(False)) semicolon.triggered.connect( lambda *args, action=tab: action.setChecked(False)) archive = QAction("Include archive if present", self.tool_window.ui_area, checkable=True) archive.triggered.connect( lambda checked: setattr(self.settings, "archive", checked)) archive.triggered.connect( lambda *args: self.fill_table(self.file_selector.count() - 1)) archive.setChecked(self.settings.archive) export.addAction(archive) unit = menu.addMenu("&Units") energy = unit.addMenu("energy") hartree = QAction("Hartree", self.tool_window.ui_area, checkable=True) hartree.setChecked(self.settings.energy == "Hartree") kcal = QAction("kcal/mol", self.tool_window.ui_area, checkable=True) kcal.setChecked(self.settings.energy == "kcal/mol") kjoule = QAction("kJ/mol", self.tool_window.ui_area, checkable=True) kjoule.setChecked(self.settings.energy == "kJ/mol") energy.addAction(hartree) energy.addAction(kcal) energy.addAction(kjoule) hartree.triggered.connect( lambda *args, val="Hartree": setattr(self.settings, "energy", val)) hartree.triggered.connect( lambda *args: self.fill_table(self.file_selector.count() - 1)) hartree.triggered.connect( lambda *args, action=kcal: action.setChecked(False)) hartree.triggered.connect( lambda *args, action=kjoule: action.setChecked(False)) kcal.triggered.connect(lambda *args, val="kcal/mol": setattr( self.settings, "energy", val)) kcal.triggered.connect( lambda *args: self.fill_table(self.file_selector.count() - 1)) kcal.triggered.connect( lambda *args, action=hartree: action.setChecked(False)) kcal.triggered.connect( lambda *args, action=kjoule: action.setChecked(False)) kjoule.triggered.connect( lambda *args, val="kJ/mol": setattr(self.settings, "energy", val)) kjoule.triggered.connect( lambda *args: self.fill_table(self.file_selector.count() - 1)) kjoule.triggered.connect( lambda *args, action=hartree: action.setChecked(False)) kjoule.triggered.connect( lambda *args, action=kcal: action.setChecked(False)) mass = unit.addMenu("mass") kg = QAction("kg", self.tool_window.ui_area, checkable=True) kg.setChecked(self.settings.mass == "kg") amu = QAction("Da", self.tool_window.ui_area, checkable=True) amu.setChecked(self.settings.mass == "Da") mass.addAction(kg) mass.addAction(amu) kg.triggered.connect( lambda *args, val="kg": setattr(self.settings, "mass", val)) kg.triggered.connect( lambda *args: self.fill_table(self.file_selector.count() - 1)) kg.triggered.connect( lambda *args, action=amu: action.setChecked(False)) amu.triggered.connect( lambda *args, val="Da": setattr(self.settings, "mass", val)) amu.triggered.connect( lambda *args: self.fill_table(self.file_selector.count() - 1)) amu.triggered.connect( lambda *args, action=kg: action.setChecked(False)) rot_const = unit.addMenu("rotational constants") temperature = QAction("K", self.tool_window.ui_area, checkable=True) temperature.setChecked(self.settings.rot_const == "K") hertz = QAction("GHz", self.tool_window.ui_area, checkable=True) hertz.setChecked(self.settings.rot_const == "GHz") rot_const.addAction(temperature) rot_const.addAction(hertz) temperature.triggered.connect( lambda *args, val="K": setattr(self.settings, "rot_const", val)) temperature.triggered.connect( lambda *args: self.fill_table(self.file_selector.count() - 1)) temperature.triggered.connect( lambda *args, action=hertz: action.setChecked(False)) hertz.triggered.connect( lambda *args, val="GHz": setattr(self.settings, "rot_const", val)) hertz.triggered.connect( lambda *args: self.fill_table(self.file_selector.count() - 1)) hertz.triggered.connect( lambda *args, action=temperature: action.setChecked(False)) menu.setNativeMenuBar(False) self._menu = menu layout.setMenuBar(menu) menu.setVisible(True) if len(self.session.filereader_manager.list()) > 0: self.fill_table(0) self.tool_window.ui_area.setLayout(layout) self.tool_window.manage(None)
def _build_ui(self): layout = QFormLayout() self.radii_option = QComboBox() self.radii_option.addItems(["Bondi", "UMN"]) ndx = self.radii_option.findText(self.settings.radii, Qt.MatchExactly) self.radii_option.setCurrentIndex(ndx) layout.addRow("radii:", self.radii_option) self.L_style = QComboBox() self.L_style.addItems(["FORTRAN", "AaronTools"]) ndx = self.L_style.findText(self.settings.L_style, Qt.MatchExactly) self.L_style.setCurrentIndex(ndx) self.L_style.setToolTip( """FORTRAN: Add 0.4 + the ideal X-H bond length to the length of the substituent AaronTools: add VDW radius to the length of the substituent""") layout.addRow("L correction:", self.L_style) self.display_vectors = QCheckBox() self.display_vectors.setChecked(self.settings.display_vectors) layout.addRow("show vectors:", self.display_vectors) self.display_radii = QCheckBox() self.display_radii.setChecked(self.settings.display_radii) layout.addRow("show radii:", self.display_radii) calc_sterimol_button = QPushButton( "calculate parameters for selected substituents") calc_sterimol_button.clicked.connect(self.calc_sterimol) layout.addRow(calc_sterimol_button) self.calc_sterimol_button = calc_sterimol_button remove_sterimol_button = QPushButton("remove Sterimol visualizations") remove_sterimol_button.clicked.connect(self.del_sterimol) layout.addRow(remove_sterimol_button) self.remove_sterimol_button = remove_sterimol_button self.table = QTableWidget() self.table.setColumnCount(8) self.table.setHorizontalHeaderLabels([ 'model', 'substituent atom', 'B\u2081', 'B\u2082', 'B\u2083', 'B\u2084', 'B\u2085', 'L', ]) self.table.setSelectionBehavior(QTableWidget.SelectRows) self.table.setEditTriggers(QTableWidget.NoEditTriggers) self.table.resizeColumnToContents(0) self.table.resizeColumnToContents(1) self.table.resizeColumnToContents(2) self.table.resizeColumnToContents(3) self.table.resizeColumnToContents(4) self.table.resizeColumnToContents(5) self.table.resizeColumnToContents(6) self.table.resizeColumnToContents(7) self.table.horizontalHeader().setSectionResizeMode( 2, QHeaderView.Stretch) self.table.horizontalHeader().setSectionResizeMode( 3, QHeaderView.Stretch) self.table.horizontalHeader().setSectionResizeMode( 4, QHeaderView.Stretch) self.table.horizontalHeader().setSectionResizeMode( 5, QHeaderView.Stretch) self.table.horizontalHeader().setSectionResizeMode( 6, QHeaderView.Stretch) self.table.horizontalHeader().setSectionResizeMode( 7, QHeaderView.Stretch) layout.addRow(self.table) menu = QMenuBar() export = menu.addMenu("&Export") clear = QAction("Clear data table", self.tool_window.ui_area) clear.triggered.connect(self.clear_table) export.addAction(clear) copy = QAction("&Copy CSV to clipboard", self.tool_window.ui_area) copy.triggered.connect(self.copy_csv) shortcut = QKeySequence(Qt.CTRL + Qt.Key_C) copy.setShortcut(shortcut) export.addAction(copy) save = QAction("&Save CSV...", self.tool_window.ui_area) save.triggered.connect(self.save_csv) #this shortcut interferes with main window's save shortcut #I've tried different shortcut contexts to no avail #thanks Qt... #shortcut = QKeySequence(Qt.CTRL + Qt.Key_S) #save.setShortcut(shortcut) #save.setShortcutContext(Qt.WidgetShortcut) export.addAction(save) delimiter = export.addMenu("Delimiter") comma = QAction("comma", self.tool_window.ui_area, checkable=True) comma.setChecked(self.settings.delimiter == "comma") comma.triggered.connect(lambda *args, delim="comma": self.settings. __setattr__("delimiter", delim)) delimiter.addAction(comma) tab = QAction("tab", self.tool_window.ui_area, checkable=True) tab.setChecked(self.settings.delimiter == "tab") tab.triggered.connect(lambda *args, delim="tab": self.settings. __setattr__("delimiter", delim)) delimiter.addAction(tab) space = QAction("space", self.tool_window.ui_area, checkable=True) space.setChecked(self.settings.delimiter == "space") space.triggered.connect(lambda *args, delim="space": self.settings. __setattr__("delimiter", delim)) delimiter.addAction(space) semicolon = QAction("semicolon", self.tool_window.ui_area, checkable=True) semicolon.setChecked(self.settings.delimiter == "semicolon") semicolon.triggered.connect(lambda *args, delim="semicolon": self. settings.__setattr__("delimiter", delim)) delimiter.addAction(semicolon) add_header = QAction("&Include CSV header", self.tool_window.ui_area, checkable=True) add_header.setChecked(self.settings.include_header) add_header.triggered.connect(self.header_check) export.addAction(add_header) comma.triggered.connect( lambda *args, action=tab: action.setChecked(False)) comma.triggered.connect( lambda *args, action=space: action.setChecked(False)) comma.triggered.connect( lambda *args, action=semicolon: action.setChecked(False)) tab.triggered.connect( lambda *args, action=comma: action.setChecked(False)) tab.triggered.connect( lambda *args, action=space: action.setChecked(False)) tab.triggered.connect( lambda *args, action=semicolon: action.setChecked(False)) space.triggered.connect( lambda *args, action=comma: action.setChecked(False)) space.triggered.connect( lambda *args, action=tab: action.setChecked(False)) space.triggered.connect( lambda *args, action=semicolon: action.setChecked(False)) semicolon.triggered.connect( lambda *args, action=comma: action.setChecked(False)) semicolon.triggered.connect( lambda *args, action=tab: action.setChecked(False)) semicolon.triggered.connect( lambda *args, action=space: action.setChecked(False)) menu.setNativeMenuBar(False) self._menu = menu layout.setMenuBar(menu) menu.setVisible(True) self.tool_window.ui_area.setLayout(layout) self.tool_window.manage(None)