Python PyQt QDialog - 返回一个值并从对话框中关闭

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/28706651/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-19 03:38:27  来源:igfitidea点击:

PyQt QDialog - returning a value and closing from dialog

pythonqtuser-interfacepyqtqdialog

提问by Emily C

I'm working on a user interface in PyQt, and I'm running into a few problems trying to use QDialog. Essentially I have a main widget and a sub-widget, saved in separate .py files; I would like the sub-widget to open when I click a certain button in the main widget. This seems to be opening fine.

我正在 PyQt 中处理用户界面,并且在尝试使用 QDialog 时遇到了一些问题。本质上,我有一个主小部件和一个子小部件,保存在单独的 .py 文件中;当我单击主窗口小部件中的某个按钮时,我希望子窗口小部件打开。这似乎打开得很好。

The issue comes with returning and closing. I have a "submit" button on my sub-widget - when the user clicks this button, I would like to return a value (a dictionary made from their input) to the main widget, and close the sub-widget. I can't seem to do either of these things with the code I have right now.

问题在于返回和关闭。我的子小部件上有一个“提交”按钮 - 当用户单击此按钮时,我想向主小部件返回一个值(根据他们的输入制作的字典),然后关闭子小部件。我似乎无法用我现在拥有的代码来做这些事情。

Applicable bits of code in the main widget (can add more to make it self-contained if the problem isn't obvious):

主小部件中的适用代码位(如果问题不明显,可以添加更多代码以使其独立):

import SGROIWidget_ui

def retranslateUi(self, ROIGUI):
    #ShowGroupROI is a push-button
    self.ShowGroupROI.clicked.connect(self.ShowGroupROIFunction)

def ShowGroupROIFunction(self):
    dialog = QDialog()
    dialog.ui = SGROIWidget_ui.Ui_ShowGroupWidget()
    dialog.ui.setupUi(dialog)
    dialog.setAttribute(QtCore.Qt.WA_DeleteOnClose)
    if dialog.exec_():
        roiGroups=dialog.Submitclose()
        print(roiGroups)
        dialog.accept()

I never seem to hit the code after the if-statement.

我似乎从来没有在 if 语句之后点击代码。

The applicable code from my sub-widget (will include a bit more here):

我的子小部件中的适用代码(将在此处包含更多内容):

try:
    _fromUtf8 = QtCore.QString.fromUtf8
except AttributeError:
    def _fromUtf8(s):
        return s

try:
    _encoding = QtGui.QApplication.UnicodeUTF8
    def _translate(context, text, disambig):
        return QtGui.QApplication.translate(context, text, disambig, _encoding)
except AttributeError:
    def _translate(context, text, disambig):
        return QtGui.QApplication.translate(context, text, disambig)

class Ui_ShowGroupWidget(QtGui.QWidget):
    def __init__(self):
        QtGui.QWidget.__init__(self)
        self.setupUi(self)

    def setupUi(self, ShowGroupWidget):
        #sets up Submit button

    def retranslateUi(self, ShowGroupWidget):
        self.Submit.clicked.connect(self.Submitclose)

     def Submitclose(self):
        roiGroups={}
        #roiGroups gets set up here as a dictionary
        #It prints nicely from here so I know it's not the issue

        return roiGroups 
        #I don't know if I can just do a return statement like this?
        self.close()*

*I have tried ex.close() here as well but ex is not recognized when this widget is run as a dialog. It doesn't seem like it should get to this line because of the return statement, but I don't know how else to close this widget after the user hits "submit". Or should the dialog.accept() in my main widget handle that?

*我也在这里尝试过 ex.close() 但当这个小部件作为对话框运行时,ex 无法识别。由于 return 语句,它似乎不应该到达这一行,但我不知道在用户点击“提交”后如何关闭此小部件。或者我的主要小部件中的 dialog.accept() 应该处理吗?

One last thing - do I need this in my sub-widget at all, since it's being run through my main widget instead?

最后一件事 - 我是否需要在我的子小部件中使用它,因为它是通过我的主小部件运行的?

if __name__=='__main__':
    app=QtGui.QApplication(sys.argv)
    ex=Ui_ShowGroupWidget()
    ex.show()
    sys.exit(app.exec_())

Thanks in advance! I am pretty new to PyQt so hopefully this is somewhat legible.

提前致谢!我对 PyQt 很陌生,所以希望这有点清晰。

采纳答案by Smasho

There are a few issues. The if dialog.exec_():line will only succeed if the dialog is exited with accept(). Are you working with QDesigner? If so, check thisfor a different way of working. If Ui_ShowGroupWidgetjust contain code you write, you should make it inherit QDialog instead of QWidget. Then, instead of closing it with self.close(), you close it with self.accept(). You can't return a diccionary, but you can save it as an object attribute. Once the dialog.exec_()returns, you can access that attribute.

有几个问题。if dialog.exec_():只有当对话框以 退出时,该行才会成功accept()。您在使用 QDesigner 吗?如果是这样,请检查以获取不同的工作方式。如果Ui_ShowGroupWidget只包含你编写的代码,你应该让它继承 QDialog 而不是 QWidget。然后,不是用 关闭它,而是用self.close()关闭它self.accept()。您不能返回字典,但可以将其保存为对象属性。一旦dialog.exec_()返回,您就可以访问该属性。

It could be something like this:

它可能是这样的:

def ShowGroupROIFunction(self):
    dialog = SGROIWidget_ui.Ui_ShowGroupWidget()
    if dialog.exec_():
        print(dialog.roiGroups)

The other one:

另一个:

...

class Ui_ShowGroupWidget(QtGui.QDialog):
    def __init__(self):
        QtGui.QDialog.__init__(self)
        self.setupUi(self)
        self.roiGroups = {}
        self.Submit.clicked.connect(self.submitclose)

    def setupUi(self, ShowGroupWidget):
        #sets up Submit button

    def submitclose(self):
        #do whatever you need with self.roiGroups    
        self.accept()

At last, if __name__=='__main__':means "if this file is executed as the main file, then..", which is not the case as you are including and using it from another one. So you can remove it, however, the idea is that you can run python ui_mywidget.pyin order to test it or see the Ui defined on that file

最后,if __name__=='__main__':意思是“如果这个文件作为主文件执行,那么..”,情况并非如此,因为您从另一个文件中包含和使用它。所以你可以删除它,但是,这个想法是你可以运行python ui_mywidget.py以测试它或查看该文件上定义的 Ui