def do_embed(self, book_ids, only_fmts=None): pd = QProgressDialog(_('Embedding updated metadata into book files...'), _('&Stop'), 0, len(book_ids), self.gui) pd.setWindowTitle(_('Embedding metadata...')) pd.setWindowModality(Qt.WindowModal) errors = [] self.job_data = (0, tuple(book_ids), pd, only_fmts, errors) self.pd_timer.start()
def __init__(self, gui, indices, callback_fn, db, db_type='calibre', status_msg_type='books', action_type=('Decrypting', 'Decryption')): ''' :param gui: Parent gui :param indices: List of Kobo books or list calibre book maps (indicated by param db_type) :param callback_fn: the function from action.py that will do the heavy lifting (get_decrypted_kobo_books or add_new_books) :param db: kobo database object or calibre database cache (indicated by param db_type) :param db_type: string indicating what kind of database param db is :param status_msg_type: string to indicate what the ProgressDialog is operating on (cosmetic only) :param action_type: 2-Tuple of strings indicating what the ProgressDialog is doing to param status_msg_type (cosmetic only) ''' self.total_count = len(indices) QProgressDialog.__init__(self, '', 'Cancel', 0, self.total_count, gui) self.setMinimumWidth(500) self.indices, self.callback_fn, self.db, self.db_type = indices, callback_fn, db, db_type self.action_type, self.status_msg_type = action_type, status_msg_type self.gui = gui self.setWindowTitle('{0} {1} {2}...'.format(self.action_type[0], self.total_count, self.status_msg_type)) self.i, self.successes, self.failures = 0, [], [] QTimer.singleShot(0, self.do_book_action) self.exec_()
def __init__(self, gui, entries, callback_fn, status_msg_type='formats', action_type=('Adding', 'Added')): ''' :param gui: Parent gui :param entries: List of 3-tuples [(target calibre id, calibre metadata object, path to epub file)] :param callback_fn: the function from action.py that will do the heavy lifting (process_epub_formats) :param status_msg_type: string to indicate what the ProgressDialog is operating on (cosmetic only) :param action_type: 2-tuple of strings indicating what the ProgressDialog is doing to param status_msg_type (cosmetic only) ''' self.total_count = len(entries) QProgressDialog.__init__(self, '', 'Cancel', 0, self.total_count, gui) self.setMinimumWidth(500) self.entries, self.callback_fn = entries, callback_fn self.action_type, self.status_msg_type = action_type, status_msg_type self.gui = gui self.setWindowTitle('{0} {1} {2}...'.format(self.action_type[0], self.total_count, self.status_msg_type)) self.i, self.successes, self.failures = 0, [], [] QTimer.singleShot(0, self.do_book_action) self.exec_()
def __init__(self, gui, books, callback_fn, db, target_format, attr, status_msg_type='books', action_type='Checking'): self.total_count = len(books) QProgressDialog.__init__(self, '', 'Cancel', 0, self.total_count, gui) self.setMinimumWidth(500) self.books, self.callback_fn, self.db, self.target_format, self.attr = books, callback_fn, db, target_format, attr self.action_type, self.status_msg_type = action_type, status_msg_type if attr == 'isKF8': self.kindle_type = 'KF8' self.goal = 'EPUB' elif attr == 'isPrintReplica': self.kindle_type = 'PrintReplica' self.goal = 'PDF' self.gui = gui zero = 0 self.setWindowTitle('{0} {1} {2} ({3} issues)...'.format( self.action_type, self.total_count, self.status_msg_type, zero)) self.i, self.successes, self.failures = 0, [], [] QTimer.singleShot(0, self.do_multiple_book_action) self.exec_()
def do_embed(self, book_ids, only_fmts=None): pd = QProgressDialog( _('Embedding updated metadata into book files...'), _('&Stop'), 0, len(book_ids), self.gui) pd.setWindowModality(Qt.WindowModal) errors = [] self.job_data = (0, tuple(book_ids), pd, only_fmts, errors) self.pd_timer.start()
def __init__(self, thread, show_file, parent=None): QProgressDialog.__init__(self, _('Printing, this will take a while, please wait...'), _('&Cancel'), 0, 0, parent) self.show_file = show_file self.setWindowTitle(_('Printing...')) self.setWindowIcon(QIcon(I('print.png'))) self.thread = thread self.timer = t = QTimer(self) t.timeout.connect(self.check) self.canceled.connect(self.do_cancel) t.start(100)
def save (self,filename = None): print ("sauvegarde") progress = QProgressDialog () progress.setWindowModality(QtCore.Qt.WindowModal) progress.setLabelText("Sauvegarde") progress.setMaximum(len(self.getWarriorList())+1) #db_name = self.database.database.databaseName() if filename == None : filename = os.path.join(Config().instance.path_to_sqlite(),self.settings.value("global/current_database")) try : print ('current filename', filename) # backup filename_bkp = filename+"_"+QtCore.QDateTime.currentDateTime().toString("yyyy-MM-dd-hh-mm-ss") QFile.copy(filename,filename_bkp) if QFile.remove(filename) == False : qWarning("echec suppression ") else: qWarning("reussite suppression %s"% filename) except OSError : qWarning("echec suppression ") result = QFile.copy(Config().instance.model_database(),filename) if result == False : print("echec de la copy ",Config().instance.model_database(),filename) return else: print("copy du model reussit") database = DatabaseManager(filename,True) database.createConnection() database.setVerbose(True) for faction in self.factions.values() : attribs = faction.getDictAttributes () database.insert("gm_faction",attribs) for empire in faction.empires.values(): attribs = empire.getDictAttributes () database.insert("gm_empire",attribs) for kingdom in empire.kingdoms.values(): attribs = kingdom.getDictAttributes () database.insert("gm_kingdom",attribs) for temple in kingdom.temples: attribs = temple.getDictAttributes () database.insert("gm_temple",attribs) for groupe in kingdom.groupes.values(): attribs = groupe.getDictAttributes () database.insert("gm_groupe",attribs) for sub_groupe in groupe.sub_groupes: attribs = sub_groupe.getDictAttributes () database.insert("gm_groupe",attribs) for perso in sub_groupe.warriors.values(): attribs = perso.getDictAttributes () database.insert("gm_perso",attribs) for perso in groupe.warriors.values(): attribs = perso.getDictAttributes () database.insert("gm_perso",attribs) progress.setValue(progress.value()+1)
def __init__(self, gui, book_ids, queue, db): QProgressDialog.__init__(self, '', '', 0, len(book_ids), gui) self.setWindowTitle('Queueing books for extracting ISBN') self.setMinimumWidth(500) self.book_ids, self.queue, self.db = book_ids, queue, db self.gui = gui self.i = 0 self.failed_ids, self.no_format_ids, self.books_to_scan = [], [], [] self.input_map = prefs['input_format_order'] QTimer.singleShot(0, self.do_book) self.exec_()
def __init__(self, parent, book_ids, output_format, queue, db, user_recs, args, use_saved_single_settings=True): QProgressDialog.__init__(self, '', None, 0, len(book_ids), parent) self.setWindowTitle(_('Queueing books for bulk conversion')) self.book_ids, self.output_format, self.queue, self.db, self.args, self.user_recs = \ book_ids, output_format, queue, db, args, user_recs self.parent = parent self.use_saved_single_settings = use_saved_single_settings self.i, self.bad, self.jobs, self.changed = 0, [], [], False QTimer.singleShot(0, self.do_book) self.exec_()
def __init__(self, gui, container, match_list, criteria, callback_fn, action_type='Checking'): self.file_list = [i[0] for i in container.mime_map.items() if i[1] in match_list] self.clean = True self.changed_files = [] self.total_count = len(self.file_list) QProgressDialog.__init__(self, '', _('Cancel'), 0, self.total_count, gui) self.setMinimumWidth(500) self.container, self.criteria, self.callback_fn, self.action_type = container, criteria, callback_fn, action_type self.gui = gui self.setWindowTitle('{0}...'.format(self.action_type)) self.i = 0 QTimer.singleShot(0, self.do_action) self.exec_()
def __init__(self, report, parent=None): total = 2 + len(report.name_map) QProgressDialog.__init__(self, _('Losslessly optimizing images, please wait...'), _('&Abort'), 0, total, parent) self.setWindowTitle(self.labelText()) self.setWindowIcon(QIcon(I('lt.png'))) self.setMinimumDuration(0) self.update_signal.connect(self.do_update, type=Qt.QueuedConnection) self.raw = self.prefix = None self.abort = Event() self.canceled.connect(self.abort.set) self.t = Thread(name='CompressIcons', target=self.run_compress, args=(report,)) self.t.daemon = False self.t.start()
def __init__(self, gui, books, callback_fn, db, target_format, attr, status_msg_type='books', action_type='Checking'): self.total_count = len(books) QProgressDialog.__init__(self, '', 'Cancel', 0, self.total_count, gui) self.setMinimumWidth(500) self.books, self.callback_fn, self.db, self.target_format, self.attr = books, callback_fn, db, target_format, attr self.action_type, self.status_msg_type = action_type, status_msg_type if attr == 'isKF8': self.kindle_type = 'KF8' self.goal = 'EPUB' elif attr == 'isPrintReplica': self.kindle_type = 'PrintReplica' self.goal = 'PDF' self.gui = gui zero = 0 self.setWindowTitle('{0} {1} {2} ({3} issues)...'.format(self.action_type, self.total_count, self.status_msg_type, zero)) self.i, self.successes, self.failures = 0, [], [] QTimer.singleShot(0, self.do_multiple_book_action) self.exec_()
def __init__(self, gui, entries, callback_fn, status_msg_type='formats', action_type=('Adding','Added')): ''' :param gui: Parent gui :param entries: List of 3-tuples [(target calibre id, calibre metadata object, path to epub file)] :param callback_fn: the function from action.py that will do the heavy lifting (process_epub_formats) :param status_msg_type: string to indicate what the ProgressDialog is operating on (cosmetic only) :param action_type: 2-tuple of strings indicating what the ProgressDialog is doing to param status_msg_type (cosmetic only) ''' self.total_count = len(entries) QProgressDialog.__init__(self, '', 'Cancel', 0, self.total_count, gui) self.setMinimumWidth(500) self.entries, self.callback_fn = entries, callback_fn self.action_type, self.status_msg_type = action_type, status_msg_type self.gui = gui self.setWindowTitle('{0} {1} {2}...'.format(self.action_type[0], self.total_count, self.status_msg_type)) self.i, self.successes, self.failures = 0, [], [] QTimer.singleShot(0, self.do_book_action) self.exec_()
def __init__(self, gui, book_list, foreach_function, init_label=_("Collecting ..."), win_title=_("Summing Columns"), status_prefix=_("Books collected")): QProgressDialog.__init__(self, init_label, _('Cancel'), 0, len(book_list), gui) self.setWindowTitle(win_title) self.setMinimumWidth(500) self.book_list = book_list self.foreach_function = foreach_function self.status_prefix = status_prefix self.i = 0 ## self.do_loop does QTimer.singleShot on self.do_loop also. ## A weird way to do a loop, but that was the example I had. QTimer.singleShot(0, self.do_loop) self.exec_()
def __init__(self, gui, book_list, foreach_function, init_label=_("Starting..."), win_title=_("Working"), status_prefix=_("Completed so far")): QProgressDialog.__init__(self, init_label, _('Cancel'), 0, len(book_list), gui) self.setWindowTitle(win_title) self.setMinimumWidth(500) self.book_list = book_list self.foreach_function = foreach_function self.status_prefix = status_prefix self.i = 0 ## self.do_loop does QTimer.singleShot on self.do_loop also. ## A weird way to do a loop, but that was the example I had. QTimer.singleShot(0, self.do_loop) self.exec_()
def __init__(self, gui, indices, callback_fn, db, db_type='calibre', status_msg_type='books', action_type=('Decrypting','Decryption')): ''' :param gui: Parent gui :param indices: List of Kobo books or list calibre book maps (indicated by param db_type) :param callback_fn: the function from action.py that will do the heavy lifting (get_decrypted_kobo_books or add_new_books) :param db: kobo database object or calibre database cache (indicated by param db_type) :param db_type: string indicating what kind of database param db is :param status_msg_type: string to indicate what the ProgressDialog is operating on (cosmetic only) :param action_type: 2-Tuple of strings indicating what the ProgressDialog is doing to param status_msg_type (cosmetic only) ''' self.total_count = len(indices) QProgressDialog.__init__(self, '', 'Cancel', 0, self.total_count, gui) self.setMinimumWidth(500) self.indices, self.callback_fn, self.db, self.db_type = indices, callback_fn, db, db_type self.action_type, self.status_msg_type = action_type, status_msg_type self.gui = gui self.setWindowTitle('{0} {1} {2}...'.format(self.action_type[0], self.total_count, self.status_msg_type)) self.i, self.successes, self.failures = 0, [], [] QTimer.singleShot(0, self.do_book_action) self.exec_()
def __init__(self, gui, split_list, foreach_function, init_label=_("Splitting Sections..."), win_title=_("Splitting Sections..."), status_prefix=_("Splitting Sections...")): QProgressDialog.__init__(self, init_label, _('Cancel'), 0, len(split_list), gui) self.setWindowTitle(win_title) self.setMinimumWidth(500) self.split_list = split_list self.foreach_function = foreach_function self.status_prefix = status_prefix self.i = 0 self.start_time = datetime.now() ## self.do_loop does QTimer.singleShot on self.do_loop also. ## A weird way to do a loop, but that was the example I had. QTimer.singleShot(0, self.do_loop) self.exec_()
def cancel(self): self.progress = QProgressDialog(self) self.progress.setFixedWidth(500) self.progress.setFixedHeight(80) self.progress.setWindowTitle("正在取消,请稍等...") self.progress.setCancelButtonText("取消") self.progress.setMinimumDuration(1) self.progress.setWindowModality(Qt.ApplicationModal) self.progress.setRange(0, 0) self.progress.show() # 清空进度条显示列表 count = self.qpb_list_widget.count() for i in range(count): item = self.qpb_list_widget.takeItem(0) del item # 清空任务线程池;线程池清空后,会触发监听线程的完成信号,重置返回和打包按钮 # 因为打包任务调用外部程序,并不能立即终止外部程序连接,所以清空过程有延迟 for channel_id in self.lbps: self.lbps[channel_id]['runnable'].is_close = True self.monitor.clear()
def process_duplicates(self): duplicates = self.db_adder.duplicates if not duplicates: return self.duplicates_processed() self.pd.hide() from calibre.gui2.dialogs.duplicates import DuplicatesQuestion self.__d_q = d = DuplicatesQuestion(self.db, duplicates, self._parent) duplicates = tuple(d.duplicates) if duplicates: pd = QProgressDialog(_('Adding duplicates...'), '', 0, len(duplicates), self._parent) pd.setCancelButton(None) pd.setValue(0) pd.show() self.__p_d = pd self.__d_a = DuplicatesAdder(self._parent, self.db, duplicates, self.db_adder) self.__d_a.added.connect(pd.setValue) self.__d_a.adding_done.connect(self.duplicates_processed) else: return self.duplicates_processed()
def process_duplicates(self): duplicates = self.db_adder.duplicates if not duplicates: return self.duplicates_processed() self.pd.hide() from calibre.gui2.dialogs.duplicates import DuplicatesQuestion self.__d_q = d = DuplicatesQuestion(self.db, duplicates, self._parent) duplicates = tuple(d.duplicates) if duplicates: pd = QProgressDialog(_("Adding duplicates..."), "", 0, len(duplicates), self._parent) pd.setCancelButton(None) pd.setValue(0) pd.show() self.__p_d = pd self.__d_a = DuplicatesAdder(self._parent, self.db, duplicates, self.db_adder) self.__d_a.added.connect(pd.setValue) self.__d_a.adding_done.connect(self.duplicates_processed) else: return self.duplicates_processed()
def refresh(self): progress_dialog = QProgressDialog(self) thread = RunFuncThread(func=get_rss_jira_log) thread.run_finished.connect(self._fill_tables) thread.run_finished.connect(progress_dialog.close) thread.start() progress_dialog.setWindowTitle('Please wait...') progress_dialog.setLabelText(progress_dialog.windowTitle()) progress_dialog.setRange(0, 0) progress_dialog.exec() from datetime import datetime self.setWindowTitle(WINDOW_TITLE + ". Last refresh date: " + datetime.now().strftime('%d/%m/%Y %H:%M:%S'))
class PackageWidget(QWidget): def __init__(self, main, channels): super(PackageWidget, self).__init__() self.setObjectName("PackageWidget") self.main_win = main self.game = self.main_win.games[self.main_win.game_index] self.channels = channels self.check_boxs = [] self.indexs = [] self.lbps = {} self.progress = None self.monitor = PackageMonitor() self.monitor.signal.connect(self.complete) v_layout = QVBoxLayout() h_layout1 = QHBoxLayout() cbox_widget = QWidget() v_layout1 = QVBoxLayout() self.all_selected_cbox = QCheckBox("全 选") self.all_selected_cbox.stateChanged.connect(self.select_all) v_layout1.addWidget(self.all_selected_cbox) for channel in self.channels: check_box = QCheckBox(channel['channelId']) check_box.setFixedWidth(100) v_layout1.addSpacing(10) v_layout1.addWidget(check_box) self.check_boxs.append(check_box) cbox_widget.setLayout(v_layout1) channel_list_area = QScrollArea() channel_list_area.setWidget(cbox_widget) h_layout1.addWidget(channel_list_area, 1) self.qpb_list_widget = QListWidget() self.qpb_list_widget.setSelectionMode( QAbstractItemView.SingleSelection) self.qpb_list_widget.itemDoubleClicked.connect(self.select_list) h_layout1.addWidget(self.qpb_list_widget, 5) v_layout.addLayout(h_layout1) h_layout2 = QHBoxLayout() self.back_btn = QPushButton("返 回") self.back_btn.setFixedWidth(100) self.back_btn.clicked.connect(self.back) h_layout2.addWidget(self.back_btn, alignment=Qt.AlignLeft | Qt.AlignBottom) h_layout2.addSpacing(100) select_apk_btn = QPushButton("选择母包:") select_apk_btn.clicked.connect(self.select_apk) h_layout2.addWidget(select_apk_btn) self.apk_path = QLineEdit() self.apk_path.setPlaceholderText("母包路径") h_layout2.addWidget(self.apk_path) h_layout2.addSpacing(100) self.pack_btn = QPushButton("打 包") self.pack_btn.setFixedWidth(100) self.pack_btn.clicked.connect(self.click) h_layout2.addWidget(self.pack_btn, alignment=Qt.AlignRight | Qt.AlignBottom) v_layout.addLayout(h_layout2) self.setLayout(v_layout) def select_list(self): index = self.qpb_list_widget.currentIndex().row() channel_id = self.channels[self.indexs[index]]['channelId'] success = self.lbps[channel_id]['success'] dest_apk_dir = Utils.get_full_path('output/' + self.game['id'] + '/' + channel_id) if success: os.startfile(dest_apk_dir) else: QMessageBox.warning(self, "警告", "打包成功了吗?") def back(self): self.monitor.deleteLater() self.main_win.set_channel_list_widget(self.channels) def select_apk(self): fname = QFileDialog.getOpenFileName( self, '选择母包', os.path.join(os.path.expanduser('~'), "Desktop"), ("Apk (*.apk)")) if fname[0]: self.apk_path.setStyleSheet("font-size:12px") self.apk_path.setText(fname[0]) def select_all(self): if self.all_selected_cbox.isChecked(): for cbox in self.check_boxs: cbox.setChecked(True) else: for cbox in self.check_boxs: cbox.setChecked(False) def click(self): if self.pack_btn.text() == "打 包": self.package() elif self.pack_btn.text() == "取 消": self.cancel() def package(self): # 清空上次打包完成后的进度条显示列表 count = self.qpb_list_widget.count() if count > 0: for i in range(count): item = self.qpb_list_widget.takeItem(0) del item self.indexs = [] for i in range(len(self.channels)): if self.check_boxs[i].isChecked(): self.indexs.append(i) if len(self.indexs) <= 0: QMessageBox.warning(self, "警告", "请选择需要打包的渠道!") return if self.apk_path.text().strip() == "": QMessageBox.warning(self, "警告", "请上传母包!") return apk = self.apk_path.text().strip().replace('\\', '/') for i in self.indexs: lbp = {} lbp['success'] = False self.set_qpb_list_item(self.channels[i], lbp) runnable = PackRunnable(self.game, self.channels[i], apk) runnable.signal.signal.connect(self.set_value) self.monitor.add_runnable(runnable) lbp['runnable'] = runnable self.lbps[self.channels[i]['channelId']] = lbp # 开启监听线程 self.monitor.start() # 开始打包,不可返回,返回按钮禁用;设置打包按钮文本为"取 消" self.back_btn.setDisabled(True) self.pack_btn.setText("取 消") def set_qpb_list_item(self, channel, lbp): item = QListWidgetItem(self.qpb_list_widget) item.setSizeHint(QSize(400, 80)) widget = QWidget(self.qpb_list_widget) v_layout = QVBoxLayout() label = QLabel(channel['channelId'] + "==>>>等待出包...") v_layout.addWidget(label) lbp['label'] = label qpb = QProgressBar(self.qpb_list_widget) v_layout.addWidget(qpb) lbp['qpb'] = qpb widget.setLayout(v_layout) self.qpb_list_widget.addItem(item) self.qpb_list_widget.setItemWidget(item, widget) def set_value(self, channel_id, result, msg, step): lbp = self.lbps[channel_id] if result: # 打包步骤异常,提示异常,关闭进度条 lbp['label'].setText(channel_id + "==>>>" + msg) lbp['qpb'].close() if step == 100: lbp['success'] = True self.lbps[channel_id] = lbp else: # 打包正常,设置进度条进度 lbp['qpb'].setValue(step) if step == 0: lbp['label'].setText(channel_id + "==>>>" + msg) # 取消打包(全部取消) def cancel(self): self.progress = QProgressDialog(self) self.progress.setFixedWidth(500) self.progress.setFixedHeight(80) self.progress.setWindowTitle("正在取消,请稍等...") self.progress.setCancelButtonText("取消") self.progress.setMinimumDuration(1) self.progress.setWindowModality(Qt.ApplicationModal) self.progress.setRange(0, 0) self.progress.show() # 清空进度条显示列表 count = self.qpb_list_widget.count() for i in range(count): item = self.qpb_list_widget.takeItem(0) del item # 清空任务线程池;线程池清空后,会触发监听线程的完成信号,重置返回和打包按钮 # 因为打包任务调用外部程序,并不能立即终止外部程序连接,所以清空过程有延迟 for channel_id in self.lbps: self.lbps[channel_id]['runnable'].is_close = True self.monitor.clear() # 取消打包(清空任务完成),或打包完成, def complete(self): if self.progress is not None: self.progress.cancel() # 清空复选框的选择 self.all_selected_cbox.setChecked(False) for cbox in self.check_boxs: cbox.setChecked(False) # 返回按钮解禁;设置打包按钮文本为"打 包" self.back_btn.setDisabled(False) self.pack_btn.setText("打 包")
class PackageWidgetM(QWidget): def __init__(self, main): super(PackageWidgetM, self).__init__() self.setObjectName("PackageWidgetM") self.main_win = main self.game_index = 0 self.selected = [ ] # 已选中的channel及所属game列表 如:[{"game": 当前game字典, "channel": 当前channel字典}, {}, {}] self.selected_name = [ ] # 已选中的渠道显示名称列表 如:["10878922-765321", "", "", ""] self.lbps = {} # 打包信息及进度条组合字典 {"765321": {}, "": {}} self.progress = None self.monitor = PackageMonitor() self.monitor.signal.connect(self.complete) v_layout = QVBoxLayout() h_layout1 = QHBoxLayout() # 全部游戏及其下的渠道列表 self.tool_box = QToolBox(self) self.tool_box.setFixedWidth(100) for game in self.main_win.games: clv = QListView() clv.setEditTriggers(QAbstractItemView.NoEditTriggers) clv.setContextMenuPolicy(Qt.CustomContextMenu) self.tool_box.addItem(clv, game['id']) self.tool_box.currentChanged.connect(self.select_game) self.tool_box.setCurrentIndex(self.game_index) channel_list_area = QScrollArea() channel_list_area.setWidget(self.tool_box) h_layout1.addWidget(channel_list_area, 1) # 已选择的渠道列表 self.cslv_model = QStringListModel() self.cslv_model.setStringList([]) self.cslv = QListView() self.cslv.setModel(self.cslv_model) self.cslv.setEditTriggers(QAbstractItemView.NoEditTriggers) self.cslv.doubleClicked.connect(self.delete_channel) self.cslv.setContextMenuPolicy(Qt.CustomContextMenu) h_layout1.addWidget(self.cslv, 2) # 打包进度条显示列表 self.qpb_list_widget = QListWidget() self.qpb_list_widget.setSelectionMode( QAbstractItemView.SingleSelection) self.qpb_list_widget.itemDoubleClicked.connect(self.select_qpb_list) h_layout1.addWidget(self.qpb_list_widget, 5) v_layout.addLayout(h_layout1) h_layout2 = QHBoxLayout() self.back_btn = QPushButton("返 回") self.back_btn.setFixedWidth(100) self.back_btn.clicked.connect(self.back) h_layout2.addWidget(self.back_btn, alignment=Qt.AlignLeft | Qt.AlignBottom) h_layout2.addSpacing(100) select_apk_btn = QPushButton("选择母包:") select_apk_btn.setFixedWidth(100) select_apk_btn.clicked.connect(self.select_apk) h_layout2.addWidget(select_apk_btn) self.apk_path = QLabel() self.apk_path.setText("<h3><font color=%s>%s</font></h3>" % ('red', "请浏览选择本地母包路径")) h_layout2.addWidget(self.apk_path) h_layout2.addSpacing(100) self.pack_btn = QPushButton("打 包") self.pack_btn.setFixedWidth(100) self.pack_btn.clicked.connect(self.click) h_layout2.addWidget(self.pack_btn, alignment=Qt.AlignRight | Qt.AlignBottom) v_layout.addLayout(h_layout2) self.setLayout(v_layout) def select_game(self, p_int): self.game_index = p_int if 'apk' in self.main_win.games[self.game_index]: self.apk_path.setText(self.main_win.games[self.game_index]['apk']) else: self.apk_path.setText("<h3><font color=%s>%s</font></h3>" % ('red', "请浏览选择本地母包路径")) # self.apk_path.setText("请浏览选择本地母包路径") # 当前选中的game,其下的所有渠道列表 self.channels = Utils.get_channels( Utils.get_full_path('games/' + self.main_win.games[p_int]['id'] + '/config.xml')) channel_ids = [] for channel in self.channels: channel_ids.append(channel['channelId']) list_model = QStringListModel() list_model.setStringList(channel_ids) self.clv = self.tool_box.currentWidget() self.clv.doubleClicked.connect(self.select_channel) self.clv.setModel(list_model) # 双击选中当前渠道,更新已选中列表的model def select_channel(self): if 'apk' not in self.main_win.games[self.game_index]: QMessageBox.warning(self, "警告", "请先添加母包!") return channel = self.channels[self.clv.currentIndex().row()] name = self.main_win.games[ self.game_index]['id'] + '-' + channel['channelId'] if name in self.selected_name: return self.selected_name.append(name) self.cslv_model.setStringList(self.selected_name) package = { 'game': self.main_win.games[self.game_index], 'channel': channel } self.selected.append(package) # 双击移除当前渠道,更新已选中列表的model def delete_channel(self): name = self.selected_name[self.cslv.currentIndex().row()] self.selected_name.remove(name) self.cslv_model.setStringList(self.selected_name) package = self.selected[self.cslv.currentIndex().row()] self.selected.remove(package) def select_qpb_list(self): index = self.qpb_list_widget.currentIndex().row() game_id = self.selected[index]['game']['id'] channel_id = self.selected[index]['channel']['channelId'] success = self.lbps[channel_id]['success'] dest_apk_dir = Utils.get_full_path('output/' + game_id + '/' + channel_id) if success: os.startfile(dest_apk_dir) else: QMessageBox.warning(self, "警告", "打包成功了吗?") def back(self): self.monitor.deleteLater() self.main_win.set_main_widget() def select_apk(self): f_name = QFileDialog.getOpenFileName( self, '选择母包', os.path.join(os.path.expanduser('~'), "Desktop"), ("Apk (*.apk)")) if f_name[0]: self.apk_path.setStyleSheet("font-size:12px") self.apk_path.setText(f_name[0]) self.main_win.games[self.game_index]['apk'] = f_name[0] def click(self): if self.pack_btn.text() == "打 包": self.package() elif self.pack_btn.text() == "取 消": self.cancel() def package(self): # 清空上次打包完成后的进度条显示列表 count = self.qpb_list_widget.count() if count > 0: for i in range(count): item = self.qpb_list_widget.takeItem(0) del item if len(self.selected) <= 0: QMessageBox.warning(self, "警告", "请选择需要打包的渠道!") return for package in self.selected: # {"success": 是否成功, "label": 进度条文本view, "qpb": 进度条view, "runnable": 打包任务} lbp = {'success': False} self.set_qpb_list_item(package['channel']['channelId'], lbp) runnable = PackRunnable(package['game'], package['channel'], package['game']['apk']) runnable.signal.signal.connect(self.set_value) self.monitor.add_runnable(runnable) lbp['runnable'] = runnable self.lbps[package['channel']['channelId']] = lbp # 开启监听线程 self.monitor.start() # 开始打包,不可返回,返回按钮禁用;设置打包按钮文本为"取 消" self.back_btn.setDisabled(True) self.pack_btn.setText("取 消") def set_qpb_list_item(self, channel_id, lbp): item = QListWidgetItem(self.qpb_list_widget) item.setSizeHint(QSize(400, 80)) widget = QWidget(self.qpb_list_widget) v_layout = QVBoxLayout() label = QLabel(channel_id + "==>>>等待出包...") v_layout.addWidget(label) lbp['label'] = label qpb = QProgressBar(self.qpb_list_widget) v_layout.addWidget(qpb) lbp['qpb'] = qpb widget.setLayout(v_layout) self.qpb_list_widget.addItem(item) self.qpb_list_widget.setItemWidget(item, widget) def set_value(self, channel_id, result, msg, step): lbp = self.lbps[channel_id] if result: # 打包步骤异常,提示异常,关闭进度条 lbp['label'].setText(channel_id + "==>>>" + msg) lbp['qpb'].close() if step == 100: lbp['success'] = True self.lbps[channel_id] = lbp else: # 打包正常,设置进度条进度 lbp['qpb'].setValue(step) if step == 0: lbp['label'].setText(channel_id + "==>>>" + msg) # 取消打包(全部取消) def cancel(self): self.progress = QProgressDialog(self) self.progress.setFixedWidth(500) self.progress.setFixedHeight(80) self.progress.setWindowTitle("正在取消,请稍等...") self.progress.setCancelButtonText("取消") self.progress.setMinimumDuration(1) self.progress.setWindowModality(Qt.ApplicationModal) self.progress.setRange(0, 0) self.progress.show() # 清空进度条显示列表 count = self.qpb_list_widget.count() for i in range(count): item = self.qpb_list_widget.takeItem(0) del item # 清空任务线程池;线程池清空后,会触发监听线程的完成信号,重置返回和打包按钮 # 因为打包任务调用外部程序,并不能立即终止外部程序连接,所以清空过程有延迟 for channel_id in self.lbps: self.lbps[channel_id]['runnable'].is_close = True self.monitor.clear() # 取消打包(清空任务完成),或打包完成, def complete(self): if self.progress is not None: self.progress.cancel() # 返回按钮解禁;设置打包按钮文本为"打 包" self.back_btn.setDisabled(False) self.pack_btn.setText("打 包")
def alterTable(self, mtd1, mtd2, key): util = FLUtil() oldMTD = None newMTD = None doc = QDomDocument("doc") docElem = None if not util.docDocumentSetContect(doc, mtd1): print("FLManager::alterTable : " + qApp.tr("Error al cargar los metadatos.")) else: docElem = doc.documentElement() oldMTD = self.db_.manager().metadata(docElem, True) if oldMTD and oldMTD.isQuery(): return True if not util.docDocumentSetContect(doc, mtd2): print("FLManager::alterTable : " + qApp.tr("Error al cargar los metadatos.")) return False else: docElem = doc.documentElement() newMTD = self.db_.manager().metadata(docElem, True) if not oldMTD: oldMTD = newMTD if not oldMTD.name() == newMTD.name(): print("FLManager::alterTable : " + qApp.tr("Los nombres de las tablas nueva y vieja difieren.")) if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return False oldPK = oldMTD.primaryKey() newPK = newMTD.primaryKey() if not oldPK == newPK: print("FLManager::alterTable : " + qApp.tr("Los nombres de las claves primarias difieren.")) if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return False if not self.db_.manager().checkMetaData(oldMTD, newMTD): if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return True if not self.db_.manager().existsTable(oldMTD.name()): print("FLManager::alterTable : " + qApp.tr( "La tabla %1 antigua de donde importar los registros no existe.").arg(oldMTD.name())) if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return False fieldList = oldMTD.fieldList() oldField = None if not fieldList: print("FLManager::alterTable : " + qApp.tr("Los antiguos metadatos no tienen campos.")) if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return False renameOld = "%salteredtable%s" % ( oldMTD.name()[0:5], QDateTime().currentDateTime().toString("ddhhssz")) if not self.db_.dbAux(): if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return False self.db_.dbAux().transaction() if key and len(key) == 40: c = FLSqlCursor("flfiles", True, self.db_.dbAux()) c.setForwardOnly(True) c.setFilter("nombre = '%s.mtd'" % renameOld) c.select() if not c.next(): buffer = c.primeInsert() buffer.setValue("nombre", "%s.mtd" % renameOld) buffer.setValue("contenido", mtd1) buffer.setValue("sha", key) c.insert() q = FLSqlQuery("", self.db_.dbAux()) if not q.exec_("CREATE TABLE %s AS SELECT * FROM %s;" % (renameOld, oldMTD.name())) or not q.exec_("DROP TABLE %s;" % oldMTD.name()): print("FLManager::alterTable : " + qApp.tr("No se ha podido renombrar la tabla antigua.")) self.db_.dbAux().rollback() if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return False if not self.db_.manager().createTable(newMTD): self.db_.dbAux().rollback() if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return False oldCursor = FLSqlCursor(renameOld, True, self.db_.dbAux()) oldCursor.setModeAccess(oldCursor.Browse) newCursor = FLSqlCursor(newMTD.name(), True, self.db_.dbAux()) newCursor.setMode(newCursor.Insert) oldCursor.select() totalSteps = oldCursor.size() progress = QProgressDialog(qApp.tr("Reestructurando registros para %1...").arg( newMTD.alias()), qApp.tr("Cancelar"), 0, totalSteps) progress.setLabelText(qApp.tr("Tabla modificada")) step = 0 newBuffer = None # sequence = "" fieldList = newMTD.fieldList() newField = None if not fieldList: print("FLManager::alterTable : " + qApp.tr("Los nuevos metadatos no tienen campos.")) self.db_.dbAux().rollback() if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return False v = None ok = True while oldCursor.next(): v = None newBuffer = newCursor.primeInsert() for it in fieldList: oldField = oldMTD.field(newField.name()) if not oldField or not oldCursor.field(oldField.name()): if not oldField: oldField = newField v = newField.defaultValue() else: v = oldCursor.value(newField.name()) if (not oldField.allowNull() or not newField.allowNull()) and (v is None): defVal = newField.defaultValue() if defVal is not None: v = defVal if not newBuffer.field(newField.name()).type() == newField.type(): print("FLManager::alterTable : " + qApp.tr("Los tipos del campo %1 no son compatibles. Se introducirá un valor nulo.") .arg(newField.name())) if not oldField.allowNull() or not newField.allowNull() and v is not None: if oldField.type() in ("int", "serial", "uint", "bool", "unlock"): v = 0 elif oldField.type() == "double": v = 0.0 elif oldField.type() == "time": v = QTime().currentTime() elif oldField.type() == "date": v = QDate().currentDate() else: v = "NULL"[0:newField.length()] newBuffer.setValue(newField.name(), v) if not newCursor.insert(): ok = False break step = step + 1 progress.setProgress(step) progress.setProgress(totalSteps) if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD if ok: self.db_.dbAux().commit() else: self.db_.dbAux().rollback() return False return True
def alterTable(self, mtd1, mtd2, key): util = FLUtil() oldMTD = None newMTD = None doc = QDomDocument("doc") docElem = None if not util.docDocumentSetContect(doc, mtd1): print("FLManager::alterTable : " + qApp.tr("Error al cargar los metadatos.")) else: docElem = doc.documentElement() oldMTD = self.db_.manager().metadata(docElem, True) if oldMTD and oldMTD.isQuery(): return True if not util.docDocumentSetContect(doc, mtd2): print("FLManager::alterTable : " + qApp.tr("Error al cargar los metadatos.")) return False else: docElem = doc.documentElement() newMTD = self.db_.manager().metadata(docElem, True) if not oldMTD: oldMTD = newMTD if not oldMTD.name() == newMTD.name(): print("FLManager::alterTable : " + qApp.tr("Los nombres de las tablas nueva y vieja difieren.")) if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return False oldPK = oldMTD.primaryKey() newPK = newMTD.primaryKey() if not oldPK == newPK: print("FLManager::alterTable : " + qApp.tr("Los nombres de las claves primarias difieren.")) if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return False if not self.db_.manager().checkMetaData(oldMTD, newMTD): if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return True if not self.db_.manager().existsTable(oldMTD.name()): print("FLManager::alterTable : " + qApp.tr( "La tabla %1 antigua de donde importar los registros no existe." ).arg(oldMTD.name())) if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return False fieldList = oldMTD.fieldList() oldField = None if not fieldList: print("FLManager::alterTable : " + qApp.tr("Los antiguos metadatos no tienen campos.")) if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return False renameOld = "%salteredtable%s" % (oldMTD.name()[0:5], QDateTime( ).currentDateTime().toString("ddhhssz")) if not self.db_.dbAux(): if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return False self.db_.dbAux().transaction() if key and len(key) == 40: c = FLSqlCursor("flfiles", True, self.db_.dbAux()) c.setForwardOnly(True) c.setFilter("nombre = '%s.mtd'" % renameOld) c.select() if not c.next(): buffer = c.primeInsert() buffer.setValue("nombre", "%s.mtd" % renameOld) buffer.setValue("contenido", mtd1) buffer.setValue("sha", key) c.insert() q = FLSqlQuery("", self.db_.dbAux()) if not q.exec_("CREATE TABLE %s AS SELECT * FROM %s;" % (renameOld, oldMTD.name())) or not q.exec_( "DROP TABLE %s;" % oldMTD.name()): print("FLManager::alterTable : " + qApp.tr("No se ha podido renombrar la tabla antigua.")) self.db_.dbAux().rollback() if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return False if not self.db_.manager().createTable(newMTD): self.db_.dbAux().rollback() if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return False oldCursor = FLSqlCursor(renameOld, True, self.db_.dbAux()) oldCursor.setModeAccess(oldCursor.Browse) newCursor = FLSqlCursor(newMTD.name(), True, self.db_.dbAux()) newCursor.setMode(newCursor.Insert) oldCursor.select() totalSteps = oldCursor.size() progress = QProgressDialog( qApp.tr("Reestructurando registros para %1...").arg( newMTD.alias()), qApp.tr("Cancelar"), 0, totalSteps) progress.setLabelText(qApp.tr("Tabla modificada")) step = 0 newBuffer = None # sequence = "" fieldList = newMTD.fieldList() newField = None if not fieldList: print("FLManager::alterTable : " + qApp.tr("Los nuevos metadatos no tienen campos.")) self.db_.dbAux().rollback() if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD return False v = None ok = True while oldCursor.next(): v = None newBuffer = newCursor.primeInsert() for it in fieldList: oldField = oldMTD.field(newField.name()) if not oldField or not oldCursor.field(oldField.name()): if not oldField: oldField = newField v = newField.defaultValue() else: v = oldCursor.value(newField.name()) if (not oldField.allowNull() or not newField.allowNull()) and (v is None): defVal = newField.defaultValue() if defVal is not None: v = defVal if not newBuffer.field( newField.name()).type() == newField.type(): print("FLManager::alterTable : " + qApp.tr( "Los tipos del campo %1 no son compatibles. Se introducirá un valor nulo." ).arg(newField.name())) if not oldField.allowNull( ) or not newField.allowNull() and v is not None: if oldField.type() in ("int", "serial", "uint", "bool", "unlock"): v = 0 elif oldField.type() == "double": v = 0.0 elif oldField.type() == "time": v = QTime().currentTime() elif oldField.type() == "date": v = QDate().currentDate() else: v = "NULL"[0:newField.length()] newBuffer.setValue(newField.name(), v) if not newCursor.insert(): ok = False break step = step + 1 progress.setProgress(step) progress.setProgress(totalSteps) if oldMTD and not oldMTD == newMTD: del oldMTD if newMTD: del newMTD if ok: self.db_.dbAux().commit() else: self.db_.dbAux().rollback() return False return True