class ManageMembers(QMainWindow): def __init__(self, parent): super(ManageMembers, self).__init__(parent) self.setWindowTitle("Tagok kezelése") widget = QWidget() main_layout = QHBoxLayout() widget.setLayout(main_layout) self.setCentralWidget(widget) self.table_view = QTableView() main_layout.addWidget(self.table_view) self.model = QSqlTableModel(db=db) self.model.setTable("members") self.model.select() self.model.setEditStrategy(QSqlTableModel.OnManualSubmit) self.model.setHeaderData(1, Qt.Horizontal, "Vezetéknév") self.model.setHeaderData(2, Qt.Horizontal, "Utónév") self.model.setHeaderData(3, Qt.Horizontal, "Született") self.model.setHeaderData(4, Qt.Horizontal, "Ir.szám") self.model.setHeaderData(5, Qt.Horizontal, "Helység") self.model.setHeaderData(6, Qt.Horizontal, "Cím") self.model.setHeaderData(7, Qt.Horizontal, "Telefon") self.model.setHeaderData(8, Qt.Horizontal, "E-mail") self.model.setHeaderData(9, Qt.Horizontal, "Tagság kezdete") self.model.setHeaderData(10, Qt.Horizontal, "Aktív") # self.model.setFilter('vezeteknev Like "Czi%"') self.table_view.setModel(self.model) self.table_view.hideColumn(0) self.table_view.resizeColumnsToContents() # Ha ez engedélyezve, akkor a model-nél beállított sort nem működik, ez felülírja # Enélkül működik a model-es beállítás self.table_view.setSortingEnabled(True) # Ha engedélyezve van a fejléc szerinti rendezés, akkor UTÁNA meg lehet adni az alap sorrendet self.table_view.sortByColumn(1, Qt.AscendingOrder) self.model.dataChanged.connect(self.valtozott) gomb_layout = QVBoxLayout() main_layout.addLayout(gomb_layout) self.delete_button = QPushButton("&Tag törlése") self.add_button = QPushButton("&Új tag") self.apply_button = QPushButton("Módosítások alkalmazása") self.cancel_button = QPushButton("Módosítások elvetése") gomb_layout.addWidget(self.delete_button) gomb_layout.addWidget(self.add_button) gomb_layout.addWidget(self.apply_button) gomb_layout.addWidget(self.cancel_button) self.space = QSpacerItem(0, 0, QSizePolicy.Minimum, QSizePolicy.Expanding) gomb_layout.addItem(self.space) self.setFixedSize(1000, 800) tb = self.addToolBar("File") exit = QAction(QIcon("images/door--arrow.png"), "Kilépés", self) tb.addAction(exit) excel = QAction(QIcon("images/excel.png"), "Excel", self) tb.addAction(excel) tb.actionTriggered[QAction].connect(self.toolbarpressed) self.delete_button.clicked.connect(self.tag_torles) self.add_button.clicked.connect(self.tag_hozzadas) self.apply_button.clicked.connect(self.valtozas_mentese) self.cancel_button.clicked.connect(self.valtozas_elvetese) def tag_hozzadas(self): self.form_window = UjtagFormDialog() self.form_window.setWindowTitle("Új tag felvétele") if self.form_window.exec_(): record = self.model.record() record.remove(record.indexOf('id')) for i in range(len(self.form_window.mezo_ertekek)): record.setValue(i, self.form_window.mezo_ertekek[i].text()) # print(i, record.value(i)) if self.model.insertRecord(-1, record): self.model.submitAll() self.apply_button.setStyleSheet('') self.cancel_button.setStyleSheet('') else: db.rollback() def tag_torles(self): if len(self.table_view.selectedIndexes()) > 0: self.model.removeRow(self.table_view.selectedIndexes()[0].row()) self.model.submitAll() else: reply = QMessageBox.question(None, 'Hiba!', 'Törlés előtt jelöljön ki egy sort!', QMessageBox.Ok) def toolbarpressed(self, a): if a.text() == "Kilépés": self.close() if a.text() == "Excel": data = [] for i in range(self.model.rowCount()): sor = [] for j in range(self.model.columnCount()): if isinstance(self.model.record(i).value(j), QDate): sor.append( self.model.record(i).value(j).toString( "yyyy-MM-dd")) else: sor.append(self.model.record(i).value(j)) data.append(sor) p.save_as(array=data, dest_file_name="tagok.xlsx") def valtozott(self): self.apply_button.setStyleSheet('background-color: green;') self.cancel_button.setStyleSheet('background-color: red;') def valtozas_mentese(self): self.model.submitAll() self.apply_button.setStyleSheet('') self.cancel_button.setStyleSheet('') def valtozas_elvetese(self): self.model.revertAll() self.apply_button.setStyleSheet('') self.cancel_button.setStyleSheet('')
class StatsManager: GROUP_BY = ['filename', 'lineno', 'traceback'] # index in the combo box GROUP_BY_FILENAME = 0 GROUP_BY_LINENO = 1 GROUP_BY_TRACEBACK = 2 def __init__(self, window, app): self.app = app self.window = window self.snapshots = window.snapshots self.source = window.source self.filename_parts = 3 self._auto_refresh = False self.filters = [] self.history = History(self) self.model = StatsModel(self) self.view = QTableView(window) self.view.setModel(self.model) self.cumulative_checkbox = QCheckBox(window.tr("Cumulative sizes"), window) self.group_by = QtGui.QComboBox(window) self.group_by.addItems([ window.tr("Filename"), window.tr("Line number"), window.tr("Traceback"), ]) self.filters_label = QLabel(window) self.summary = QLabel(window) self.view.verticalHeader().hide() self.view.resizeColumnsToContents() self.view.setSortingEnabled(True) window.connect(self.group_by, QtCore.SIGNAL("currentIndexChanged(int)"), self.group_by_changed) window.connect(self.view, QtCore.SIGNAL("doubleClicked(const QModelIndex&)"), self.double_clicked) window.connect(self.cumulative_checkbox, QtCore.SIGNAL("stateChanged(int)"), self.change_cumulative) window.connect(self.snapshots.load_button, QtCore.SIGNAL("clicked(bool)"), self.load_snapshots) window.connect( self.view.selectionModel(), QtCore.SIGNAL( "selectionChanged(const QItemSelection&, const QItemSelection&)" ), self.selection_changed) self.clear() self._auto_refresh = True def clear(self): del self.filters[:] self.cumulative_checkbox.setCheckState(Qt.Unchecked) self.group_by.setCurrentIndex(self.GROUP_BY_FILENAME) self.history.clear() self.append_history() self.refresh() def load_snapshots(self, checked): self.source.clear() self.clear() def append_history(self): group_by = self.group_by.currentIndex() filters = self.filters[:] cumulative = self.cumulative_checkbox.checkState() state = HistoryState(group_by, filters, cumulative) self.history.append(state) def restore_state(self, state): self.filters = state.filters[:] self._auto_refresh = False self.cumulative_checkbox.setCheckState(state.cumulative) self.group_by.setCurrentIndex(state.group_by) self._auto_refresh = True self.refresh() def format_filename(self, filename): parts = filename.split(os.path.sep) if len(parts) > self.filename_parts: parts = [MORE_TEXT] + parts[-self.filename_parts:] return os.path.join(*parts) def get_group_by(self): index = self.group_by.currentIndex() return self.GROUP_BY[index] def get_cumulative(self): return (self.cumulative_checkbox.checkState() == Qt.Checked) def refresh(self): group_by = self.get_group_by() if group_by != 'traceback': cumulative = self.get_cumulative() else: # FIXME: add visual feedback cumulative = False snapshot1, snapshot2 = self.snapshots.load_snapshots(self.filters) self.view.clearSelection() group_by = self.get_group_by() self.model.set_stats(snapshot1, snapshot2, group_by, cumulative) self.view.resizeColumnsToContents() self.view.sortByColumn(self.model.get_default_sort_column(), Qt.DescendingOrder) if self.filters: filters = [] for filter in self.filters: text = self.format_filename(filter.filename_pattern) if filter.lineno: text = "%s:%s" % (text, filter.lineno) if filter.all_frames: text += self.window.tr(" (any frame)") if filter.inclusive: text = fmt(self.window.tr("include %s"), text) else: text = fmt(self.window.tr("exclude %s"), text) filters.append(text) filters_text = ", ".join(filters) else: filters_text = self.window.tr("(none)") filters_text = fmt(self.window.tr("Filters: %s"), filters_text) self.filters_label.setText(filters_text) total = self.model.total_text lines = len(self.model.stats) if group_by == 'filename': lines = fmt(self.window.tr("Files: %s"), lines) elif group_by == 'lineno': lines = fmt(self.window.tr("Lines: %s"), lines) else: lines = fmt(self.window.tr("Tracebacks: %s"), lines) total = fmt(self.window.tr("%s - Total: %s"), lines, total) self.summary.setText(total) def selection_changed(self, selected, unselected): indexes = selected.indexes() if not indexes: return stat = self.model.get_stat(indexes[0]) if stat is None: return self.source.set_traceback(stat.traceback, self.get_group_by() != 'filename') self.source.show_frame(stat.traceback[0]) def double_clicked(self, index): stat = self.model.get_stat(index) if stat is None: return group_by = self.get_group_by() if group_by == 'filename': all_frames = self.get_cumulative() self.filters.append( tracemalloc.Filter(True, stat.traceback[0].filename, all_frames=all_frames)) self._auto_refresh = False self.group_by.setCurrentIndex(self.GROUP_BY_LINENO) self.append_history() self._auto_refresh = True self.refresh() elif group_by == 'lineno': # Replace filter by filename with filter by line new_filter = tracemalloc.Filter(True, stat.traceback[0].filename, stat.traceback[0].lineno, all_frames=False) if self.filters: old_filter = self.filters[-1] replace = (old_filter.inclusive == new_filter.inclusive and old_filter.filename_pattern == new_filter.filename_pattern and old_filter.lineno == None) else: replace = False if replace: self.filters[-1] = new_filter else: self.filters.append(new_filter) self._auto_refresh = False self.group_by.setCurrentIndex(self.GROUP_BY_TRACEBACK) self.append_history() self._auto_refresh = True self.refresh() def group_by_changed(self, index): if not self._auto_refresh: return self.append_history() self.refresh() def change_cumulative(self, state): if not self._auto_refresh: return self.append_history() self.refresh()
class RemoverDialog(QDialog): def __init__(self, parent=None): super(RemoverDialog, self).__init__(parent) self.setupUi() def setupUi(self): self.menuBar = QMenuBar() self.menuBar.show() self.pathInputBox = QLineEdit(self) self.pathInputBox.setEnabled(False) self.pathInputBox.setToolTip( 'Input a path or drag a directory here...') self.openPathButton = QPushButton('Open...', self) self.openPathButton.clicked.connect(self.openPath) inputLayout = QHBoxLayout() inputLayout.addWidget(QLabel('Path:', self)) inputLayout.addWidget(self.pathInputBox) inputLayout.addWidget(self.openPathButton) self.filterFolderCheckBox = QCheckBox('Folders', self) self.filterFolderCheckBox.setChecked(True) self.filterFolderCheckBox.toggled.connect(self.filter) self.filterFileCheckBox = QCheckBox('Files', self) self.filterFileCheckBox.setChecked(True) self.filterFileCheckBox.toggled.connect(self.filter) self.filterSuffixCheckBox = QCheckBox('Suffixes', self) self.filterSuffixCheckBox.setChecked(True) self.filterSuffixCheckBox.toggled.connect(self.filter) filterLayout = QHBoxLayout() filterLayout.addWidget(self.filterFolderCheckBox) filterLayout.addWidget(self.filterFileCheckBox) filterLayout.addWidget(self.filterSuffixCheckBox) filterLayout.addStretch() self.trashButton = QPushButton('Trash', self) self.trashButton.clicked.connect(self.trash) self.deleteButton = QPushButton('Delete', self) self.deleteButton.clicked.connect(self.delete) confirmLayout = QHBoxLayout() confirmLayout.addStretch() confirmLayout.addWidget(self.trashButton) confirmLayout.addWidget(self.deleteButton) layout = QVBoxLayout() layout.addLayout(inputLayout) layout.addLayout(filterLayout) layout.addWidget(self.createResultView()) layout.addLayout(confirmLayout) self.setAcceptDrops(True) self.setLayout(layout) self.setMinimumWidth(600) self.setWindowTitle('Remover') self.setWindowIcon(QApplication.style().standardIcon( QStyle.SP_DirIcon)) def createResultView(self): self.resultModel = ResultModel(self) self.resultView = QTableView(self) self.resultView.setSortingEnabled(True) self.resultView.setShowGrid(False) self.resultView.setAlternatingRowColors(True) self.resultView.verticalHeader().hide() self.resultView.setSelectionBehavior(QAbstractItemView.SelectRows) self.resultView.setSelectionMode(QAbstractItemView.ExtendedSelection) self.sortFilterModel = SortFilterResultModel(self.resultModel, self) self.resultView.setModel(self.sortFilterModel) return self.resultView def dragEnterEvent(self, event): if event.mimeData().hasUrls() and len(event.mimeData().urls()) == 1: event.acceptProposedAction() def dropEvent(self, event): if event.mimeData().hasUrls() and len(event.mimeData().urls()) == 1: self.pathInputBox.setText(event.mimeData().urls()[0].toLocalFile()) self.reloadPath(self.pathInputBox.text()) def openPath(self): path = QFileDialog.getExistingDirectory( parent=self, caption='Open', options=QFileDialog.ShowDirsOnly | QFileDialog.DontResolveSymlinks) if path: self.pathInputBox.setText(path) self.reloadPath(path) def filter(self): filters = [] if self.filterFolderCheckBox.isChecked(): filters.append('folder') if self.filterFileCheckBox.isChecked(): filters.append('file') if self.filterSuffixCheckBox.isChecked(): filters.append('suffix') self.sortFilterModel.setFilterRegularExpression('|'.join(filters)) self.sortFilterModel.filterRegularExpression() self.resultView.resizeRowsToContents() def trash(self): folders, files = self.collectSelectedFolderFiles() try: for file in files: send2trash(file) for folder in folders: if QFile(folder).exists(): send2trash(folder) except: QMessageBox.warning(self, 'Failed', 'Failed to trash selected files/folders') return self.reloadPath(self.pathInputBox.text()) def delete(self): folders, files = self.collectSelectedFolderFiles() try: for file in files: os.remove(file) for folder in folders: shutil.rmtree(folder) except: QMessageBox.warning(self, 'Failed', 'Failed to delete selected files/folders') return self.reloadPath(self.pathInputBox.text()) def collectSelectedFolderFiles(self): folders, files, suffixes = [], [], [] for index in self.resultView.selectedIndexes(): if index.column() != 0: # 忽略第二列的selection continue item = self.sortFilterModel.data(index, Qt.UserRole) if 'folder' == item.type: folders.append(item.name) elif 'file' == item.type: files.append(item.name) elif 'suffix' == item.type: suffixes.append(item.name[2:]) # 将后缀符合选中条件的文件添加到files中 path = self.pathInputBox.text() iterator = QDirIterator(path, filter=QDir.Files | QDir.Dirs | QDir.Hidden | QDir.NoDotAndDotDot, flags=QDirIterator.Subdirectories) folderPaths, filePaths = set(), set() while iterator.hasNext(): file = iterator.next() if '.' == file[-1] or '..' == file[-2]: continue fileInfo = QFileInfo(file) if fileInfo.isDir(): if fileInfo.fileName() in folders: folderPaths.add(fileInfo.absoluteFilePath()) if fileInfo.isFile(): if fileInfo.fileName() in files: filePaths.add(fileInfo.absoluteFilePath()) if fileInfo.suffix() in suffixes: filePaths.add(fileInfo.absoluteFilePath()) return sorted(folderPaths), filePaths def reloadPath(self, path): self.resultModel.reload(path) self.resultView.horizontalHeader().setSectionResizeMode( 0, QHeaderView.Stretch) self.resultView.horizontalHeader().setSectionResizeMode( 1, QHeaderView.ResizeToContents) self.filter() self.resultView.sortByColumn(1, Qt.DescendingOrder)