class MainWindow(QMainWindow): def __init__(self, parent=None, movable=False): super(MainWindow, self).__init__() self.setAcceptDrops(True) self.shellWin = PlainTextEdit() self.setCentralWidget(self.shellWin) self.setGeometry(0, 0, 600, 600) self.setWindowTitle("QTerminal") self.settings = QSettings("QTerminal", "QTerminal") self.readSettings() def closeEvent(self, e): self.writeSettings() def readSettings(self): if self.settings.contains("commands"): self.shellWin.commands = self.settings.value("commands") if self.settings.contains("pos"): pos = self.settings.value("pos", QPoint(200, 200)) self.move(pos) if self.settings.contains("size"): size = self.settings.value("size", QSize(400, 400)) self.resize(size) def writeSettings(self): self.settings.setValue("commands", self.shellWin.commands) self.settings.setValue("pos", self.pos()) self.settings.setValue("size", self.size())
def loadSettings(self): settings = QSettings(QSettings.UserScope, 'Georgia Tech', 'RamanGui', self) if settings.contains('alpha'): self.alphaBox.setText(settings.value('alpha')) if settings.contains('l1Ratio'): self.l1RatioBox.setText(settings.value('l1Ratio'))
def _load_settings(self): # try: # with open(self.settings_path, 'r') as f: # settings = json.load(f) settings = QSettings("Maccesch", "SongScreen") if settings.contains('lyrics_screen'): self.display_lyrics_on_screen(settings.value('lyrics_screen')) if settings.contains('control_window_position'): self.move(settings.value('control_window_position')) for key in settings.allKeys(): self.settings[key] = settings.value(key) # self.settings.update(settings) self.songtext_widget.set_font_size(self.settings['font_size']) self.songtext_widget.set_line_increment(self.settings['line_increment']) # except (FileNotFoundError, ValueError): # pass if not os.path.exists(self.lyrics_language_path) or not self.settings['lyrics_language']: languages = list( filter(lambda p: os.path.isdir(os.path.join(self.lyrics_path, p)) and p != "timings", os.listdir(self.lyrics_path)) ) self.settings['lyrics_language'] = languages[0] if languages else ""
def IsApisIni(ini): s = QSettings(ini, QSettings.IniFormat) requiredKeysIsFile = ['database_file'] requiredKeysIsDir = [ 'flightpath_dir', 'image_dir', 'ortho_image_dir', 'repr_image_dir', 'insp_image_dir' ] requiredKeys = [ 'hires_vertical', 'hires_oblique_digital', 'hires_oblique_analog' ] isIni = True errorKeys = [] for k in requiredKeysIsFile: key = "APIS/" + k if not s.contains(key) or not os.path.isfile(s.value(key)): isIni = False errorKeys.append(k) for k in requiredKeysIsDir: key = "APIS/" + k if not s.contains(key) or not os.path.isdir(s.value(key)): isIni = False errorKeys.append(k) for k in requiredKeys: key = "APIS/" + k if not s.contains(key): isIni = False errorKeys.append(k) return isIni, s if isIni else tr( "Folgende Schlüssel in der INI Datei sind nicht korrekt oder nicht vorhanden: " ) + ", ".join(errorKeys)
def __restore_window_state(self): settings = QSettings(os.path.join(CONFIG, 'qt.ini'), QSettings.IniFormat) if settings.contains("geometry"): self.restoreGeometry(settings.value("geometry")) if settings.contains("window_state"): self.restoreState(settings.value("window_state")) if settings.contains("toolbox_expanded"): self.__toolbox.expanded = settings.value("toolbox_expanded", type=bool)
def set_list_creneaux(cls): """ Permet de charger la liste contenant tout les creneaux déjà créés""" fichier = Qst(OPTION, Qst.IniFormat) if fichier.contains("Tableau/tab_creneau"): cls.listCreneaux = fichier.value("Tableau/tab_creneau") cls.nombreCreneaux = len(cls.listCreneaux) if fichier.contains("List/categorie_Creneau"): cls.catCreneaux = fichier.value("List/categorie_Creneau") cls.etatCatCre = fichier.value("List/categorie_Creneau_state")
def LoadSettings(self): settingsPath = QDir.temp().absoluteFilePath("polygonize.ini") settings = QSettings(settingsPath, QSettings.IniFormat) settings.beginGroup("export") if settings.contains("path"): self.ui.le_Path.setText(settings.value("path")) if settings.contains("name"): self.ui.le_Name.setText(settings.value("name")) settings.endGroup()
def read_settings(self): """Read settings.""" group_name = self.__class__.__name__ settings = QSettings() settings.beginGroup(group_name) if settings.contains('size'): self.resize(settings.value('size')) if settings.contains('pos'): self.move(settings.value('pos')) settings.endGroup()
def getAutoLoadValues(self): sttgns = QSettings() if sttgns.contains("autoLoad"): autoLoad = True if sttgns.value("autoLoad") in ["true", True ] else False else: autoLoad = False if autoLoad and sttgns.contains("lastProject"): last = sttgns.value("lastProject") else: last = "" return autoLoad, last
def run(): app = QApplication(sys.argv) app.setOrganizationName("manuskript") app.setOrganizationDomain("www.theologeek.ch") app.setApplicationName("manuskript") app.setApplicationVersion(_version) icon = QIcon() for i in [16, 31, 64, 128, 256, 512]: icon.addFile(appPath("icons/Manuskript/icon-{}px.png".format(i))) qApp.setWindowIcon(icon) app.setStyle("Fusion") # Load style from QSettings settings = QSettings(app.organizationName(), app.applicationName()) if settings.contains("applicationStyle"): style = settings.value("applicationStyle") app.setStyle(style) # Translation process locale = QLocale.system().name() appTranslator = QTranslator() # By default: locale translation = appPath( os.path.join("i18n", "manuskript_{}.qm".format(locale))) # Load translation from settings if settings.contains("applicationTranslation"): translation = appPath( os.path.join("i18n", settings.value("applicationTranslation"))) print("Found translation in settings:", translation) if appTranslator.load(translation): app.installTranslator(appTranslator) print(app.tr("Loaded translation: {}.").format(translation)) else: print( app.tr("Warning: failed to load translator for locale {}..."). format(locale)) QIcon.setThemeSearchPaths(QIcon.themeSearchPaths() + [appPath("icons")]) QIcon.setThemeName("NumixMsk") # qApp.setWindowIcon(QIcon.fromTheme("im-aim")) # Seperating launch to avoid segfault, so it seem. # Cf. http://stackoverflow.com/questions/12433491/is-this-pyqt-4-python-bug-or-wrongly-behaving-code launch()
def read_settings(self): """Read settings.""" group_name = self.__class__.__name__ settings = QSettings() settings.beginGroup(group_name) self.resize(settings.value('size', defaults.RESULT_TABLE_VIEW_SIZE)) if settings.contains('pos'): self.move(settings.value('pos')) if settings.contains('horizontal_header_state'): self.horizontalHeader().restoreState( settings.value('horizontal_header_state')) settings.endGroup()
def __init__(self, cookies: dict): self.server = cookies['server'] self.channel = cookies['channel'] self.cookies = cookies['cookies'] self.hlp = LoginHelper() qsettings = QSettings(get_qsettings_file(), QSettings.IniFormat) if qsettings.contains(QKEYS.CONN_API_RTY) is True: self.max_retry = qsettings.value(QKEYS.CONN_API_RTY, type=int) else: self.max_retry = 5 if qsettings.contains(QKEYS.CONN_API_SLP) is True: self.sleep_time = qsettings.value(QKEYS.CONN_API_SLP, type=int) else: self.sleep_time = 3
def readSettings(self): settings = QSettings() settings.beginGroup('MainWindow') if settings.value('isMaximized') == True: self.setWindowState(Qt.WindowMaximized) else: self.resize(settings.value('size', QSize(800, 500))) # if there is no position already saved, it will center itself if settings.contains('pos'): self.move(settings.value('pos')) else: screenGeometry = QGuiApplication.primaryScreen().geometry() screenHeight = screenGeometry.height() screenWidth = screenGeometry.width() self.move( QPoint((screenWidth - self.size().width()) / 2, (screenHeight - self.size().height()) / 2)) self.fileDialogDirectory = Path( settings.value('fileDialogDirectory', Path().home())) settings.endGroup() settings.beginGroup('Panels') self.trackerDock.setVisible( settings.value('tracker', 'true') == 'true') self.imageGridDock.setVisible( settings.value('imageGrid', 'true') == 'true') self.trackerAddDock.setVisible( settings.value('trackerAdd', 'true') == 'true') settings.endGroup() settings.beginGroup('ImageGrid') self.imageGridViewer.rows = settings.value('rows', 2) self.imageGridViewer.cols = settings.value('cols', 2) settings.endGroup() settings.beginGroup('ImagePainter') self.imagePainter.penWidth = settings.value('penWidth', 30) if settings.contains('penColor'): self.imagePainter.setPenColor(settings.value('penColor')) else: self.imagePainter.setDefaultPenColor() settings.endGroup()
def charger_horaire(fileName, listwid): ##fonction pour charger les donnees d'une Qlist cleState = "List/Horaire_state" fi = Qst(fileName,Qst.IniFormat) dejaPresent = [] if fi.contains(cleState): for i in range(listwid.count()): dejaPresent.append(listwid.item(i).text().title()) state = fi.value(cleState) for i in range(len(HORAIRE)): if not(HORAIRE[i] in dejaPresent) : item = QtWidgets.QListWidgetItem(HORAIRE[i].title(), listwid) item.setTextAlignment(QtCore.Qt.AlignCenter) item.setFlags(item.flags() | QtCore.Qt.ItemIsUserCheckable) if int(state[i]) == 2: item.setCheckState(QtCore.Qt.Checked) if int(state[i]) == 0: item.setCheckState(QtCore.Qt.Unchecked) return state else: state = ["0"]*24 for horaire in HORAIRE: if not(horaire in dejaPresent) : item = QtWidgets.QListWidgetItem(horaire.title(), listwid) item.setTextAlignment(QtCore.Qt.AlignCenter) item.setFlags(item.flags() | QtCore.Qt.ItemIsUserCheckable) item.setCheckState(QtCore.Qt.Unchecked) return state
def requireScripts(self, urlList): """ Public method to get the sources of all required scripts. @param urlList list of URLs (list of string) @return sources of all required scripts (string) """ requiresDir = QDir(self.requireScriptsDirectory()) if not requiresDir.exists() or len(urlList) == 0: return "" script = "" settings = QSettings( os.path.join(self.requireScriptsDirectory(), "requires.ini"), QSettings.IniFormat) settings.beginGroup("Files") for url in urlList: if settings.contains(url): fileName = settings.value(url) try: f = open(fileName, "r", encoding="utf-8") source = f.read() f.close() except (IOError, OSError): source = "" script += source.strip() + "\n" return script
def load_file(self, fname): self.sheets = [ os.path.basename(fname) ] self.schdata = [self.read_file(fname)] self.file_format_ver = re.match('EESchema Schematic File Version (\d)', self.schdata[0]).group(1) pattern = '\$Sheet\s.+\s.+\sF0.+\sF1\s\"(.+)\".+\s\$EndSheet' self.dirname = os.path.dirname(fname) self.sheets += list( set( re.findall(pattern, self.schdata[0]) ) ) #print(self.sheets) sheets_paths = [ os.path.join(self.dirname, filepath) for filepath in self.sheets ] for sheet in sheets_paths[1:]: self.schdata.append(self.read_file(sheet)) Settings = QSettings('kicad-tools', 'Schematic Component Manager') if Settings.contains('component-ignore'): ipl = Settings.value('component-ignore') else: ipl = [] cmp_dict = { } rcls = [] for schdata in self.schdata: rcls.append( self.raw_cmp_list(schdata) ) # rcl - raw component list cmp_dict = self.create_cmp_dict( rcls, ipl ) self.current_file_path = fname self.cmp_dict = cmp_dict return cmp_dict
def __init__(self, parent=None, aw=None, title="", content=""): super(HelpDlg, self).__init__(parent, aw) self.setWindowTitle(title) self.setModal(False) settings = QSettings() if settings.contains("HelpGeometry"): self.restoreGeometry(settings.value("HelpGeometry")) phelp = QTextEdit() phelp.setHtml(content) phelp.setReadOnly(True) # connect the ArtisanDialog standard OK/Cancel buttons self.dialogbuttons.removeButton( self.dialogbuttons.button(QDialogButtonBox.Cancel)) self.dialogbuttons.accepted.connect(self.close) buttonLayout = QHBoxLayout() buttonLayout.addStretch() buttonLayout.addWidget(self.dialogbuttons) hLayout = QVBoxLayout() hLayout.addWidget(phelp) hLayout.addLayout(buttonLayout) self.setLayout(hLayout) self.dialogbuttons.button(QDialogButtonBox.Ok).setFocus()
def getThemeName(theme): settings = QSettings(theme, QSettings.IniFormat) if settings.contains("Name"): return settings.value("Name") else: return os.path.splitext(os.path.split(theme)[1])[0]
def update_cmp_list(self, cd): keys = list( cd.keys() ) keys.sort( key=split_alphanumeric ) self.setRowCount(len(cd)) Settings = QSettings('kicad-tools', 'Schematic Component Manager') if Settings.contains('component-view'): CmpViewDict = Settings.value('component-view') else: CmpViewDict = {} for idx, k in enumerate( keys ): Ref = QTableWidgetItem(k) res = re.match('([a-zA-Z]+)\d+', k) Pattern = '$LibRef' if res: RefBase = res.groups()[0] if RefBase in CmpViewDict.keys(): Pattern = CmpViewDict[RefBase] cmp = cd[k][0] info_str = cmp.get_str_from_pattern(Pattern) Name = QTableWidgetItem(info_str) self.setItem(idx, 0, Ref) self.setItem(idx, 1, Name)
def __init__(self, parent = None, aw = None, title = "", content = ""): super(HelpDlg,self).__init__(parent, aw) self.setWindowTitle(title) self.setModal(False) settings = QSettings() if settings.contains("HelpGeometry"): self.restoreGeometry(settings.value("HelpGeometry")) phelp = QTextEdit() phelp.setHtml(content) phelp.setReadOnly(True) # connect the ArtisanDialog standard OK/Cancel buttons self.dialogbuttons.removeButton(self.dialogbuttons.button(QDialogButtonBox.Cancel)) self.dialogbuttons.accepted.connect(self.close) homeLabel = QLabel() homeLabel.setText("{} {}".format(QApplication.translate("Label", "For more details visit", None), "<a href='https://artisan-scope.org'>artisan-scope.org</a>")) homeLabel.setOpenExternalLinks(True) buttonLayout = QHBoxLayout() buttonLayout.addWidget(homeLabel) buttonLayout.addStretch() buttonLayout.addWidget(self.dialogbuttons) hLayout = QVBoxLayout() hLayout.addWidget(phelp) hLayout.addLayout(buttonLayout) self.setLayout(hLayout) self.dialogbuttons.button(QDialogButtonBox.Ok).setFocus()
def update_cmp_list(self, cd): keys = list(cd.keys()) keys.sort(key=split_alphanumeric) self.setRowCount(len(cd)) Settings = QSettings('kicad-tools', 'Schematic Component Manager') if Settings.contains('component-view'): CmpViewDict = Settings.value('component-view') else: CmpViewDict = {} for idx, k in enumerate(keys): Ref = QTableWidgetItem(k) res = re.match('([a-zA-Z]+)\d+', k) Pattern = '$LibRef' if res: RefBase = res.groups()[0] if RefBase in CmpViewDict.keys(): Pattern = CmpViewDict[RefBase] cmp = cd[k][0] info_str = cmp.get_str_from_pattern(Pattern) Name = QTableWidgetItem(info_str) self.setItem(idx, 0, Ref) self.setItem(idx, 1, Name)
class SubUI(QWidget): def __init__(self): super().__init__() self.settings = QSettings("OrganizationName", "ApplicationName") self.label = QLabel("Input to save text") self.le = QLineEdit() self.init_ui() self.load_settings() def __del__(self): self.save_settings() def init_ui(self): hlayout = QHBoxLayout() hlayout.addWidget(self.label) hlayout.addWidget(self.le) self.setLayout(hlayout) def save_settings(self): self.settings.setValue("label", self.le.text()) def load_settings(self): if self.settings.contains("label"): self.le.setText(self.settings.value("label"))
def charger_variable(fileName,typevariable): # chargement d'une variable classique cle = "Variables/"+str(typevariable) fi = Qst(fileName,Qst.IniFormat) variable = False if fi.contains(cle): variable = fi.value(cle) return variable #retourne la variable = False si inexistante
def load_file(self, fname): self.sheets = [os.path.basename(fname)] self.schdata = [self.read_file(fname)] self.file_format_ver = re.match('EESchema Schematic File Version (\d)', self.schdata[0]).group(1) pattern = '\$Sheet\s.+\s.+\sF0.+\sF1\s\"(.+)\".+\s\$EndSheet' self.dirname = os.path.dirname(fname) self.sheets += list(set(re.findall(pattern, self.schdata[0]))) #print(self.sheets) sheets_paths = [ os.path.join(self.dirname, filepath) for filepath in self.sheets ] for sheet in sheets_paths[1:]: self.schdata.append(self.read_file(sheet)) Settings = QSettings('kicad-tools', 'Schematic Component Manager') if Settings.contains('component-ignore'): ipl = Settings.value('component-ignore') else: ipl = [] cmp_dict = {} rcls = [] for schdata in self.schdata: rcls.append(self.raw_cmp_list(schdata)) # rcl - raw component list cmp_dict = self.create_cmp_dict(rcls, ipl) self.current_file_path = fname self.cmp_dict = cmp_dict return cmp_dict
def get_postgres_conn_info(selected): """ Read PostgreSQL connection details from QSettings stored by QGIS """ settings = QSettings() settings.beginGroup(u"/PostgreSQL/connections/" + selected) if not settings.contains("database"): # non-existent entry? return {} conn_info = dict() conn_info["host"] = settings.value("host", "", type=str) # password and username username = '' password = '' authconf = settings.value('authcfg', '') if authconf: # password encrypted in AuthManager auth_manager = QgsApplication.authManager() conf = QgsAuthMethodConfig() auth_manager.loadAuthenticationConfig(authconf, conf, True) if conf.id(): username = conf.config('username', '') password = conf.config('password', '') else: # basic (plain-text) settings username = settings.value('username', '', type=str) password = settings.value('password', '', type=str) return username, password
def load_init_data(self): setting = QSettings() if setting.contains('DB/init_data'): _data = setting.value('DB/init_data', [0, 0, []]) else: _data = [0, 0, []] self.last_db_no = _data[1] self.init_data = _data
def charger_horaire_artistes(fileName, tableau): cleV = "List/artistesVendredi" cleS = "List/artistesSamedi" artV, artS = ['','','','','','','',''], ['','','','','','','',''] fi = Qst(fileName, Qst.IniFormat) if fi.contains(cleV): artV = fi.value(cleV) for i in range(0,len(artV),2): item = M.item_tab_hor_artistes(artV[i]) tableau.setItem(i//2,0,item) if fi.contains(cleS): artS = fi.value(cleS) for i in range(0,len(artS),2): item = M.item_tab_hor_artistes(artS[i]) tableau.setItem(i//2,1,item) tableau.resizeColumnsToContents() return artV, artS
def run(): app = QApplication(sys.argv) app.setOrganizationName("manuskript") app.setOrganizationDomain("www.theologeek.ch") app.setApplicationName("manuskript") app.setApplicationVersion(_version) icon = QIcon() for i in [16, 31, 64, 128, 256, 512]: icon.addFile(appPath("icons/Manuskript/icon-{}px.png".format(i))) qApp.setWindowIcon(icon) app.setStyle("Fusion") # Load style from QSettings settings = QSettings(app.organizationName(), app.applicationName()) if settings.contains("applicationStyle"): style = settings.value("applicationStyle") app.setStyle(style) # Translation process locale = QLocale.system().name() appTranslator = QTranslator() # By default: locale translation = appPath(os.path.join("i18n", "manuskript_{}.qm".format(locale))) # Load translation from settings if settings.contains("applicationTranslation"): translation = appPath(os.path.join("i18n", settings.value("applicationTranslation"))) print("Found translation in settings:", translation) if appTranslator.load(translation): app.installTranslator(appTranslator) print(app.tr("Loaded translation: {}.").format(translation)) else: print(app.tr("Warning: failed to load translator for locale {}...").format(locale)) QIcon.setThemeSearchPaths(QIcon.themeSearchPaths() + [appPath("icons")]) QIcon.setThemeName("NumixMsk") # qApp.setWindowIcon(QIcon.fromTheme("im-aim")) # Seperating launch to avoid segfault, so it seem. # Cf. http://stackoverflow.com/questions/12433491/is-this-pyqt-4-python-bug-or-wrongly-behaving-code launch()
def set_up_ui(self): # Set size from last resize, if any settings = QSettings() if settings.contains(MultiOsUtil.LAST_BULKADD_SIZE_SETTING): last_size = settings.value(MultiOsUtil.LAST_BULKADD_SIZE_SETTING) self.ui.resize(last_size) self.ui.installEventFilter(self)
def moveArthurbackendPrint(): k = "arthurbackend_print" oldk = "musicview/" + k newk = "printing/" + k s = QSettings() if s.contains(oldk): s.setValue(newk, s.value(oldk)) s.remove(oldk)
class AppSettings: def __init__(self): self.settings = QSettings('Tuxtas', 'MyQueryTutor') def has_settings(self): if self.settings.contains('MainWindow/geometry'): return True else: return False def set_geometry(self, main_win, splitter_1, splitter_2): self.settings.setValue("MainWindow/geometry", main_win) self.settings.setValue("MainWindow/splitter_1", splitter_1) self.settings.setValue("MainWindow/splitter_2", splitter_2) def get_geometry(self): return self.settings.value("MainWindow/geometry") def get_splitter_1_geometry(self): return self.settings.value('MainWindow/splitter_1', [], int) def get_splitter_2_geometry(self): return self.settings.value('MainWindow/splitter_2', [], int) def set_user_details(self, first_name, surname, email): self.settings.setValue("User/FirstName", first_name) self.settings.setValue("User/Surname", surname) self.settings.setValue("User/email", email) def get_user_details(self): first_name = self.settings.value("User/FirstName") surname = self.settings.value("User/Surname") email = self.settings.value("User/email") return first_name, surname, email def set_server_details(self, server_address, class_key, time_stamp, ssl_on): self.settings.setValue("Server/address", server_address) self.settings.setValue("Server/class_key", class_key) self.settings.setValue("Server/time_stamp", time_stamp) self.settings.setValue("Server/ssl", ssl_on) self.settings.sync() def get_server_details(self): server = self.settings.value("Server/address") class_key = self.settings.value("Server/class_key") ssl_val = self.settings.value("Server/ssl") if ssl_val == 'true': ssl = True else: ssl = False return server, class_key, ssl def set_time_stamp(self, time_stamp): self.settings.setValue("Server/time_stamp", time_stamp) def get_time_stamp(self): return self.settings.value("Server/time_stamp")
def load(self, scheme): """Load the settings for the scheme. Called on init.""" s = QSettings() s.beginGroup("fontscolors/" + scheme) # load font defaultfont = "Lucida Console" if os.name == "nt" else "monospace" self.font = QFont(s.value("fontfamily", defaultfont, str)) self.font.setPointSizeF(s.value("fontsize", 10.0, float)) # load base colors s.beginGroup("basecolors") for name in baseColors: if s.contains(name): self.baseColors[name] = QColor(s.value(name, "", str)) else: self.baseColors[name] = baseColorDefaults[name]() s.endGroup() # get the list of supported styles from ly.colorize all_styles = ly.colorize.default_mapping() default_styles = set() for group, styles in all_styles: d = self._inherits[group] = {} for style in styles: if style.base: default_styles.add(style.base) d[style.name] = style.base default_scheme = ly.colorize.default_scheme # load default styles s.beginGroup("defaultstyles") for name in default_styles: self.defaultStyles[name] = f = QTextCharFormat() css = default_scheme[None].get(name) if css: css2fmt(css, f) s.beginGroup(name) self.loadTextFormat(f, s) s.endGroup() s.endGroup() # load specific styles s.beginGroup("allstyles") for group, styles in all_styles: self.allStyles[group] = {} s.beginGroup(group) for style in styles: self.allStyles[group][style.name] = f = QTextCharFormat() css = default_scheme[group].get(style.name) if css: css2fmt(css, f) s.beginGroup(style.name) self.loadTextFormat(f, s) s.endGroup() s.endGroup() s.endGroup()
def load(self, scheme): """Load the settings for the scheme. Called on init.""" s = QSettings() s.beginGroup("fontscolors/" + scheme) # load font defaultfont = "Lucida Console" if os.name == "nt" else "monospace" self.font = QFont(s.value("fontfamily", defaultfont, str)) self.font.setPointSizeF(s.value("fontsize", 10.0, float)) # load base colors s.beginGroup("basecolors") for name in baseColors: if s.contains(name): self.baseColors[name] = QColor(s.value(name, "", str)) else: self.baseColors[name] = baseColorDefaults[name]() s.endGroup() # get the list of supported styles from ly.colorize all_styles = ly.colorize.default_mapping() default_styles = set() for group, styles in all_styles: d = self._inherits[group] = {} for style in styles: if style.base: default_styles.add(style.base) d[style.name] = style.base default_scheme = ly.colorize.default_scheme # load default styles s.beginGroup("defaultstyles") for name in default_styles: self.defaultStyles[name] = f = QTextCharFormat() css = default_scheme[None].get(name) if css: css2fmt(css, f) s.beginGroup(name) self.loadTextFormat(f, s) s.endGroup() s.endGroup() # load specific styles s.beginGroup("allstyles") for group, styles in all_styles: self.allStyles[group]= {} s.beginGroup(group) for style in styles: self.allStyles[group][style.name] = f = QTextCharFormat() css = default_scheme[group].get(style.name) if css: css2fmt(css, f) s.beginGroup(style.name) self.loadTextFormat(f, s) s.endGroup() s.endGroup() s.endGroup()
def readSettings(self): # Load State and geometry sttgns = QSettings(qApp.organizationName(), qApp.applicationName()) if sttgns.contains("geometry"): self.restoreGeometry(sttgns.value("geometry")) if sttgns.contains("windowState"): self.restoreState(sttgns.value("windowState")) else: self.dckCheatSheet.hide() self.dckSearch.hide() if sttgns.contains("metadataState"): state = [False if v == "false" else True for v in sttgns.value("metadataState")] self.redacMetadata.restoreState(state) if sttgns.contains("revisionsState"): state = [False if v == "false" else True for v in sttgns.value("revisionsState")] self.redacMetadata.revisions.restoreState(state) if sttgns.contains("splitterRedacH"): self.splitterRedacH.restoreState(sttgns.value("splitterRedacH")) if sttgns.contains("splitterRedacV"): self.splitterRedacV.restoreState(sttgns.value("splitterRedacV")) if sttgns.contains("toolbar"): # self.toolbar is not initialized yet, so we just store balue self._toolbarState = sttgns.value("toolbar") else: self._toolbarState = ""
def restoreSettings(self): settings = QSettings(version.organisation, version.appname) settings.beginGroup('preferences') if settings.contains('host'): self.host = settings.value('host', type=str) if settings.contains('port'): self.port = settings.value('port', type=int) if settings.contains('path_mapping'): self.mapping_str = settings.value('path_mapping') if settings.contains('target_platform'): self.target_platform = settings.value('target_platform') if settings.contains('batch_size'): self.batch_size = settings.value('batch_size', type=int) if settings.contains('cluster_support'): self.cluster_support = settings.value('cluster_support', type=bool) if settings.contains('stylesheet'): self.stylesheet = settings.value('stylesheet', type=str) settings.endGroup()
def readSettings(self): # Load State and geometry sttgns = QSettings(qApp.organizationName(), qApp.applicationName()) if sttgns.contains("geometry"): self.restoreGeometry(sttgns.value("geometry")) if sttgns.contains("windowState"): self.restoreState(sttgns.value("windowState")) else: self.dckCheatSheet.hide() self.dckSearch.hide() if sttgns.contains("metadataState"): state = [ False if v == "false" else True for v in sttgns.value("metadataState") ] self.redacMetadata.restoreState(state) if sttgns.contains("revisionsState"): state = [ False if v == "false" else True for v in sttgns.value("revisionsState") ] self.redacMetadata.revisions.restoreState(state) if sttgns.contains("splitterRedacH"): self.splitterRedacH.restoreState(sttgns.value("splitterRedacH")) if sttgns.contains("splitterRedacV"): self.splitterRedacV.restoreState(sttgns.value("splitterRedacV")) if sttgns.contains("toolbar"): # self.toolbar is not initialized yet, so we just store balue self._toolbarState = sttgns.value("toolbar") else: self._toolbarState = ""
def __init__(self, parent=None, aw=None): super(LargeExtraLCDs, self).__init__(parent, aw) settings = QSettings() if settings.contains("ExtraLCDGeometry"): self.restoreGeometry(settings.value("ExtraLCDGeometry")) else: self.resize(100, 200) self.chooseLayout(self.width(), self.height()) self.setWindowTitle(UIconst.TOOLKIT_MENU_EXTRA_LCDS)
class NetArchitecture(QObject): def __init__(self, parent=None): # TODO should know its name super(NetArchitecture, self).__init__() self.renderer = QSvgRenderer() self.source_url = QUrl("") self.settings = QSettings('dt', 'DeepThought') self.graph = None self.update_source() def source_setting_changed(self): return not self.settings.value('protofile') == self.source_url def update_source(self): if self.settings.contains('protofile'): source_url = QUrl(self.settings.value('protofile')) source = source_url.toDisplayString(QUrl.RemoveScheme) if os.path.isfile(source): self.source_url = source_url self.set_source(source) return not self.source_url.isEmpty() def set_source(self, caffeproto_file): net = caffe_pb2.NetParameter() text_format.Merge(open(caffeproto_file).read(), net) self.graph = caffe.draw.draw_net(net, 'LR', 'svg') # self.sourceChanged.emit('network_architecture') def get_image(self, size): if self.source_setting_changed(): self.update_source() image = QImage(size.width(), size.height(), QImage.Format_ARGB32) painter = QPainter(image) if self.graph is None: if self.settings.contains('protofile'): url = QUrl(self.settings.value('protofile')) self.set_source(url.toDisplayString(QUrl.RemoveScheme)) else: image.fill(QColor(200, 200, 200)) return image self.renderer.load(QByteArray(self.graph)) self.renderer.render(painter) return image
class Gui(QMainWindow, Ui_MainWindow): def __init__(self): QObject.__init__(self) super(Gui, self).__init__() self.setupUi(self) self.show() devs_play = DeviceList('aplay -l') devs_record = DeviceList('arecord -l', True) self.play = GuiDeviceList(devs_play, self.list_play) self.record = GuiDeviceList(devs_record, self.list_record) self.settings = QSettings('alsa_jack', 'playback') self.play.update() self.record.update() if self.settings.contains('playback'): self.play.selection_json = self.settings.value('playback') if self.settings.contains('record'): self.record.selection_json = self.settings.value('record') # noinspection PyUnresolvedReferences self.btn_update_playback.clicked.connect(self.play.update) # noinspection PyUnresolvedReferences self.btn_update_record.clicked.connect(self.record.update) self.btn_dc_all.clicked.connect(self.clearSelection) def clearSelection(self): self.list_play.clearSelection() self.list_record.clearSelection() def update_record(self): self.record.update() self.update_lists() def closeEvent(self, event): self.settings.setValue('playback', self.play.selection_json) self.settings.setValue('record', self.record.selection_json) self.play.devlist.stop() self.record.devlist.stop() print('closing')
def appendToRecentFiles(self, project): sttgns = QSettings() if sttgns.contains("recentFiles"): recentFiles = sttgns.value("recentFiles") else: recentFiles = [] while project in recentFiles: recentFiles.remove(project) recentFiles.insert(0, project) recentFiles = recentFiles[:10] sttgns.setValue("recentFiles", recentFiles)
def __init__(self, parent): #--------------------------------------------------- super().__init__(parent) self.Parent = parent #--------------------------------------------------- Settings = QSettings('kicad-tools', 'Schematic Component Manager') if Settings.contains('component-view'): CmpViewDict = Settings.value('component-view') else: CmpViewDict = { 'C' : '$Value, $Footprint', 'D' : '$LibRef', 'R' : '$Value, $Footprint' } if Settings.contains('component-ignore'): IgnoreCmpRefsList = Settings.value('component-ignore') else: IgnoreCmpRefsList = [] #--------------------------------------------------- self.CmpViewTable = self.TCmpViewTable(self, CmpViewDict) self.IgnoreCmpList = self.TIgnoreCmpList(self, IgnoreCmpRefsList) #--------------------------------------------------- self.Tabs = QTabWidget(self) self.Tabs.addTab(self.CmpViewTable, 'Component View') self.Tabs.addTab(self.IgnoreCmpList, 'Ignore Component List') #--------------------------------------------------- self.ButtonBox = QDialogButtonBox(QDialogButtonBox.Ok | QDialogButtonBox.Cancel) self.ButtonBox.accepted.connect(self.save_settings) self.ButtonBox.rejected.connect(self.cancel) #--------------------------------------------------- self.Layout = QVBoxLayout(self) self.Layout.addWidget(self.Tabs) self.Layout.addWidget(self.ButtonBox) #--------------------------------------------------- self.setWindowTitle('Settings') self.setModal(True) #--------------------------------------------------- self.shortcutHelp = QShortcut(QKeySequence(Qt.Key_F1), self) self.shortcutHelp.activated.connect(self.show_help)
def __scriptDownloaded(self): """ Private slot to handle the finished download of a script. """ if self.sender() != self.__reply: self.finished.emit() return response = bytes(self.__reply.readAll()).decode() if self.__reply.error() == QNetworkReply.NoError and \ "// ==UserScript==" in response: from Helpviewer import HelpUtilities filePath = os.path.join( self.__manager.scriptsDirectory(), HelpUtilities.getFileNameFromUrl(self.__reply.url())) self.__fileName = HelpUtilities.ensureUniqueFilename(filePath) try: f = open(self.__fileName, "w", encoding="utf-8") except (IOError, OSError) as err: E5MessageBox.critical( None, self.tr("GreaseMonkey Download"), self.tr( """<p>The file <b>{0}</b> could not be opened""" """ for writing.<br/>Reason: {1}</p>""").format( self.__fileName, str(err))) self.finished.emit() return f.write(response) f.close() settings = QSettings( os.path.join(self.__manager.requireScriptsDirectory(), "requires.ini"), QSettings.IniFormat) settings.beginGroup("Files") rx = QRegExp("@require(.*)\\n") rx.setMinimal(True) rx.indexIn(response) for i in range(1, rx.captureCount() + 1): url = rx.cap(i).strip() if url and not settings.contains(url): self.__requireUrls.append(QUrl(url)) self.__reply.deleteLater() self.__reply = None self.__downloadRequires()
def restoreSettings(self): settings = QSettings(version.organisation, version.appname) settings.beginGroup('preferences') if settings.contains('host'): self.host = settings.value('host', type=str) if settings.contains('port'): self.port = settings.value('port', type=int) if settings.contains('path_mapping'): self.mapping_str = settings.value('path_mapping') if settings.contains('target_platform'): self.target_platform = settings.value('target_platform') if settings.contains('batch_size'): self.batch_size = settings.value('batch_size', type=int) if settings.contains('cluster_support'): self.cluster_support = settings.value('cluster_support', type=bool) if settings.contains('track_length'): self.track_length = settings.value('track_length', type=int) if settings.contains('cradius'): self.cradius = settings.value('cradius', type=int) if settings.contains('display_tracks'): self.display_tracks = settings.value('display_tracks', type=bool) if settings.contains('write_logs'): self.display_tracks = settings.value('write_logs', type=bool) settings.endGroup()
def loadRecents(self): sttgns = QSettings() self.mw.menuRecents.setIcon(QIcon.fromTheme("folder-recent")) if sttgns.contains("recentFiles"): lst = sttgns.value("recentFiles") self.mw.menuRecents.clear() for f in [f for f in lst if os.path.exists(f)]: name = os.path.split(f)[1] a = QAction(name, self) a.setData(f) a.setStatusTip(f) a.triggered.connect(self.loadRecentFile) self.mw.menuRecents.addAction(a) self.btnRecent.setMenu(self.mw.menuRecents)
def switchScheme(self, scheme): if scheme not in self._shortcuts: s = QSettings() key = "shortcuts/{0}/{1}/{2}".format(scheme, self.collection.name, self.name) if s.contains(key): try: shortcuts = s.value(key, [], QKeySequence) except TypeError: # PyQt5 raises TypeError when an empty list was stored shortcuts = [] self._shortcuts[scheme] = (shortcuts, False) else: # default self._shortcuts[scheme] = (self.defaultShortcuts(), True) self.display(scheme)
def getAutoLoadValues(self): """ Reads manuskript system's settings and returns a tuple: - `bool`: whether manuskript should automatically load the last opened project or display the welcome widget. - `str`: the absolute path to the last opened project. """ sttgns = QSettings() autoLoad = sttgns.value("autoLoad", defaultValue=False, type=bool) if autoLoad and sttgns.contains("lastProject"): last = sttgns.value("lastProject") else: last = "" return autoLoad, last
def __init__(self, parent, title, path): #super().__init__(parent, Qt.WA_DeleteOnClose ) super().__init__(parent, Qt.Window) self.text_browser = QTextBrowser(self) #self.text_browser = QWebEngineView(self) self.back_button = QPushButton('Back', self) self.forward_button = QPushButton('Forward', self) self.close_button = QPushButton('Close', self) self.layout = QVBoxLayout(self) self.btn_widget = QWidget(self) self.btn_layout = QHBoxLayout(self.btn_widget) self.btn_layout.addWidget(self.back_button) self.btn_layout.addWidget(self.forward_button) self.btn_layout.addStretch(1) self.btn_layout.addWidget(self.close_button) self.shortcutEscape = QShortcut(QKeySequence(Qt.Key_Escape), self) self.shortcutEscape.activated.connect(self.close) self.layout.addWidget(self.btn_widget) self.layout.addWidget(self.text_browser) self.back_button.clicked.connect(self.text_browser.backward) self.forward_button.clicked.connect(self.text_browser.forward) self.close_button.clicked.connect(self.close) self.text_browser.setSearchPaths([os.path.join(resources_path, 'doc')]) self.text_browser.setSource(QUrl(path)) # f = QFont() # f.setPointSize(14) # self.text_browser.setFont(f) Settings = QSettings('kicad-tools', 'Schematic Component Manager') if Settings.contains('help-window'): self.restoreGeometry(Settings.value('help-window')) #pos_x, pos_y, width, height = Settings.value('help-window') else: pos_x, pos_y, width, height = 0, 0, 640, 640 self.setGeometry(pos_x, pos_y, width, height) self.window().setWindowTitle(title) self.show()
def restoreSettings(self): settings = QSettings(version.organisation, version.appname) settings.beginGroup("Preferences") if settings.contains("compression"): value = settings.value("compression", None) self.compression = value if settings.contains("compression_opts"): value = settings.value("compression_opts", None) if isinstance(value, basestring): self.compression_opts = eval(value) else: self.compression_opts = value if settings.contains("max_sv_fraction"): value = settings.value("max_sv_fraction", type=float) self.max_sv_fraction = value if settings.contains("interactive_item_limit"): value = settings.value("interactive_item_limit", 5000, type=int) self.interactive_item_limit = value if settings.contains("default_sorter"): value = settings.value("default_sorter", type=str) self.default_sorter = value if settings.contains("default_feature_group"): value = settings.value("default_feature_group") self.default_feature_group = value if settings.contains("contours_complementary_color"): value = settings.value("contours_complementary_color", type=bool) self.contours_complementary_color = value if settings.contains("save_raw_images"): value = settings.value("save_raw_images", type=bool) self.save_raw_images = value settings.endGroup()
def __init__(self, parent = None, width = 5, height = 4, dpi = 100): fig = Figure(figsize = (width, height), dpi = dpi) self.axes = fig.add_subplot(111) self.axes.hold(False) super().__init__(fig) self.setParent(parent) super().setSizePolicy(QSizePolicy.Expanding, QSizePolicy.Expanding) super().updateGeometry() self.base = 0 settings = QSettings(QSettings.UserScope, 'Georgia Tech', 'RamanGui', self) if settings.contains('ele'): self.ele = float(settings.value('ele')) else: settings.setValue('ele', 20) self.ele = 20
def generate_png(test, ref, output_dir=None): output_f = test.name + '.png' if output_dir: if not exists(output_dir): os.makedirs(output_dir) output_f = join(output_dir, output_f) plt.plot(ref.times(), ref.values(), color='#00FF21', label='ref', linestyle='solid', linewidth=2.5) plt.plot(test.times(), test.values(), color='#FF1D00', label='test', linestyle='dashed', linewidth=1.5) plt.title(test.name) plt.ylabel('value') plt.xlabel('seconds') # one plt.legend(ncol=1, loc=1) # get the min and max values in the Y axis ymin, ymax = plt.ylim() # set the y axis to be drawn 30% more than the default plt.ylim(ymax=ymax*1.3) # for some weird reason we must call savefig before show, otherwise the output file is all white # 240 for very high quality. 110 acceptable. 70 is fast but ugly mySettings = QSettings(QSettings.IniFormat, QSettings.UserScope, 'Sogeti', 'validate') # image quality value is 110 by default, unless the user set it to something else image_q = 110 if mySettings.contains('report/imageQuality'): image_q = int(mySettings.value('report/imageQuality')) plt.savefig(output_f, dpi=image_q, bbox_inches='tight') # use clf instead of close, otherwise pyplot will crash in windows the second time! # clearing somehow is necessary for pdf files with more than one chart plt.clf() if exists(output_f): return abspath(output_f) else: return None
class MainWindow(QMainWindow, ui_window.Ui_Window): emulator_found = QtCore.pyqtSignal(dict) emulators_loaded = QtCore.pyqtSignal() def __init__(self): super(MainWindow, self).__init__() self.setupUi(self) self.emulators = { } self.settings = QSettings('SanderTheDragon', 'Qtendo') self.ui_create() self.ui_connect() self.settings_load() def showEvent(self, ev): QMainWindow.showEvent(self, ev) self.statusBar.showMsg('Searching for emulators', 1000) Thread(target=self.find_emulators, daemon=True).start() def closeEvent(self, ev): QMainWindow.closeEvent(self, ev) self.settings_save() def ui_create(self): #Add toolbar self.toolBar = QToolBar() self.toolBar.addAction(self.actionPageEmulation) self.toolBar.setFloatable(False) self.toolBar.setMovable(False) self.toolBar.setToolButtonStyle(Qt.ToolButtonTextBesideIcon) self.gridLayout.addWidget(self.toolBar, 1, 0) #Add a second toolbar on emulation page self.toolBarEmulation = QToolBar() self.toolBarEmulation.setFloatable(False) self.toolBarEmulation.setMovable(False) self.toolBarEmulation.setToolButtonStyle(Qt.ToolButtonTextBesideIcon) self.pageEmulationLayout.addWidget(self.toolBarEmulation, 0, 0) #Add progress bar to status bar self.taskProgress = QProgressBar() self.taskProgress.setVal = lambda x: ( self.taskProgress.setVisible(True), self.taskProgress.setValue(x) ) self.taskProgress.setVal(0) self.taskProgress.setTextVisible(False) self.statusBar.addPermanentWidget(self.taskProgress) #Also print messages to terminal self.statusBar.showMsg = lambda msg, timeout: ( logging.info(msg), self.statusBar.showMessage(msg, timeout) ) #Styling self.setStyleSheet('QToolButton { padding-right: -3px; }') def ui_connect(self): #Menu actions self.actionQuit.triggered.connect(QCoreApplication.quit) self.actionSettings.triggered.connect(lambda: settings.SettingsDialog(parent=self).exec_()) self.actionAbout.triggered.connect(lambda: about.AboutDialog(parent=self).exec_()) #Toolbar actions self.actionPageEmulation.triggered.connect(lambda: self.stackedWidget.setCurrentIndex(0)) #Other signals self.emulator_found.connect(self.add_emulator) self.emulators_loaded.connect(self.reset_status) def settings_load(self): if self.settings.value('qtendo/window/restore', True, type=bool): self.restoreGeometry(self.settings.value('qtendo/window/geometry', type=QByteArray)) def settings_save(self): if self.settings.value('qtendo/window/restore', True, type=bool): self.settings.setValue('qtendo/window/geometry', self.saveGeometry()) def change_emulator(self, index): current = self.stackedWidgetEmulation.currentIndex() if current != index: emulator = self.emulators[list(self.emulators.keys())[current]] emulator['action'].setIcon(QIcon(emulator['action'].icon().pixmap(QSize(24, 24), QIcon.Disabled))) self.stackedWidgetEmulation.setCurrentIndex(index) emulator = self.emulators[list(self.emulators.keys())[index]] emulator['action'].setIcon(QIcon(':' + emulator['icon'])) def add_emulator(self, emulator): if len(emulator['path']) > 0: self.statusBar.showMsg('Found ' + emulator['name'], 1000) else: self.statusBar.showMsg('Failed to find ' + emulator['name'], 1000) self.emulators[emulator['name']] = emulator i = self.stackedWidgetEmulation.count() emulator['action'] = QAction() emulator['action'].setIcon(QIcon(':' + emulator['icon'])) if i > 0: self.toolBarEmulation.addSeparator() emulator['action'].setIcon(QIcon(emulator['action'].icon().pixmap(QSize(24, 24), QIcon.Disabled))) emulator['action'].setIconText(emulator['name']) emulator['action'].triggered.connect(lambda checked, index=i: self.change_emulator(index)) self.toolBarEmulation.addAction(emulator['action']) self.stackedWidgetEmulation.insertWidget(i, emulator['widget'](emulator)) if len(self.settings.value('emulation/emulator/' + emulator['name'].lower().replace(' ', '_') + '/path', emulator['path'], type=str)) == 0: self.toolBarEmulation.widgetForAction(emulator['action']).setStyleSheet('color: ' + QApplication.palette().color(QPalette.Disabled, QPalette.WindowText).name() + ';') emulator['reload_settings'] = self.reload_settings self.taskProgress.setVal(int((100.0 / float(emulator_count)) * float(i + 1))) def reset_status(self): self.statusBar.clearMessage() self.taskProgress.setValue(0) self.taskProgress.setVisible(False) def reload_settings(self): emulator = self.emulators[list(self.emulators.keys())[self.stackedWidgetEmulation.currentIndex()]] if len(self.settings.value('emulation/emulator/' + emulator['name'].lower().replace(' ', '_') + '/path', emulator['path'], type=str)) == 0: self.toolBarEmulation.widgetForAction(emulator['action']).setStyleSheet('color: ' + QApplication.palette().color(QPalette.Disabled, QPalette.WindowText).name() + ';') else: self.toolBarEmulation.widgetForAction(emulator['action']).setStyleSheet('') def find_emulators(self): #Search for FCEUX self.emulator_found.emit(fceux.find(None if not self.settings.contains('emulation/emulator/fceux/path') else self.settings.value('emulation/emulator/fceux/path', type=str))) #Search for ZSNES self.emulator_found.emit(zsnes.find(None if not self.settings.contains('emulation/emulator/zsnes/path') else self.settings.value('emulation/emulator/zsnes/path', type=str))) #Search for Mupen64Plus self.emulator_found.emit(mupen64plus.find(None if not self.settings.contains('emulation/emulator/mupen64plus/path') else self.settings.value('emulation/emulator/mupen64plus/path', type=str))) #Search for Dolphin Emulator self.emulator_found.emit(dolphin.find(None if not self.settings.contains('emulation/emulator/dolphin/path') else self.settings.value('emulation/emulator/dolphin/path', type=str))) #Search for Citra self.emulator_found.emit(citra.find(None if not self.settings.contains('emulation/emulator/citra/path') else self.settings.value('emulation/emulator/citra/path', type=str))) self.emulators_loaded.emit()
def prepare(tests=False): app = QApplication(sys.argv) app.setOrganizationName("manuskript"+("_tests" if tests else "")) app.setOrganizationDomain("www.theologeek.ch") app.setApplicationName("manuskript"+("_tests" if tests else "")) app.setApplicationVersion(getVersion()) print("Running manuskript version {}.".format(getVersion())) icon = QIcon() for i in [16, 32, 64, 128, 256, 512]: icon.addFile(appPath("icons/Manuskript/icon-{}px.png".format(i))) qApp.setWindowIcon(icon) app.setStyle("Fusion") # Load style from QSettings settings = QSettings(app.organizationName(), app.applicationName()) if settings.contains("applicationStyle"): style = settings.value("applicationStyle") app.setStyle(style) # Translation process locale = QLocale.system().name() appTranslator = QTranslator(app) # By default: locale def extractLocale(filename): # len("manuskript_") = 13, len(".qm") = 3 return filename[11:-3] if len(filename) >= 16 else "" def tryLoadTranslation(translation, source): if appTranslator.load(appPath(os.path.join("i18n", translation))): app.installTranslator(appTranslator) print(app.tr("Loaded translation from {}: {}.").format(source, translation)) return True else: print(app.tr("Note: No translator found or loaded from {} for locale {}."). format(source, extractLocale(translation))) return False # Load translation from settings translation = "" if settings.contains("applicationTranslation"): translation = settings.value("applicationTranslation") print("Found translation in settings:", translation) if (translation != "" and not tryLoadTranslation(translation, "settings")) or translation == "": # load from settings failed or not set, fallback translation = "manuskript_{}.qm".format(locale) tryLoadTranslation(translation, "system locale") QIcon.setThemeSearchPaths(QIcon.themeSearchPaths() + [appPath("icons")]) QIcon.setThemeName("NumixMsk") # Font siue if settings.contains("appFontSize"): f = qApp.font() f.setPointSize(settings.value("appFontSize", type=int)) app.setFont(f) # Main window from manuskript.mainWindow import MainWindow MW = MainWindow() # We store the system default cursor flash time to be able to restore it # later if necessary MW._defaultCursorFlashTime = qApp.cursorFlashTime() # Command line project if len(sys.argv) > 1 and sys.argv[1][-4:] == ".msk": if os.path.exists(sys.argv[1]): path = os.path.abspath(sys.argv[1]) MW._autoLoadProject = path return app, MW
class SimulationGui(QMainWindow): """ class for the graphical user interface """ # TODO enable closing plot docks by right-clicking their name runSimulation = pyqtSignal() stopSimulation = pyqtSignal() playbackTimeChanged = pyqtSignal() regimeFinished = pyqtSignal() finishedRegimeBatch = pyqtSignal(bool) def __init__(self): # constructor of the base class QMainWindow.__init__(self) QCoreApplication.setOrganizationName("RST") QCoreApplication.setOrganizationDomain("https://tu-dresden.de/rst") QCoreApplication.setApplicationVersion( pkg_resources.require("PyMoskito")[0].version) QCoreApplication.setApplicationName(globals()["__package__"]) # load settings self._settings = QSettings() self._read_settings() # initialize logger self._logger = logging.getLogger(self.__class__.__name__) # Create Simulation Backend self.guiProgress = None self.cmdProgress = None self.sim = SimulatorInteractor(self) self.runSimulation.connect(self.sim.run_simulation) self.stopSimulation.connect(self.sim.stop_simulation) self.sim.simulation_finalized.connect(self.new_simulation_data) self.currentDataset = None self.interpolator = None # sim setup viewer self.targetView = SimulatorView(self) self.targetView.setModel(self.sim.target_model) self.targetView.expanded.connect(self.target_view_changed) self.targetView.collapsed.connect(self.target_view_changed) # sim results viewer self.result_view = QTreeView() # the docking area allows to rearrange the user interface at runtime self.area = pg.dockarea.DockArea() # Window properties icon_size = QSize(25, 25) self.setCentralWidget(self.area) self.resize(1000, 700) self.setWindowTitle("PyMoskito") res_path = get_resource("mosquito.png") icon = QIcon(res_path) self.setWindowIcon(icon) # create docks self.propertyDock = pg.dockarea.Dock("Properties") self.animationDock = pg.dockarea.Dock("Animation") self.regimeDock = pg.dockarea.Dock("Regimes") self.dataDock = pg.dockarea.Dock("Data") self.logDock = pg.dockarea.Dock("Log") self.plotDockPlaceholder = pg.dockarea.Dock("Placeholder") # arrange docks self.area.addDock(self.animationDock, "right") self.area.addDock(self.regimeDock, "left", self.animationDock) self.area.addDock(self.propertyDock, "bottom", self.regimeDock) self.area.addDock(self.dataDock, "bottom", self.propertyDock) self.area.addDock(self.plotDockPlaceholder, "bottom", self.animationDock) self.area.addDock(self.logDock, "bottom", self.dataDock) self.non_plotting_docks = list(self.area.findAll()[1].keys()) # add widgets to the docks self.propertyDock.addWidget(self.targetView) if not vtk_available: self._logger.error("loading vtk failed with:{}".format(vtk_error_msg)) # check if there is a registered visualizer available_vis = get_registered_visualizers() self._logger.info("found visualizers: {}".format( [name for cls, name in available_vis])) if available_vis: # instantiate the first visualizer self._logger.info("loading visualizer '{}'".format(available_vis[0][1])) self.animationLayout = QVBoxLayout() if issubclass(available_vis[0][0], MplVisualizer): self.animationWidget = QWidget() self.visualizer = available_vis[0][0](self.animationWidget, self.animationLayout) self.animationDock.addWidget(self.animationWidget) elif issubclass(available_vis[0][0], VtkVisualizer): if vtk_available: # vtk window self.animationFrame = QFrame() self.vtkWidget = QVTKRenderWindowInteractor( self.animationFrame) self.animationLayout.addWidget(self.vtkWidget) self.animationFrame.setLayout(self.animationLayout) self.animationDock.addWidget(self.animationFrame) self.vtk_renderer = vtkRenderer() self.vtkWidget.GetRenderWindow().AddRenderer( self.vtk_renderer) self.visualizer = available_vis[0][0](self.vtk_renderer) self.vtkWidget.Initialize() else: self._logger.warning("visualizer depends on vtk which is " "not available on this system!") elif available_vis: raise NotImplementedError else: self.visualizer = None # regime window self.regime_list = QListWidget(self) self.regime_list.setSelectionMode(QAbstractItemView.ExtendedSelection) self.regimeDock.addWidget(self.regime_list) self.regime_list.itemDoubleClicked.connect(self.regime_dclicked) self._regimes = [] self.regime_file_name = "" self.actDeleteRegimes = QAction(self.regime_list) self.actDeleteRegimes.setText("&Delete Selected Regimes") # TODO shortcut works always, not only with focus on the regime list # self.actDeleteRegimes.setShortcutContext(Qt.WindowShortcut) self.actDeleteRegimes.setShortcut(QKeySequence(Qt.Key_Delete)) self.actDeleteRegimes.triggered.connect(self.remove_regime_items) self.actSave = QAction(self) self.actSave.setText('Save Results As') self.actSave.setIcon(QIcon(get_resource("save.png"))) self.actSave.setDisabled(True) self.actSave.setShortcut(QKeySequence.Save) self.actSave.triggered.connect(self.export_simulation_data) self.actLoadRegimes = QAction(self) self.actLoadRegimes.setText("Load Regimes from File") self.actLoadRegimes.setIcon(QIcon(get_resource("load.png"))) self.actLoadRegimes.setDisabled(False) self.actLoadRegimes.setShortcut(QKeySequence.Open) self.actLoadRegimes.triggered.connect(self.load_regime_dialog) self.actExitOnBatchCompletion = QAction(self) self.actExitOnBatchCompletion.setText("&Exit On Batch Completion") self.actExitOnBatchCompletion.setCheckable(True) self.actExitOnBatchCompletion.setChecked( self._settings.value("control/exit_on_batch_completion") == "True" ) self.actExitOnBatchCompletion.changed.connect( self.update_exit_on_batch_completion_setting) # regime management self.runningBatch = False self._current_regime_index = None self._current_regime_name = None self._regimes = [] self.regimeFinished.connect(self.run_next_regime) self.finishedRegimeBatch.connect(self.regime_batch_finished) # data window self.dataList = QListWidget(self) self.dataDock.addWidget(self.dataList) self.dataList.itemDoubleClicked.connect(self.create_plot) # actions for simulation control self.actSimulateCurrent = QAction(self) self.actSimulateCurrent.setText("&Simulate Current Regime") self.actSimulateCurrent.setIcon(QIcon(get_resource("simulate.png"))) self.actSimulateCurrent.setShortcut(QKeySequence("F5")) self.actSimulateCurrent.triggered.connect(self.start_simulation) self.actSimulateAll = QAction(self) self.actSimulateAll.setText("Simulate &All Regimes") self.actSimulateAll.setIcon(QIcon(get_resource("execute_regimes.png"))) self.actSimulateAll.setShortcut(QKeySequence("F6")) self.actSimulateAll.setDisabled(True) self.actSimulateAll.triggered.connect(self.start_regime_execution) # actions for animation control self.actAutoPlay = QAction(self) self.actAutoPlay.setText("&Autoplay Simulation") self.actAutoPlay.setCheckable(True) self.actAutoPlay.setChecked( self._settings.value("control/autoplay_animation") == "True" ) self.actAutoPlay.changed.connect(self.update_autoplay_setting) self.actPlayPause = QAction(self) self.actPlayPause.setText("Play Animation") self.actPlayPause.setIcon(QIcon(get_resource("play.png"))) self.actPlayPause.setDisabled(True) self.actPlayPause.setShortcut(QKeySequence(Qt.Key_Space)) self.actPlayPause.triggered.connect(self.play_animation) self.actStop = QAction(self) self.actStop.setText("Stop") self.actStop.setIcon(QIcon(get_resource("stop.png"))) self.actStop.setDisabled(True) self.actStop.triggered.connect(self.stop_animation) self.actSlow = QAction(self) self.actSlow.setText("Slowest") self.actSlow.setIcon(QIcon(get_resource("slow.png"))) self.actSlow.setDisabled(False) self.actSlow.triggered.connect(self.set_slowest_playback_speed) self.actFast = QAction(self) self.actFast.setText("Fastest") self.actFast.setIcon(QIcon(get_resource("fast.png"))) self.actFast.setDisabled(False) self.actFast.triggered.connect(self.set_fastest_playback_speed) self.speedControl = QSlider(Qt.Horizontal, self) self.speedControl.setMaximumSize(200, 25) self.speedControl.setTickPosition(QSlider.TicksBothSides) self.speedControl.setDisabled(False) self.speedControl.setMinimum(0) self.speedControl.setMaximum(12) self.speedControl.setValue(6) self.speedControl.setTickInterval(6) self.speedControl.setSingleStep(2) self.speedControl.setPageStep(3) self.speedControl.valueChanged.connect(self.update_playback_speed) self.timeSlider = QSlider(Qt.Horizontal, self) self.timeSlider.setMinimum(0) self.timeSliderRange = 1000 self.timeSlider.setMaximum(self.timeSliderRange) self.timeSlider.setTickInterval(1) self.timeSlider.setTracking(True) self.timeSlider.setDisabled(True) self.timeSlider.valueChanged.connect(self.update_playback_time) self.playbackTime = .0 self.playbackGain = 1 self.currentStepSize = .0 self.currentEndTime = .0 self.playbackTimer = QTimer() self.playbackTimer.timeout.connect(self.increment_playback_time) self.playbackTimeChanged.connect(self.update_gui) self.playbackTimeout = 33 # in [ms] -> 30 fps self.actResetCamera = QAction(self) self.actResetCamera.setText("Reset Camera") self.actResetCamera.setIcon(QIcon(get_resource("reset_camera.png"))) self.actResetCamera.setDisabled(True) if available_vis: self.actResetCamera.setEnabled(self.visualizer.can_reset_view) self.actResetCamera.triggered.connect(self.reset_camera_clicked) # postprocessing self.actPostprocessing = QAction(self) self.actPostprocessing.setText("Launch Postprocessor") self.actPostprocessing.setIcon(QIcon(get_resource("processing.png"))) self.actPostprocessing.setDisabled(False) self.actPostprocessing.triggered.connect(self.postprocessing_clicked) self.actPostprocessing.setShortcut(QKeySequence("F7")) self.postprocessor = None # toolbar self.toolbarSim = QToolBar("Simulation") self.toolbarSim.setContextMenuPolicy(Qt.PreventContextMenu) self.toolbarSim.setMovable(False) self.toolbarSim.setIconSize(icon_size) self.addToolBar(self.toolbarSim) self.toolbarSim.addAction(self.actLoadRegimes) self.toolbarSim.addAction(self.actSave) self.toolbarSim.addSeparator() self.toolbarSim.addAction(self.actSimulateCurrent) self.toolbarSim.addAction(self.actSimulateAll) self.toolbarSim.addSeparator() self.toolbarSim.addAction(self.actPlayPause) self.toolbarSim.addAction(self.actStop) self.toolbarSim.addWidget(self.timeSlider) self.toolbarSim.addSeparator() self.toolbarSim.addAction(self.actSlow) self.toolbarSim.addWidget(self.speedControl) self.toolbarSim.addAction(self.actFast) self.toolbarSim.addSeparator() self.toolbarSim.addAction(self.actPostprocessing) self.toolbarSim.addAction(self.actResetCamera) self.postprocessor = None # log dock self.logBox = QPlainTextEdit(self) self.logBox.setReadOnly(True) self.logDock.addWidget(self.logBox) # init logger for logging box self.textLogger = PlainTextLogger(logging.INFO) self.textLogger.set_target_cb(self.logBox.appendPlainText) logging.getLogger().addHandler(self.textLogger) # menu bar fileMenu = self.menuBar().addMenu("&File") fileMenu.addAction(self.actLoadRegimes) fileMenu.addAction(self.actSave) fileMenu.addAction("&Quit", self.close) editMenu = self.menuBar().addMenu("&Edit") editMenu.addAction(self.actDeleteRegimes) simMenu = self.menuBar().addMenu("&Simulation") simMenu.addAction(self.actSimulateCurrent) simMenu.addAction(self.actSimulateAll) simMenu.addAction(self.actExitOnBatchCompletion) simMenu.addAction(self.actPostprocessing) animMenu = self.menuBar().addMenu("&Animation") animMenu.addAction(self.actPlayPause) animMenu.addAction("&Increase Playback Speed", self.increment_playback_speed, QKeySequence(Qt.CTRL + Qt.Key_Plus)) animMenu.addAction("&Decrease Playback Speed", self.decrement_playback_speed, QKeySequence(Qt.CTRL + Qt.Key_Minus)) animMenu.addAction("&Reset Playback Speed", self.reset_playback_speed, QKeySequence(Qt.CTRL + Qt.Key_0)) animMenu.addAction(self.actAutoPlay) animMenu.addAction(self.actResetCamera) helpMenu = self.menuBar().addMenu("&Help") helpMenu.addAction("&Online Documentation", self.show_online_docs) helpMenu.addAction("&About", self.show_info) # status bar self.status = QStatusBar(self) self.setStatusBar(self.status) self.statusLabel = QLabel("Ready.") self.statusBar().addPermanentWidget(self.statusLabel) self.timeLabel = QLabel("current time: 0.0") self.statusBar().addPermanentWidget(self.timeLabel) self._logger.info("Simulation GUI is up and running.") def _read_settings(self): # add default settings if none are present if not self._settings.contains("path/simulation_results"): self._settings.setValue("path/simulation_results", os.path.join(os.path.curdir, "results", "simulation")) if not self._settings.contains("path/postprocessing_results"): self._settings.setValue("path/postprocessing_results", os.path.join(os.path.curdir, "results", "postprocessing")) if not self._settings.contains("path/metaprocessing_results"): self._settings.setValue("path/metaprocessing_results", os.path.join(os.path.curdir, "results", "metaprocessing")) if not self._settings.contains("control/autoplay_animation"): self._settings.setValue("control/autoplay_animation", "False") if not self._settings.contains("control/exit_on_batch_completion"): self._settings.setValue("control/exit_on_batch_completion", "False") def _write_settings(self): """ Store the application state. """ pass @pyqtSlot() def update_autoplay_setting(self): self._settings.setValue("control/autoplay_animation", str(self.actAutoPlay.isChecked())) @pyqtSlot() def update_exit_on_batch_completion_setting(self, state=None): if state is None: state = self.actExitOnBatchCompletion.isChecked() self._settings.setValue("control/exit_on_batch_completion", str(state)) def set_visualizer(self, vis): self.visualizer = vis self.vtkWidget.Initialize() @pyqtSlot() def play_animation(self): """ play the animation """ self._logger.debug("Starting Playback") # if we are at the end, start from the beginning if self.playbackTime == self.currentEndTime: self.timeSlider.setValue(0) self.actPlayPause.setText("Pause Animation") self.actPlayPause.setIcon(QIcon(get_resource("pause.png"))) self.actPlayPause.triggered.disconnect(self.play_animation) self.actPlayPause.triggered.connect(self.pause_animation) self.playbackTimer.start(self.playbackTimeout) @pyqtSlot() def pause_animation(self): """ pause the animation """ self._logger.debug("Pausing Playback") self.playbackTimer.stop() self.actPlayPause.setText("Play Animation") self.actPlayPause.setIcon(QIcon(get_resource("play.png"))) self.actPlayPause.triggered.disconnect(self.pause_animation) self.actPlayPause.triggered.connect(self.play_animation) def stop_animation(self): """ Stop the animation if it is running and reset the playback time. """ self._logger.debug("Stopping Playback") if self.actPlayPause.text() == "Pause Animation": # animation is playing -> stop it self.playbackTimer.stop() self.actPlayPause.setText("Play Animation") self.actPlayPause.setIcon(QIcon(get_resource("play.png"))) self.actPlayPause.triggered.disconnect(self.pause_animation) self.actPlayPause.triggered.connect(self.play_animation) self.timeSlider.setValue(0) @pyqtSlot() def start_simulation(self): """ start the simulation and disable start button """ if self._current_regime_index is None: regime_name = "" else: regime_name = str(self.regime_list.item( self._current_regime_index).text()) self.statusLabel.setText("simulating {}".format(regime_name)) self._logger.info("Simulating: {}".format(regime_name)) self.actSimulateCurrent.setIcon(QIcon( get_resource("stop_simulation.png"))) self.actSimulateCurrent.setText("Abort &Simulation") self.actSimulateCurrent.triggered.disconnect(self.start_simulation) self.actSimulateCurrent.triggered.connect(self.stop_simulation) if not self.runningBatch: self.actSimulateAll.setDisabled(True) self.guiProgress = QProgressBar(self) self.sim.simulationProgressChanged.connect(self.guiProgress.setValue) self.statusBar().addWidget(self.guiProgress) self.runSimulation.emit() @pyqtSlot() def stop_simulation(self): self.stopSimulation.emit() def export_simulation_data(self, ok): """ Query the user for a custom name and export the current simulation results. :param ok: unused parameter from QAction.triggered() Signal """ self._save_data() def _save_data(self, file_path=None): """ Save the current simulation results. If *fie_name* is given, the result will be saved to the specified location, making automated exporting easier. Args: file_path(str): Absolute path of the target file. If `None` the use will be asked for a storage location. """ regime_name = self._regimes[self._current_regime_index]["Name"] if file_path is None: # get default path path = self._settings.value("path/simulation_results") # create canonic file name suggestion = self._simfile_name(regime_name) else: path = os.path.dirname(file_path) suggestion = os.path.basename(file_path) # check if path exists otherwise create it if not os.path.isdir(path): box = QMessageBox() box.setText("Export Folder does not exist yet.") box.setInformativeText("Do you want to create it? \n" "{}".format(os.path.abspath(path))) box.setStandardButtons(QMessageBox.Ok | QMessageBox.No) box.setDefaultButton(QMessageBox.Ok) ret = box.exec_() if ret == QMessageBox.Ok: os.makedirs(path) else: path = os.path.abspath(os.path.curdir) file_path = None # If no path was given, present the default and let the user choose if file_path is None: dialog = QFileDialog(self) dialog.setAcceptMode(QFileDialog.AcceptSave) dialog.setFileMode(QFileDialog.AnyFile) dialog.setDirectory(path) dialog.setNameFilter("PyMoskito Results (*.pmr)") dialog.selectFile(suggestion) if dialog.exec_(): file_path = dialog.selectedFiles()[0] else: self._logger.warning("Export Aborted") return -1 # ask whether this should act as new default path = os.path.abspath(os.path.dirname(file_path)) if path != self._settings.value("path/simulation_results"): box = QMessageBox() box.setText("Use this path as new default?") box.setInformativeText("{}".format(path)) box.setStandardButtons(QMessageBox.Yes | QMessageBox.No) box.setDefaultButton(QMessageBox.Yes) ret = box.exec_() if ret == QMessageBox.Yes: self._settings.setValue("path/simulation_results", path) self.currentDataset.update({"regime name": regime_name}) with open(file_path, "wb") as f: pickle.dump(self.currentDataset, f, protocol=4) self.statusLabel.setText("results saved to {}".format(file_path)) self._logger.info("results saved to {}".format(file_path)) def _simfile_name(self, regime_name): """ Create a canonical name for a simulation result file """ suggestion = (time.strftime("%Y%m%d-%H%M%S") + "_" + regime_name + ".pmr") return suggestion def load_regime_dialog(self): regime_path = os.path.join(os.curdir) dialog = QFileDialog(self) dialog.setFileMode(QFileDialog.ExistingFile) dialog.setDirectory(regime_path) dialog.setNameFilter("Simulation Regime files (*.sreg)") if dialog.exec_(): file = dialog.selectedFiles()[0] self.load_regimes_from_file(file) def load_regimes_from_file(self, file_name): """ load simulation regime from file :param file_name: """ self.regime_file_name = os.path.split(file_name)[-1][:-5] self._logger.info("loading regime file: {0}".format(self.regime_file_name)) with open(file_name.encode(), "r") as f: self._regimes += yaml.load(f) self._update_regime_list() if self._regimes: self.actSimulateAll.setDisabled(False) self._logger.info("loaded {} regimes".format(len(self._regimes))) self.statusBar().showMessage("loaded {} regimes.".format(len(self._regimes)), 1000) return def _update_regime_list(self): self.regime_list.clear() for reg in self._regimes: self._logger.debug("adding '{}' to regime list".format(reg["Name"])) self.regime_list.addItem(reg["Name"]) def remove_regime_items(self): if self.regime_list.currentRow() >= 0: # flag all selected files as invalid items = self.regime_list.selectedItems() for item in items: del self._regimes[self.regime_list.row(item)] self.regime_list.takeItem(self.regime_list.row(item)) @pyqtSlot(QListWidgetItem) def regime_dclicked(self, item): """ Apply the selected regime to the current target. """ self.apply_regime_by_name(str(item.text())) def apply_regime_by_name(self, regime_name): """ Apply the regime given by `regime_name` und update the regime index. Returns: bool: `True` if successful, `False` if errors occurred. """ # get regime idx try: idx = list(map(itemgetter("Name"), self._regimes)).index(regime_name) except ValueError as e: self._logger.error("apply_regime_by_name(): Error no regime called " "'{0}'".format(regime_name)) return False # apply return self._apply_regime_by_idx(idx) def _apply_regime_by_idx(self, index=0): """ Apply the given regime. Args: index(int): Index of the regime in the `RegimeList` . Returns: bool: `True` if successful, `False` if errors occurred. """ if index >= len(self._regimes): self._logger.error("applyRegime: index error! ({})".format(index)) return False reg_name = self._regimes[index]["Name"] self.statusBar().showMessage("regime {} applied.".format(reg_name), 1000) self._logger.info("applying regime '{}'".format(reg_name)) self._current_regime_index = index self._current_regime_name = reg_name return self.sim.set_regime(self._regimes[index]) @pyqtSlot() def start_regime_execution(self): """ Simulate all regimes in the regime list. """ self.actSimulateAll.setText("Stop Simulating &All Regimes") self.actSimulateAll.setIcon(QIcon(get_resource("stop_batch.png"))) self.actSimulateAll.triggered.disconnect(self.start_regime_execution) self.actSimulateAll.triggered.connect(self.stop_regime_excecution) self.runningBatch = True self._current_regime_index = -1 self.regimeFinished.emit() def run_next_regime(self): """ Execute the next regime in the regime batch. """ # are we finished? if self._current_regime_index == len(self._regimes) - 1: self.finishedRegimeBatch.emit(True) return suc = self._apply_regime_by_idx(self._current_regime_index + 1) if not suc: self.finishedRegimeBatch.emit(False) return self.start_simulation() @pyqtSlot() def stop_regime_excecution(self): """ Stop the batch process. """ self.stopSimulation.emit() self.finishedRegimeBatch.emit(False) def regime_batch_finished(self, status): self.runningBatch = False self.actSimulateAll.setDisabled(False) self.actSave.setDisabled(True) self.actSimulateAll.setText("Simulate &All Regimes") self.actSimulateAll.setIcon(QIcon(get_resource("execute_regimes.png"))) self.actSimulateAll.triggered.disconnect(self.stop_regime_excecution) self.actSimulateAll.triggered.connect(self.start_regime_execution) if status: self.statusLabel.setText("All regimes have been simulated") self._logger.info("All Regimes have been simulated") else: self._logger.error("Batch simulation has been aborted") if self._settings.value("control/exit_on_batch_completion") == "True": self._logger.info("Shutting down SimulationGUI") self.close() @pyqtSlot(str, dict, name="new_simulation_data") def new_simulation_data(self, status, data): """ Slot to be called when the simulation interface has completed the current job and new data is available. Args: status (str): Status of the simulation, either - `finished` : Simulation has been finished successfully or - `failed` : Simulation has failed. data (dict): Dictionary, holding the simulation data. """ self._logger.info("Simulation {}".format(status)) self.statusLabel.setText("Simulation {}".format(status)) self.actSimulateCurrent.setText("&Simulate Current Regime") self.actSimulateCurrent.setIcon(QIcon(get_resource("simulate.png"))) self.actSimulateCurrent.triggered.disconnect(self.stop_simulation) self.actSimulateCurrent.triggered.connect(self.start_simulation) self.actPlayPause.setDisabled(False) self.actStop.setDisabled(False) self.actSave.setDisabled(False) self.speedControl.setDisabled(False) self.timeSlider.setDisabled(False) self.sim.simulationProgressChanged.disconnect(self.guiProgress.setValue) self.statusBar().removeWidget(self.guiProgress) self.stop_animation() self.currentDataset = data if data: self._read_results() self._update_data_list() self._update_plots() if self._settings.value("control/autoplay_animation") == "True": self.actPlayPause.trigger() if self.runningBatch: regime_name = self._regimes[self._current_regime_index]["Name"] file_name = self._simfile_name(regime_name) self._save_data(os.path.join( self._settings.value("path/simulation_results"), file_name)) self.regimeFinished.emit() else: self.actSimulateAll.setDisabled(False) def _read_results(self): state = self.currentDataset["results"]["Solver"] self.interpolator = interp1d(self.currentDataset["results"]["time"], state, axis=0, bounds_error=False, fill_value=(state[0], state[-1])) self.currentStepSize = 1.0/self.currentDataset["simulation"][ "measure rate"] self.currentEndTime = self.currentDataset["simulation"]["end time"] self.validData = True def increment_playback_speed(self): self.speedControl.setValue(self.speedControl.value() + self.speedControl.singleStep()) def decrement_playback_speed(self): self.speedControl.setValue(self.speedControl.value() - self.speedControl.singleStep()) def reset_playback_speed(self): self.speedControl.setValue((self.speedControl.maximum() - self.speedControl.minimum())/2) def set_slowest_playback_speed(self): self.speedControl.setValue(self.speedControl.minimum()) def set_fastest_playback_speed(self): self.speedControl.setValue(self.speedControl.maximum()) def update_playback_speed(self, val): """ adjust playback time to slider value :param val: """ maximum = self.speedControl.maximum() self.playbackGain = 10**(3.0 * (val - maximum / 2) / maximum) @pyqtSlot() def increment_playback_time(self): """ go one time step forward in playback """ if self.playbackTime == self.currentEndTime: self.pause_animation() return increment = self.playbackGain * self.playbackTimeout / 1000 self.playbackTime = min(self.currentEndTime, self.playbackTime + increment) pos = int(self.playbackTime / self.currentEndTime * self.timeSliderRange) self.timeSlider.blockSignals(True) self.timeSlider.setValue(pos) self.timeSlider.blockSignals(False) self.playbackTimeChanged.emit() def update_playback_time(self): """ adjust playback time to slider value """ self.playbackTime = self.timeSlider.value()/self.timeSliderRange*self.currentEndTime self.playbackTimeChanged.emit() return def update_gui(self): """ updates the graphical user interface, including: - timestamp - visualisation - time cursor in diagrams """ if not self.validData: return self.timeLabel.setText("current time: %4f" % self.playbackTime) # update time cursor in plots self._update_time_cursors() # update state of rendering if self.visualizer: state = self.interpolator(self.playbackTime) self.visualizer.update_scene(state) if isinstance(self.visualizer, MplVisualizer): pass elif isinstance(self.visualizer, VtkVisualizer): self.vtkWidget.GetRenderWindow().Render() def _update_data_list(self): self.dataList.clear() for module_name, results in self.currentDataset["results"].items(): if not isinstance(results, np.ndarray): continue if len(results.shape) == 1: self.dataList.insertItem(0, module_name) elif len(results.shape) == 2: for col in range(results.shape[1]): self.dataList.insertItem( 0, self._build_entry_name(module_name, (col, )) ) elif len(results.shape) == 3: for col in range(results.shape[1]): for der in range(results.shape[2]): self.dataList.insertItem( 0, self._build_entry_name(module_name, (col, der)) ) def _build_entry_name(self, module_name, idx): """ Construct an identifier for a given entry of a module. Args: module_name (str): name of the module the entry belongs to. idx (tuple): Index of the entry. Returns: str: Identifier to use for display. """ # save the user from defining 1d entries via tuples if len(idx) == 1: m_idx = idx[0] else: m_idx = idx mod_settings = self.currentDataset["modules"] info = mod_settings.get(module_name, {}).get("output_info", None) if info: if m_idx in info: return ".".join([module_name, info[m_idx]["Name"]]) return ".".join([module_name] + [str(i) for i in idx]) def _get_index_from_suffix(self, module_name, suffix): info = self.currentDataset["modules"].get(module_name, {}).get( "output_info", None) idx = next((i for i in info if info[i]["Name"] == suffix), None) return idx def _get_units(self, entry): """ Return the unit that corresponds to a given entry. If no information is available, None is returned. Args: entry (str): Name of the entry. This can either be "Model.a.b" where a and b are numbers or if information is available "Model.Signal" where signal is the name of that part. Returns: """ args = entry.split(".") module_name = args.pop(0) info = self.currentDataset["modules"].get(module_name, {}).get( "output_info", None) if info is None: return None if len(args) == 1: try: idx = int(args[0]) except ValueError: idx = next((i for i in info if info[i]["Name"] == args[0]), None) else: idx = (int(a) for a in args) return info[idx]["Unit"] def create_plot(self, item): """ Creates a plot widget based on the given item. If a plot for this item is already open no new plot is created but the existing one is raised up again. Args: item(Qt.ListItem): Item to plot. """ title = str(item.text()) if title in self.non_plotting_docks: self._logger.error("Title '{}' not allowed for a plot window since" "it would shadow on of the reserved " "names".format(title)) # check if plot has already been opened if title in self.area.findAll()[1]: self.area.docks[title].raiseDock() return # collect data data = self._get_data_by_name(title) t = self.currentDataset["results"]["time"] unit = self._get_units(title) if "." in title: name = title.split(".")[1] else: name = title # create plot widget widget = pg.PlotWidget(title=title) widget.showGrid(True, True) widget.plot(x=t, y=data) widget.getPlotItem().getAxis("bottom").setLabel(text="Time", units="s") widget.getPlotItem().getAxis("left").setLabel(text=name, units=unit) # add a time line time_line = pg.InfiniteLine(self.playbackTime, angle=90, movable=False, pen=pg.mkPen("#FF0000", width=2.0)) widget.getPlotItem().addItem(time_line) # create dock container and add it to dock area dock = pg.dockarea.Dock(title, closable=True) dock.addWidget(widget) self.area.addDock(dock, "above", self.plotDockPlaceholder) def _get_data_by_name(self, name): tmp = name.split(".") module_name = tmp[0] if len(tmp) == 1: data = np.array(self.currentDataset["results"][module_name]) elif len(tmp) == 2: try: idx = int(tmp[1]) except ValueError: idx = self._get_index_from_suffix(module_name, tmp[1]) finally: data = self.currentDataset["results"][module_name][..., idx] elif len(tmp) == 3: idx = int(tmp[1]) der = int(tmp[2]) data = self.currentDataset["results"][module_name][..., idx, der] else: raise ValueError("Format not supported") return data def _update_time_cursors(self): """ Update the time lines of all plot windows """ for title, dock in self.area.findAll()[1].items(): if title in self.non_plotting_docks: continue for widget in dock.widgets: for item in widget.getPlotItem().items: if isinstance(item, pg.InfiniteLine): item.setValue(self.playbackTime) def _update_plots(self): """ Update the data in all plot windows """ for title, dock in self.area.findAll()[1].items(): if title in self.non_plotting_docks: continue if not self.dataList.findItems(dock.name(), Qt.MatchExactly): # no data for this plot -> remove it dock.close() continue for widget in dock.widgets: for item in widget.getPlotItem().items: if isinstance(item, pg.PlotDataItem): x_data = self.currentDataset["results"]["time"] y_data = self._get_data_by_name(dock.name()) item.setData(x=x_data, y=y_data) @pyqtSlot(QModelIndex) def target_view_changed(self, index): self.targetView.resizeColumnToContents(0) def postprocessing_clicked(self): """ starts the post- and metaprocessing application """ self._logger.info("launching postprocessor") self.statusBar().showMessage("launching postprocessor", 1000) if self.postprocessor is None: self.postprocessor = PostProcessor() self.postprocessor.show() def reset_camera_clicked(self): """ reset camera in vtk window """ self.visualizer.reset_camera() self.vtkWidget.GetRenderWindow().Render() def show_info(self): icon_lic = open(get_resource("license.txt"), "r").read() text = "This application was build using PyMoskito ver. {} .<br />" \ "PyMoskito is free software distributed under GPLv3. <br />" \ "It is developed by members of the " \ "<a href=\'https://tu-dresden.de/ing/elektrotechnik/rst'>" \ "Institute of Control Theory</a>" \ " at the <a href=\'https://tu-dresden.de'>" \ "Dresden University of Technology</a>. <br />" \ "".format(pkg_resources.require("PyMoskito")[0].version) \ + "<br />" + icon_lic box = QMessageBox.about(self, "PyMoskito", text) def show_online_docs(self): webbrowser.open("https://pymoskito.readthedocs.org") def closeEvent(self, QCloseEvent): self._logger.info("Close Event received, shutting down.") logging.getLogger().removeHandler(self.textLogger) super().closeEvent(QCloseEvent)
def __init__(self, mainWindow): QWidget.__init__(self) self.setupUi(self) self.mw = mainWindow # UI for l in [self.lblTitleGeneral, self.lblTitleGeneral_2, self.lblTitleViews, self.lblTitleLabels, self.lblTitleStatus, self.lblTitleFullscreen, ]: l.setStyleSheet(S.titleLabelSS()) icons = [QIcon.fromTheme("configure"), QIcon.fromTheme("history-view"), QIcon.fromTheme("gnome-settings"), themeIcon("label"), themeIcon("status"), QIcon.fromTheme("preferences-desktop-theme") ] for i in range(self.lstMenu.count()): item = self.lstMenu.item(i) item.setSizeHint(QSize(item.sizeHint().width(), 42)) item.setTextAlignment(Qt.AlignCenter) if icons[i]: item.setIcon(icons[i]) self.lstMenu.setMaximumWidth(140) self.lstMenu.setMinimumWidth(140) # General self.cmbStyle.addItems(list(QStyleFactory.keys())) self.cmbStyle.setCurrentIndex( [i.lower() for i in list(QStyleFactory.keys())] .index(qApp.style().objectName())) self.cmbStyle.currentIndexChanged[str].connect(self.setStyle) self.cmbTranslation.clear() tr = OrderedDict() tr["English"] = "" tr["Arabic (Saudi Arabia)"] = "manuskript_ar_SA.qm" tr["Deutsch"] = "manuskript_de.qm" tr["Español"] = "manuskript_es.qm" tr["Français"] = "manuskript_fr.qm" tr["Hungarian"] = "manuskript_hu.qm" tr["Indonesian"] = "manuskript_id.qm" tr["Italian"] = "manuskript_it.qm" tr["Norwegian Bokmål"] = "manuskript_nb_NO.qm" tr["Dutch"] = "manuskript_nl.qm" tr["Polish"] = "manuskript_pl.qm" tr["Portuguese (Brazil)"] = "manuskript_pt_BR.qm" tr["Portuguese (Portugal)"] = "manuskript_pt_PT.qm" tr["Russian"] = "manuskript_ru.qm" tr["Svenska"] = "manuskript_sv.qm" tr["Ukranian"] = "manuskript_uk.qm" tr["Chinese (Simplified)"] = "manuskript_zh_CN.qm" self.translations = tr for name in tr: self.cmbTranslation.addItem(name, tr[name]) sttgs = QSettings(qApp.organizationName(), qApp.applicationName()) if (sttgs.contains("applicationTranslation") and sttgs.value("applicationTranslation") in tr.values()): # Sets the correct translation self.cmbTranslation.setCurrentText( [i for i in tr if tr[i] == sttgs.value("applicationTranslation")][0]) self.cmbTranslation.currentIndexChanged.connect(self.setTranslation) f = qApp.font() self.spnGeneralFontSize.setValue(f.pointSize()) self.spnGeneralFontSize.valueChanged.connect(self.setAppFontSize) self.txtAutoSave.setValidator(QIntValidator(0, 999, self)) self.txtAutoSaveNoChanges.setValidator(QIntValidator(0, 999, self)) self.chkAutoSave.setChecked(settings.autoSave) self.chkAutoSaveNoChanges.setChecked(settings.autoSaveNoChanges) self.txtAutoSave.setText(str(settings.autoSaveDelay)) self.txtAutoSaveNoChanges.setText(str(settings.autoSaveNoChangesDelay)) self.chkSaveOnQuit.setChecked(settings.saveOnQuit) self.chkSaveToZip.setChecked(settings.saveToZip) self.chkAutoSave.stateChanged.connect(self.saveSettingsChanged) self.chkAutoSaveNoChanges.stateChanged.connect(self.saveSettingsChanged) self.chkSaveOnQuit.stateChanged.connect(self.saveSettingsChanged) self.chkSaveToZip.stateChanged.connect(self.saveSettingsChanged) self.txtAutoSave.textEdited.connect(self.saveSettingsChanged) self.txtAutoSaveNoChanges.textEdited.connect(self.saveSettingsChanged) autoLoad, last = self.mw.welcome.getAutoLoadValues() self.chkAutoLoad.setChecked(autoLoad) self.chkAutoLoad.stateChanged.connect(self.saveSettingsChanged) # Revisions opt = settings.revisions self.chkRevisionsKeep.setChecked(opt["keep"]) self.chkRevisionsKeep.stateChanged.connect(self.revisionsSettingsChanged) self.chkRevisionRemove.setChecked(opt["smartremove"]) self.chkRevisionRemove.toggled.connect(self.revisionsSettingsChanged) self.spnRevisions10Mn.setValue(60 / opt["rules"][10 * 60]) self.spnRevisions10Mn.valueChanged.connect(self.revisionsSettingsChanged) self.spnRevisionsHour.setValue(60 * 10 / opt["rules"][60 * 60]) self.spnRevisionsHour.valueChanged.connect(self.revisionsSettingsChanged) self.spnRevisionsDay.setValue(60 * 60 / opt["rules"][60 * 60 * 24]) self.spnRevisionsDay.valueChanged.connect(self.revisionsSettingsChanged) self.spnRevisionsMonth.setValue(60 * 60 * 24 / opt["rules"][60 * 60 * 24 * 30]) self.spnRevisionsMonth.valueChanged.connect(self.revisionsSettingsChanged) self.spnRevisionsEternity.setValue(60 * 60 * 24 * 7 / opt["rules"][None]) self.spnRevisionsEternity.valueChanged.connect(self.revisionsSettingsChanged) # Views self.tabViews.setCurrentIndex(0) lst = ["Nothing", "POV", "Label", "Progress", "Compile"] for cmb in self.viewSettingsDatas(): item, part = self.viewSettingsDatas()[cmb] cmb.setCurrentIndex(lst.index(settings.viewSettings[item][part])) cmb.currentIndexChanged.connect(self.viewSettingsChanged) for chk in self.outlineColumnsData(): col = self.outlineColumnsData()[chk] chk.setChecked(col in settings.outlineViewColumns) chk.stateChanged.connect(self.outlineColumnsChanged) self.chkOutlinePOV.setVisible(settings.viewMode != "simple") # Hides checkbox if non-fiction view mode for item, what, value in [ (self.rdoTreeItemCount, "InfoFolder", "Count"), (self.rdoTreeWC, "InfoFolder", "WC"), (self.rdoTreeProgress, "InfoFolder", "Progress"), (self.rdoTreeSummary, "InfoFolder", "Summary"), (self.rdoTreeNothing, "InfoFolder", "Nothing"), (self.rdoTreeTextWC, "InfoText", "WC"), (self.rdoTreeTextProgress, "InfoText", "Progress"), (self.rdoTreeTextSummary, "InfoText", "Summary"), (self.rdoTreeTextNothing, "InfoText", "Nothing"), ]: item.setChecked(settings.viewSettings["Tree"][what] == value) item.toggled.connect(self.treeViewSettignsChanged) self.sldTreeIconSize.valueChanged.connect(self.treeViewSettignsChanged) self.sldTreeIconSize.valueChanged.connect( lambda v: self.lblTreeIconSize.setText("{}x{}".format(v, v))) self.sldTreeIconSize.setValue(settings.viewSettings["Tree"]["iconSize"]) self.rdoCorkOldStyle.setChecked(settings.corkStyle == "old") self.rdoCorkNewStyle.setChecked(settings.corkStyle == "new") self.rdoCorkNewStyle.toggled.connect(self.setCorkStyle) self.rdoCorkOldStyle.toggled.connect(self.setCorkStyle) self.populatesCmbBackgrounds(self.cmbCorkImage) self.setCorkImageDefault() self.updateCorkColor() self.cmbCorkImage.currentIndexChanged.connect(self.setCorkBackground) self.btnCorkColor.clicked.connect(self.setCorkColor) # Text editor opt = settings.textEditor # Font self.setButtonColor(self.btnEditorFontColor, opt["fontColor"]) self.btnEditorFontColor.clicked.connect(self.choseEditorFontColor) self.setButtonColor(self.btnEditorMisspelledColor, opt["misspelled"]) self.btnEditorMisspelledColor.clicked.connect(self.choseEditorMisspelledColor) self.setButtonColor(self.btnEditorBackgroundColor, opt["background"]) self.btnEditorBackgroundColor.clicked.connect(self.choseEditorBackgroundColor) self.chkEditorBackgroundTransparent.setChecked(opt["backgroundTransparent"]) self.chkEditorBackgroundTransparent.stateChanged.connect(self.updateEditorSettings) self.btnEditorColorDefault.clicked.connect(self.restoreEditorColors) f = QFont() f.fromString(opt["font"]) self.cmbEditorFontFamily.setCurrentFont(f) self.cmbEditorFontFamily.currentFontChanged.connect(self.updateEditorSettings) self.spnEditorFontSize.setValue(f.pointSize()) self.spnEditorFontSize.valueChanged.connect(self.updateEditorSettings) # Cursor self.chkEditorCursorWidth.setChecked(opt["cursorWidth"] != 1) self.chkEditorCursorWidth.stateChanged.connect(self.updateEditorSettings) self.spnEditorCursorWidth.setValue(opt["cursorWidth"] if opt["cursorWidth"] != 1 else 9) self.spnEditorCursorWidth.valueChanged.connect(self.updateEditorSettings) self.spnEditorCursorWidth.setEnabled(opt["cursorWidth"] != 1) self.chkEditorNoBlinking.setChecked(opt["cursorNotBlinking"]) self.chkEditorNoBlinking.stateChanged.connect(self.setApplicationCursorBlinking) self.chkEditorTypeWriterMode.setChecked(opt["alwaysCenter"]) self.chkEditorTypeWriterMode.stateChanged.connect(self.updateEditorSettings) self.cmbEditorFocusMode.setCurrentIndex( 0 if not opt["focusMode"] else 1 if opt["focusMode"] == "sentence" else 2 if opt["focusMode"] == "line" else 3) self.cmbEditorFocusMode.currentIndexChanged.connect(self.updateEditorSettings) # Text areas self.chkEditorMaxWidth.setChecked(opt["maxWidth"] != 0) self.chkEditorMaxWidth.stateChanged.connect(self.updateEditorSettings) self.spnEditorMaxWidth.setEnabled(opt["maxWidth"] != 0) self.spnEditorMaxWidth.setValue(500 if opt["maxWidth"] == 0 else opt["maxWidth"]) self.spnEditorMaxWidth.valueChanged.connect(self.updateEditorSettings) self.spnEditorMarginsLR.setValue(opt["marginsLR"]) self.spnEditorMarginsLR.valueChanged.connect(self.updateEditorSettings) self.spnEditorMarginsTB.setValue(opt["marginsTB"]) self.spnEditorMarginsTB.valueChanged.connect(self.updateEditorSettings) # Paragraphs self.cmbEditorAlignment.setCurrentIndex(opt["textAlignment"]) self.cmbEditorAlignment.currentIndexChanged.connect(self.updateEditorSettings) self.cmbEditorLineSpacing.setCurrentIndex( 0 if opt["lineSpacing"] == 100 else 1 if opt["lineSpacing"] == 150 else 2 if opt["lineSpacing"] == 200 else 3) self.cmbEditorLineSpacing.currentIndexChanged.connect(self.updateEditorSettings) self.spnEditorLineSpacing.setValue(opt["lineSpacing"]) self.spnEditorLineSpacing.valueChanged.connect(self.updateEditorSettings) self.spnEditorLineSpacing.setEnabled(opt["lineSpacing"] not in [100, 150, 200]) self.spnEditorLineSpacing.valueChanged.connect(self.updateEditorSettings) self.spnEditorTabWidth.setValue(opt["tabWidth"]) self.spnEditorTabWidth.valueChanged.connect(self.updateEditorSettings) self.chkEditorIndent.setChecked(opt["indent"]) self.chkEditorIndent.stateChanged.connect(self.updateEditorSettings) self.spnEditorParaAbove.setValue(opt["spacingAbove"]) self.spnEditorParaAbove.valueChanged.connect(self.updateEditorSettings) self.spnEditorParaBelow.setValue(opt["spacingBelow"]) self.spnEditorParaBelow.valueChanged.connect(self.updateEditorSettings) self.timerUpdateWidgets = QTimer() self.timerUpdateWidgets.setSingleShot(True) self.timerUpdateWidgets.setInterval(250) self.timerUpdateWidgets.timeout.connect(self.updateAllWidgets) # Labels self.lstLabels.setModel(self.mw.mdlLabels) self.lstLabels.setRowHidden(0, True) self.lstLabels.clicked.connect(self.updateLabelColor) self.btnLabelAdd.clicked.connect(self.addLabel) self.btnLabelRemove.clicked.connect(self.removeLabel) self.btnLabelColor.clicked.connect(self.setLabelColor) # Statuses self.lstStatus.setModel(self.mw.mdlStatus) self.lstStatus.setRowHidden(0, True) self.btnStatusAdd.clicked.connect(self.addStatus) self.btnStatusRemove.clicked.connect(self.removeStatus) # Fullscreen self._editingTheme = None self.btnThemeEditOK.setIcon(qApp.style().standardIcon(QStyle.SP_DialogApplyButton)) self.btnThemeEditOK.clicked.connect(self.saveTheme) self.btnThemeEditCancel.setIcon(qApp.style().standardIcon(QStyle.SP_DialogCancelButton)) self.btnThemeEditCancel.clicked.connect(self.cancelEdit) self.cmbThemeEdit.currentIndexChanged.connect(self.themeEditStack.setCurrentIndex) self.cmbThemeEdit.setCurrentIndex(0) self.cmbThemeEdit.currentIndexChanged.emit(0) self.themeStack.setCurrentIndex(0) self.lstThemes.currentItemChanged.connect(self.themeSelected) self.populatesThemesList() self.btnThemeAdd.clicked.connect(self.newTheme) self.btnThemeEdit.clicked.connect(self.editTheme) self.btnThemeRemove.clicked.connect(self.removeTheme) self.timerUpdateFSPreview = QTimer() self.timerUpdateFSPreview.setSingleShot(True) self.timerUpdateFSPreview.setInterval(250) self.timerUpdateFSPreview.timeout.connect(self.updatePreview)
def restoreSettings(self): settings = QSettings(version.organisation, version.appname) settings.beginGroup('Preferences') if settings.contains('compression'): value = settings.value('compression', None) self.compression = value if settings.contains('compression_opts'): value = settings.value('compression_opts', None) if isinstance(value, basestring): self.compression_opts = eval(value) else: self.compression_opts = value if settings.contains('max_sv_fraction'): value = settings.value('max_sv_fraction', type=float) self.max_sv_fraction = value if settings.contains('batch_size'): value = settings.value('batch_size', type=str) self.batch_size = value if settings.contains('default_sorter'): value = settings.value('default_sorter', type=str) self.default_sorter = value if settings.contains('default_feature_group'): value = settings.value('default_feature_group') self.default_feature_group = value if settings.contains('contours_complementary_color'): value = settings.value('contours_complementary_color', type=bool) self.contours_complementary_color = value if settings.contains('save_raw_images'): value = settings.value('save_raw_images', type=bool) self.save_raw_images = value if settings.contains('only_classifier_features'): value = settings.value('only_classifier_features', type=bool) self.only_classifier_features = value if settings.contains('features'): value = settings.value('features') self.features = value if settings.contains('enable_plugins'): value = settings.value('enable_plugins', type=bool) self.enable_plugins = value settings.endGroup()
def initUI(self): #---------------------------------------------------- # # Main Window # work_zone = QWidget(self) Layout = QHBoxLayout(work_zone) self.setCentralWidget(work_zone) openAction = QAction(QIcon( os.path.join(resources_path, 'open24.png') ), 'Open', self) openAction.setShortcut('Ctrl+O') openAction.setStatusTip('Open Schematic File') openAction.triggered.connect(self.open_file) saveAction = QAction(QIcon( os.path.join(resources_path, 'save24.png') ), 'Save', self) saveAction.setShortcut('Ctrl+S') saveAction.setStatusTip('Save Schematic File') saveAction.triggered.connect(self.save_file) saveAsAction = QAction(QIcon( os.path.join(resources_path, 'save-as24.png') ), 'Save As...', self) saveAsAction.setShortcut('Ctrl+Shift+S') saveAsAction.setStatusTip('Save Schematic File As...') saveAsAction.triggered.connect(self.save_file_as) exitAction = QAction(QIcon( os.path.join(resources_path, 'exit24.png') ), 'Exit', self) exitAction.setShortcut('Ctrl+Q') exitAction.setStatusTip('Exit application') exitAction.triggered.connect(self.close) settingsAction = QAction(QIcon( os.path.join(resources_path, 'settings24.png') ), 'Settings', self) settingsAction.setShortcut('Ctrl+Alt+S') settingsAction.setStatusTip('Edit settings') settingsAction.triggered.connect(self.edit_settings) helpAction = QAction(QIcon( os.path.join(resources_path, 'help_book24.png') ), 'User\'s Manual', self) helpAction.setShortcut('F1') helpAction.setStatusTip('User\'s Manual') helpAction.triggered.connect(self.show_user_manual_slot) helpSDAction = QAction(QIcon( os.path.join(resources_path, 'gear24.png') ), 'Settings Dialog', self) helpSDAction.setShortcut('Ctrl+F1') helpSDAction.setStatusTip('Settings Dialog Help') helpSDAction.triggered.connect(self.show_setting_dialog_help_slot) helpHKAction = QAction(QIcon( os.path.join(resources_path, 'rocket24.png') ), 'Hotkeys', self) helpHKAction.setShortcut('Shift+F1') helpHKAction.setStatusTip('Hotkeys Help') helpHKAction.triggered.connect(self.show_hotkeys_help_slot) self.statusBar().showMessage('Ready') #-------------------------------------------- # # Main Menu # menubar = self.menuBar() fileMenu = menubar.addMenu('&File') fileMenu.addAction(openAction) fileMenu.addAction(saveAction) fileMenu.addAction(saveAsAction) fileMenu.addAction(exitAction) #-------------------------------------------- # # Options Menu # optionsMenu = menubar.addMenu('&Options') optionsMenu.addAction(settingsAction) #-------------------------------------------- # # Help Menu # helpMenu = menubar.addMenu('&Help') helpMenu.addAction(helpAction) helpMenu.addAction(helpSDAction) helpMenu.addAction(helpHKAction) #-------------------------------------------- # # Toolbar # toolbar = self.addToolBar('Exit') toolbar.addAction(exitAction) toolbar.addAction(openAction) toolbar.addAction(saveAction) toolbar.addAction(saveAsAction) toolbar.addAction(settingsAction) toolbar.addAction(helpAction) #---------------------------------------------------- # # Settings Dialog # #---------------------------------------------------- # # Components Table # self.CmpTabBox = QGroupBox('Components', self) self.CmpTabLayout = QVBoxLayout(self.CmpTabBox) self.CmpTabLayout.setContentsMargins(4,10,4,4) self.CmpTabLayout.setSpacing(10) self.CmpTabLayout.setSizeConstraint(QVBoxLayout.SetMaximumSize) self.CmpTable = ComponentsTable(self) #self.CmpChooseButton = QPushButton('Choose', self) self.CmpTabLayout.addWidget(self.CmpTable) #self.CmpTabLayout.addWidget(self.CmpChooseButton) #---------------------------------------------------- # # Selector # self.SelectorBox = QGroupBox('Selector', self) self.SelectorLayout = QVBoxLayout(self.SelectorBox) self.SelectorLayout.setContentsMargins(4,10,4,4) self.SelectorLayout.setSpacing(2) self.SelectorBtnWidget = QWidget(self) self.SelectorBtnLayout = QHBoxLayout(self.SelectorBtnWidget) self.SelectorBtnLayout.setContentsMargins(4,10,4,4) self.SelectorBtnLayout.setSpacing(10) self.Selector = Selector(self) self.SelApplyButton = QPushButton('Apply', self) self.SelApplyButton.setToolTip('Alt+S: Apply selection patterns to components') self.SelClearButton = QPushButton('Clear', self) self.SelClearButton.setToolTip('Alt+C: Clear selection patterns') self.SelTemplateButton = QPushButton('Use Component', self) self.SelTemplateButton.setToolTip('Alt+T: Use Selected Component As Template') self.SelectorLayout.addWidget(self.Selector) self.SelectorBtnLayout.addWidget(self.SelTemplateButton) self.SelectorBtnLayout.addWidget(self.SelApplyButton) self.SelectorBtnLayout.addWidget(self.SelClearButton) self.SelectorLayout.addWidget(self.SelectorBtnWidget) self.shortcutSelApply = QShortcut(QKeySequence(Qt.ALT + Qt.Key_S), self) self.shortcutSelApply.activated.connect(self.Selector.apply_slot) self.shortcutSelClear = QShortcut(QKeySequence(Qt.ALT + Qt.Key_C), self) self.shortcutSelClear.activated.connect(self.Selector.clear_slot) self.shortcutSelTemplate = QShortcut(QKeySequence(Qt.ALT + Qt.Key_T), self) self.shortcutSelTemplate.activated.connect(self.Selector.use_comp_as_template_slot) #---------------------------------------------------- # # Inspector # self.Inspector = Inspector(self) self.FieldInspector = FieldInspector(self) self.InspectorBtnWidget = QWidget(self) self.InspectorBtnLayout = QHBoxLayout(self.InspectorBtnWidget) self.InspectorBtnLayout.setContentsMargins(4,10,4,4) self.InspectorBtnLayout.setSpacing(10) self.AddUserProperty = QPushButton('Add Property', self) self.AddUserProperty.setToolTip('Alt+A: Add new user property') self.DeleteUserProperty = QPushButton('Delete Property', self) self.DeleteUserProperty.setToolTip('Alt+Delete: Delete user property') self.RenameUserProperty = QPushButton('Rename Property', self) self.RenameUserProperty.setToolTip('Alt+R: Rename user property') self.InspectorBox = QGroupBox('Inspector', self) self.InspectorSplit = QSplitter(Qt.Vertical, self) self.InspectorLayout = QVBoxLayout(self.InspectorBox) self.InspectorLayout.setContentsMargins(4,10,4,4) self.InspectorLayout.setSpacing(2) self.InspectorSplit.addWidget(self.Inspector) self.InspectorSplit.addWidget(self.FieldInspector) self.InspectorLayout.addWidget(self.InspectorSplit) self.InspectorBtnLayout.addWidget(self.AddUserProperty) self.InspectorBtnLayout.addWidget(self.DeleteUserProperty) self.InspectorBtnLayout.addWidget(self.RenameUserProperty) self.InspectorLayout.addWidget(self.InspectorBtnWidget) self.shortcutSelApply = QShortcut(QKeySequence(Qt.ALT + Qt.Key_A), self) self.shortcutSelApply.activated.connect(self.add_user_property) self.shortcutSelApply = QShortcut(QKeySequence(Qt.ALT + Qt.Key_Delete), self) self.shortcutSelApply.activated.connect(self.remove_user_property) self.shortcutSelApply = QShortcut(QKeySequence(Qt.ALT + Qt.Key_R), self) self.shortcutSelApply.activated.connect(self.rename_user_property) #---------------------------------------------------- self.Splitter = QSplitter(self) self.Splitter.addWidget(self.CmpTabBox) self.Splitter.addWidget(self.SelectorBox) self.Splitter.addWidget(self.InspectorBox) self.centralWidget().layout().addWidget(self.Splitter) #---------------------------------------------------- # # Signals and Slots connections # self.CmpTable.cells_chosen.connect(self.Inspector.load_cmp) self.CmpTable.cells_chosen.connect(self.Selector.comp_template_slot) self.CmpTable.file_load.connect(self.file_loaded_slot) self.CmpTable.cmps_updated.connect(self.Selector.process_comps_slot) self.CmpTable.cmps_selected.connect(self.set_status_text_slot) self.SelApplyButton.clicked.connect(self.Selector.apply_slot) self.SelClearButton.clicked.connect(self.Selector.clear_slot) self.SelTemplateButton.clicked.connect(self.Selector.use_comp_as_template_slot) self.Selector.select_comps_signal.connect(self.CmpTable.select_comps_slot) self.Inspector.load_field.connect(self.FieldInspector.load_field_slot) self.Inspector.update_comps.connect(self.data_changed_slot) self.Inspector.update_comps.connect(self.CmpTable.update_cmp_list_slot) self.FieldInspector.data_changed.connect(self.data_changed_slot) CmpMgr.file_saved.connect(self.file_saved_slot) self.CmpTable.mouse_click.connect(self.mouse_change_tool) self.Inspector.mouse_click.connect(self.mouse_change_tool) self.FieldInspector.mouse_click.connect(self.mouse_change_tool) self.Inspector.header().sectionResized.connect(self.FieldInspector.column_resize) self.AddUserProperty.clicked.connect(self.add_user_property) self.DeleteUserProperty.clicked.connect(self.remove_user_property) self.RenameUserProperty.clicked.connect(self.rename_user_property) #---------------------------------------------------- self.ToolList = [] self.ToolList.append(self.CmpTable) self.ToolList.append(self.Selector) self.ToolList.append(self.Inspector) self.ToolList.append(self.FieldInspector) self.ToolIndex = 0 #---------------------------------------------------- # # Window # self.setWindowTitle(self.PROGRAM_NAME) Settings = QSettings('kicad-tools', 'Schematic Component Manager') #print(Settings.allKeys()) if Settings.contains('geometry'): self.restoreGeometry( Settings.value('geometry') ) else: self.setGeometry(100, 100, 1024, 768) if Settings.contains('cmptable'): w0, w1 = Settings.value('cmptable') self.CmpTable.setColumnWidth( 0, int(w0) ) self.CmpTable.setColumnWidth( 1, int(w1) ) if Settings.contains('selector'): w0, w1 = Settings.value('selector') self.Selector.setColumnWidth( 0, int(w0) ) self.Selector.setColumnWidth( 1, int(w1) ) if Settings.contains('inspector'): w0, w1 = Settings.value('inspector') self.Inspector.setColumnWidth( 0, int(w0) ) self.Inspector.setColumnWidth( 1, int(w1) ) self.FieldInspector.setColumnWidth( 0, int(w0) ) self.FieldInspector.setColumnWidth( 1, int(w1) ) #self.Inspector.setColumnWidth( 2, int(w2) ) if Settings.contains('splitter'): self.Splitter.restoreState( Settings.value('splitter') ) if Settings.contains('inssplitter'): self.InspectorSplit.restoreState( Settings.value('inssplitter') ) #---------------------------------------------------- # # Process command line arguments # if len(sys.argv) > 1: fname = sys.argv[1] if os.path.exists(fname): self.CmpTable.load_file(fname) else: print('E: input file "' + fname + '"does not exist') self.show()
class Preferences(QObject): prefsChanged = pyqtSignal() def __init__(self): QObject.__init__(self) self.reset() self._settings = QSettings() def _load_values(self, settings, get): pass def get_rect(self, name, default=None): r = self.get_value(name, default) if r is not None: return QRect(*r) else: return None def get_value(self, name, default=None): if self._settings.contains(name): result = adjust_after_deserialization(self._settings.value(name)) if result is not None: return result else: # If result is None, but still present in self._settings, it usually means a value # like "@Invalid". return default else: return default def load(self): self.reset() self._load_values(self._settings) def reset(self): pass def _save_values(self, settings, set_): pass def save(self): self._save_values(self._settings) self._settings.sync() def set_rect(self, name, r): if isinstance(r, QRect): rectAsList = [r.x(), r.y(), r.width(), r.height()] self.set_value(name, rectAsList) def set_value(self, name, value): self._settings.setValue(name, normalize_for_serialization(value)) def saveGeometry(self, name, widget): # We save geometry under a 5-sized int array: first item is a flag for whether the widget # is maximized and the other 4 are (x, y, w, h). m = 1 if widget.isMaximized() else 0 r = widget.geometry() rectAsList = [r.x(), r.y(), r.width(), r.height()] self.set_value(name, [m] + rectAsList) def restoreGeometry(self, name, widget): l = self.get_value(name) if l and len(l) == 5: m, x, y, w, h = l if m: widget.setWindowState(Qt.WindowMaximized) else: r = QRect(x, y, w, h) widget.setGeometry(r)