import inspect import os from qtpy.QtCore import QFile, QFileInfo, QIODevice, QSettings, Qt from qtpy.QtGui import QFont, QIcon from qtpy.QtWidgets import (QAction, QFileDialog, QGroupBox, QHBoxLayout, QLabel, QLineEdit, QMenuBar, QPushButton, QVBoxLayout) from pyqtacc.bdbase.enumkind import MsgSeverity _version = "1.0.0" _pymodule = os.path.basename(__file__) _appname, _appext = _pymodule.split(".") def _line(): """Macro to return the current line number. The current line number within the file is used when reporting messages to the message logging window. Returns: int: Current line number. """ return inspect.currentframe().f_back.f_lineno class HDF5File(QGroupBox): def __init__(self, parent): super(HDF5File, self).__init__(parent) self.parent = parent self.show_message = self.parent.show_log_message self.updateStatus = self.parent.updateStatus self.createAction = self.parent.create_action self.filename = None self.save_filename = None self.common_path = None self.recent_files = [] self.max_no_files = 9 self.show_common_path_flag = False self.file_dir = "." self.qsettings = QSettings() self.loadInitialFile() def show_common_path_only(self, yes=False): self.show_common_path_flag = yes def saveToFileProcedure(self): f = QFile(self.save_filename) if f.open(QIODevice.WriteOnly): f.write(self.fByteArray) f.close() return True else: return False def fileSave(self): if self.save_filename: if self.saveToFileProcedure(): self.updateStatus("Saved file {0}".format(self.save_filename)) self.show_message(MsgSeverity.INFO, _pymodule, _line(), "Saved file='{0}'".format(self.save_filename)) else: return False else: self.updateStatus( "Unable to save as no filename was given") self.show_message(MsgSeverity.WARN, _pymodule, _line(), "Unable to save as no filename was given") return False if self.save_filename: self.showSaveFile() def fileSaveAs(self): _dir = (os.path.dirname(self.save_filename) if self.save_filename is not None else self.file_dir) _fname = QFileDialog.getSaveFileName( self, "Save File", _dir, "HDF5 files (*.hdf *.h5 *.hdf5 *.he5)") if _fname == "('', '')": return False else: fname = _fname[0] if fname: if "." not in os.path.basename(fname): fname += ".h5" #self.addRecentSaveFile(fname) self.save_filename = fname self.fileSave() return True return False def showSaveFile(self): self.loaded_file_widget.setObjectName("hdf") self.style().unpolish(self.loaded_file_widget) self.style().polish(self.loaded_file_widget) self.loaded_file_widget.setText(self.save_filename) def fileOpen(self): _dir = os.path.dirname( self.filename) if self.filename is not None else self.file_dir fname = QFileDialog.getOpenFileName( self, "Select/Open File", str(_dir), ( "HDF5 files (*.hdf *.h5 *.hdf5 *.he5)"))[0] if fname: self.loadFile(fname) def loadInitialFile(self): self.recent_files = [] if self.qsettings.value("H5RecentFiles"): mylist = self.qsettings.value("H5RecentFiles") self.recent_files = str(mylist).split(',') if self.qsettings.value("H5LastLoadedFile"): fname = str(self.qsettings.value("H5LastLoadedFile")) if fname and QFile.exists(fname): #print ("loadInitialFile==============>", fname) self.filename = fname def loadFile(self, fname): if not fname: action = self.sender() if isinstance(action, QAction): fname = str(action.data()) if fname: self.filename = None if fname is None: message = "Failed to read file='{0}'".format(fname) self.show_message( MsgSeverity.WARN, _pymodule, _line(), message) self.updateStatus(message) return else: self.addRecentFile(fname) self.filename = fname self.parent.hdf_filename_loaded = fname _filename_wgt_str = fname #os.path.basename(fname) if self.show_common_path_flag: _start = str(fname).rfind(str(self.common_path)) #print("common path in loadFile ========>", self.common_path) if _start == 0: _filename_wgt_str = str(fname).replace(self.common_path, "") if _filename_wgt_str: if _filename_wgt_str.count("/") > 1: _filename_wgt_str = ".../" + _filename_wgt_str else: _filename_wgt_str = fname if self.loadFromFileProcedure(): message = "Loaded {0}".format(os.path.basename(fname)) message2 = "Loaded file='{0}'".format((fname)) self.show_message( MsgSeverity.INFO, _pymodule, _line(), message2) #self.loadFileProc() self.updateStatus(message) self.loaded_file_widget.setObjectName("load") self.style().unpolish(self.loaded_file_widget) self.style().polish(self.loaded_file_widget) self.loaded_file_widget.setText(_filename_wgt_str) else: message = "No input file given!" self.show_message( MsgSeverity.WARN, _pymodule, _line(), message) self.qsettings.setValue("H5LastLoadedFile", self.filename) recentFiles = ', '.join(self.recent_files) #recentFiles = (self.recentFiles) if self.recentFiles else None self.qsettings.setValue("H5RecentFiles", (recentFiles)) #print("loaded to qsettings", self.filename) def resetFileWidget(self, obj_name): self.loaded_file_widget.clear() self.loaded_file_widget.setObjectName(obj_name) self.style().unpolish(self.loaded_file_widget) self.style().polish(self.loaded_file_widget) def addRecentFile(self, fname): if fname is None: return if self.recent_files is None: self.recent_files.insert(0, fname) if fname not in self.recent_files: self.recent_files.insert(0, fname) while len(self.recent_files) > self.max_no_files: self.recent_files.pop((len(self.recent_files)-1)) #print(self.recent_files) def loadFromFileProcedure(self): f = QFile(self.filename) if f.open(QIODevice.ReadOnly): self.fByteArray = f.readAll() f.close() else: message = "Failed to load file='{0}'".format(self.filename) self.show_message( MsgSeverity.WARN, _pymodule, _line(), message) def updateFileMenu(self): self.file_menu.clear() self.file_menu.addAction(self.file_open_action) #self.parent.addActions(self._file_menu, self.fileMenuActions[:-1]) _current = str( self.filename) if self.filename is not None else None _recent_files = [_current] if _current is not None else [] if _current is not None: if self.recent_files: for fname in self.recent_files: if fname != _current and QFile.exists(fname): _recent_files.append(fname.strip()) if _recent_files: self.common_path = os.path.commonpath(_recent_files) + "/" else: self.common_path = None #print("_common_path=====>", self.common_path) if _recent_files: self.file_menu.addSeparator() for i, fname in enumerate(_recent_files): _label_icon = QFileInfo(fname).fileName() if self.common_path is not None: print(self.common_path) print(str(os.path.dirname(fname))) _start = str(os.path.dirname(fname)).rfind( str(self.common_path)) if _start == 0: _addon_str = str(os.path.dirname(fname)).replace( self.common_path, "") if _addon_str: _label_icon += " [..." + _addon_str + "/]" action = QAction(QIcon(":/icon.png"), "&{0} {1}".format(i + 1, _label_icon), self) action.setData(str(fname)) action.triggered.connect(self.loadFile) self.file_menu.addAction(action) self.recent_files = _recent_files class HDF5SaveLoad(HDF5File): def __init__(self, parent, title="HDF5", file_dir=".", obj_name="INNER"): super(HDF5SaveLoad, self).__init__(parent) self.parent = parent self.file_dir = file_dir self.setTitle(title) self.setObjectName(obj_name) _font16 = QFont("sans-serif") _font16.setPixelSize(16) self.loaded_file_widget = QLineEdit() self.loaded_file_widget.setObjectName("blank") self.loaded_file_widget.setProperty("readOnly", True) self.loaded_file_widget.setFixedHeight(35) self.loaded_file_widget.setAlignment(Qt.AlignRight) _menu_bar = QMenuBar() _menu_bar.setFont(_font16) _menu_bar.setFixedWidth(120) _menu_bar.setFixedHeight(38) _menu_bar.setObjectName("load") self.file_menu = _menu_bar.addMenu('Load Matrix') self.file_menu.setFont(_font16) self.file_open_action = self.createAction( "O&pen...", self.fileOpen, "Ctrl+Shift+P", "fileopen", "Load file") self.separator = QAction(self) self.separator.setSeparator(True) self.file_menu.addAction(self.file_open_action) _menu_save_bar = QMenuBar() _menu_save_bar.setFont(_font16) _menu_save_bar.setFixedWidth(120) _menu_save_bar.setFixedHeight(38) _menu_save_bar.setObjectName("hdf") self.save_menu = _menu_save_bar.addMenu('Save Matrix') self.save_menu.setFont(_font16) self.file_save_action = self.createAction( "O&pen...", self.fileSaveAs, "Ctrl+Shift+S", "filesaveas", "Save file") self.save_menu.addAction(self.file_save_action) _hb3 = QHBoxLayout() _hb3.setContentsMargins(5, 0, 5, 0) _hb3.setAlignment(Qt.AlignTop) _hb3.addWidget(self.loaded_file_widget) _hb = QHBoxLayout() _hb.addWidget(_menu_bar) _hb.addWidget(_menu_save_bar) _hb.setAlignment(Qt.AlignTop | Qt.AlignHCenter) _hb.setSpacing(15) _vb2 = QVBoxLayout() _vb2.setContentsMargins(5, 0, 0, 0) _vb2.setAlignment(Qt.AlignTop) _vb2.addLayout(_hb3) _vb2.addLayout(_hb) self.setLayout(_vb2) self.setFixedWidth(400) self.setFixedHeight(100) #or 156/120 self.setAlignment(Qt.AlignTop | Qt.AlignLeft) self.file_menu.aboutToShow.connect(self.updateFileMenu) self.updateFileMenu() class HDF5GroupBox(QGroupBox): def __init__(self, parent, title="HDF5", layout="Box"): super(HDF5GroupBox, self).__init__(parent) self.parent = parent self.show_message = self.parent.gui_frame.show_log_message self.updateStatus = self.parent.statusbar.showMessage self.createAction = self.parent.create_action self.filename = None self.common_path = None self.recent_files = [] self.max_no_files = 9 self.setTitle(title) self.qsettings = QSettings() _font16 = QFont("sans-serif") _font16.setPixelSize(16) _menu_bar = QMenuBar() _menu_bar.setFont(_font16) _menu_bar.setFixedWidth(50) _menu_bar.setFixedHeight(24) _loaded_file_label = QLabel(" Loaded:") _loaded_file_label.setFixedHeight(13) _loaded_file_label.setAlignment(Qt.AlignLeft | Qt.AlignTop) _loaded_file_label.setContentsMargins(0, 8, 0, 0) self.loaded_file_widget = QLineEdit() self.loaded_file_widget.setObjectName("hdf") self.loaded_file_widget.setProperty("readOnly", True) self.loaded_file_widget.setFixedHeight(35) self.analyze_h5_widget = QPushButton("Analyze") self.analyze_h5_widget.setObjectName("WriteData") self.analyze_h5_widget.setFixedWidth(100) self.analyze_h5_widget.setFixedHeight(34) self.analyze_h5_widget.setToolTip("Analyze pre-loaded hdf data") self.file_menu = _menu_bar.addMenu('File') self.file_menu.setFont(_font16) self.file_open_action = self.createAction( "O&pen...", self.fileOpen, "Ctrl+Shift+P", "fileopen", "Load file") self.separator = QAction(self) self.separator.setSeparator(True) self.file_menu.addAction(self.file_open_action) if layout == "Hor": self.setObjectName("OUTER") _hb = QHBoxLayout() _hb.setContentsMargins(10, 8, 10, 8) _hb.setAlignment(Qt.AlignTop) _hb.addWidget(_menu_bar) _hb.addWidget(self.loaded_file_widget) _hb.addWidget(self.analyze_h5_widget) _hb.setAlignment(Qt.AlignCenter) _hb.setSpacing(15) self.setAlignment(Qt.AlignCenter) self.setLayout(_hb) self.setFixedWidth(600) self.setFixedHeight(64) #or 156/120 else: self.setObjectName("OUTER") _vb3 = QVBoxLayout() _vb3.setContentsMargins(5, 0, 5, 0) _vb3.setAlignment(Qt.AlignTop) _loaded_file_label.setFixedHeight(30) _loaded_file_label.setContentsMargins(0, 18, 0, 0) _vb3.addWidget(_loaded_file_label) _vb3.addWidget(self.loaded_file_widget) _hb = QHBoxLayout() _hb.addWidget(_menu_bar) _hb.addWidget(self.analyze_h5_widget) _hb.setAlignment(Qt.AlignTop | Qt.AlignHCenter) _hb.setSpacing(15) _vb2 = QVBoxLayout() _vb2.setContentsMargins(5, 0, 0, 0) _vb2.setAlignment(Qt.AlignTop) _vb2.addLayout(_vb3) _vb2.addLayout(_hb) self.setLayout(_vb2) self.setFixedWidth(200) self.setFixedHeight(136) #or 156/120 self.setAlignment(Qt.AlignTop | Qt.AlignLeft) #self.recent_files_dict[fileOpenAction] = [] self.file_menu.aboutToShow.connect(self.updateFileMenu) self.loadInitialFile() self.updateFileMenu() def fileOpen(self): dir_name = os.path.dirname( self.filename) if self.filename is not None else "." fname = QFileDialog.getOpenFileName( self, "Select File", dir_name, ( "HDF5 files (*.hdf *.h5 *.hdf5 *.he5)"))[0] if fname: self.loadFile(fname) def loadInitialFile(self): if self.qsettings.value("H5GroupLastFile"): fname = str(self.qsettings.value("H5GroupLastFile")) if fname and QFile.exists(fname): #print ("loadInitialFile=============>", fname) self.loadFile(fname) def loadFile(self, fname): if not fname: action = self.sender() if isinstance(action, QAction): fname = str(action.data()) print("from self.sender:") print(fname) if fname: self.filename = None if fname is None: message = "Failed to read file='{0}'".format(fname) self.show_message( MsgSeverity.WARN, _pymodule, _line(), message) else: self.addRecentFile(fname) self.filename = fname message = "Loaded {0}".format(os.path.basename(fname)) message2 = "Loaded hdf file '{0}'".format((fname)) self.show_message( MsgSeverity.INFO, _pymodule, _line(), message2) #self.loadFileProc() #self.updateStatus(message) self.parent.hdf_filename_loaded = fname _filename_wgt_str = fname #os.path.basename(fname) _start = str(fname).rfind(str(self.common_path)) #print("common path in loadFile ============>", self.common_path) if _start == 0: _filename_wgt_str = str(fname).replace(self.common_path, "") if _filename_wgt_str: if _filename_wgt_str.count("/") > 1: _filename_wgt_str = ".../" + _filename_wgt_str else: _filename_wgt_str = fname self.loaded_file_widget.setText(_filename_wgt_str) else: message = "No input file given!" self.show_message( MsgSeverity.WARN, _pymodule, _line(), message) self.qsettings.setValue("H5GroupLastFile", self.filename) recentFiles = ', '.join(self.recent_files) #recentFiles = (self.recentFiles) if self.recentFiles else None self.qsettings.setValue("H5GroupRecentFiles", (recentFiles)) def addRecentFile(self, fname): if fname is None: return if self.recent_files is None: self.recent_files.insert(0, fname) if fname not in self.recent_files: self.recent_files.insert(0, fname) while len(self.recent_files) > self.max_no_files: self.recent_files.pop((len(self.recent_files)-1)) def loadFileProc(self): f = QFile(self.filename) if f.open(QIODevice.ReadOnly): self.fByteArray = f.readAll() f.close() else: message = "Failed to load file='{0}'".format(self.filename) self.show_message( MsgSeverity.WARN, _pymodule, _line(), message) def updateFileMenu(self): self.file_menu.clear() self.file_menu.addAction(self.file_open_action) #self.parent.addActions(self.file_menu, self.fileMenuActions[:-1]) _current = str(self.filename) if self.filename is not None else None _recent_files = [_current] if _current is not None else [] if _current is not None: if self.recent_files: for fname in self.recent_files: if fname != _current and QFile.exists(fname): _recent_files.append(fname) if _recent_files: self.common_path = os.path.commonpath(_recent_files) + "/" else: self.common_path = None if _recent_files: self.file_menu.addSeparator() for i, fname in enumerate(_recent_files): _label_icon = QFileInfo(fname).fileName() if self.common_path is not None: #print(self.common_path) #print(str(os.path.dirname(fname))) _start = str(os.path.dirname(fname)).rfind( str(self.common_path)) if _start == 0: _addon_str = str(os.path.dirname(fname)).replace( self.common_path, "") if _addon_str: _label_icon += " [..." + _addon_str + "/]" action = QAction(QIcon(":/icon.png"), "&{0} {1}".format(i + 1, _label_icon), self) action.setData(str(fname)) action.triggered.connect(self.loadFile) self.file_menu.addAction(action) self.recent_files = _recent_files