PyQt5脚本点击对话框按钮关闭后无法返回终端提示符如何解决
问题原因
你的代码执行逻辑存在多余的事件循环启动步骤:
- 实例化
MainAppWindow时,会先执行构造方法里的dialog.exec_(),启动模态对话框的阻塞事件循环,点击按钮后对话框关闭、打印对应内容,构造方法执行完毕。 - 此时你已经创建了未显示的
MainAppWindow实例win,代码随后进入app.exec_()启动全局应用事件循环,由于还有存活的顶级窗口(隐藏的主窗口),事件循环不会自动退出,因此终端会一直挂住无法返回提示符。
解决方案
有两种常用修复方式,按需选择即可:
方案1:删除冗余的主窗口逻辑(更适合当前仅需要对话框的场景)
你当前的需求仅需要弹出交互对话框,不需要主窗口,直接删掉MainAppWindow类的封装即可,修改后代码如下:
from PyQt5 import Qt from PyQt5.QtWidgets import QApplication import sys if __name__ == "__main__": app = QApplication(sys.argv) dialog = Qt.QDialog() buttonbox = Qt.QDialogButtonBox(Qt.QDialogButtonBox.Ok | Qt.QDialogButtonBox.Cancel) layout = Qt.QVBoxLayout() param_box = Qt.QGroupBox('Iterate over parameters:') pblayout = Qt.QVBoxLayout() pblayout.setContentsMargins(0, 0, 0, 0) scroll = Qt.QScrollArea() scroll.setWidgetResizable(True) scroll.setFrameStyle(scroll.NoFrame) scroll.setViewportMargins(0, 0, 0, 0) pblayout.addWidget(scroll) param_lay = Qt.QGridLayout() wid = Qt.QWidget() scroll.setWidget(wid) wid.setLayout(param_lay) param_box.setLayout(pblayout) layout.addWidget(param_box) layout.addWidget(buttonbox) dialog.setLayout(layout) buttonbox.accepted.connect(dialog.accept) buttonbox.rejected.connect(dialog.reject) param_lay.addWidget(Qt.QLabel('iter. / database:'), 0, 0, 1, 3) param_lay.addWidget(Qt.QLabel('iter.:'), 0, 3, 1, 2) param_lay.setColumnStretch(2, 1) param_lay.setColumnStretch(4, 1) param_lay.setRowStretch(0, 0) res = dialog.exec_() if res != dialog.Accepted: print('dialog not accepted') else: print('dialog accepted') sys.exit(0)
方案2:保留主窗口结构,对话框处理完主动退出事件循环
如果后续需要用到主窗口功能,可以在对话框返回后主动退出全局事件循环,只需在MainAppWindow构造方法的打印语句后新增一行退出逻辑即可:
if res != dialog.Accepted: print('dialog not accepted') else: print('dialog accepted') # 新增:主动退出全局事件循环 Qt.QApplication.instance().quit()
内容的提问来源于stack exchange,提问作者servoz
相关产品推荐
相关产品推荐

