wxPython-自动关闭嵌套模式对话框

亚当·桑德斯

Python 2.7,WxPython 3.0.2

我们正在尝试在某些条件下自动关闭整个程序。由于各种原因,我们不能仅仅终止进程。我们已经取得了一定程度的成功。如果没有模式对话框或单个模式对话框,我们可以将其关闭。一旦引入第二个模式对话框(嵌套),它就无法正确停止。

收到的实际错误似乎是:

wx._core.PyAssertionError: C++ assertion "IsRunning()" failed at ..\..\src\common\evtloopcmn.cpp(83) in wxEventLoopBase::Exit(): Use ScheduleExit() on not running loop

这是我们问题的一个有效例子。框架将在5秒钟后自动关闭。单击该按钮将加载一个对话框。单击对话框上的按钮将打开另一个对话框。在打开最后一个对话框之前,它工作正常。

from threading import Thread
from time import sleep
import wx


class MainFrame(wx.Frame):
    def __init__(self):
        wx.Frame.__init__(self, None, title="TEST", size=(400, 400))
        self.Show()
        self.__someDialog = None
        self.__myThread = None

        self.__okButton = wx.Button(self, -1, "Press me")
        self.Bind(wx.EVT_BUTTON, self.__onOK)

        self.__myThread = Thread(target=self.__waitThenClose, name="Closer")
        self.__myThread.setDaemon(True)
        self.__myThread.start()

    def __onOK(self, evt):
        self.__someDialog = SomeDialog(self)
        self.__someDialog.ShowModal()

    def closeOpenDialogs(self):
        lst = wx.GetTopLevelWindows()

        for i in range(len(lst) - 1, 0, -1):
            if isinstance(lst[i], wx.Dialog):
                print "Closing " + str(lst[i])
                lst[i].Close(True)
                #lst[i].Destroy()

    def __waitThenClose(self):

        for x in range(0, 5):
            print "Sleeping..."
            sleep(1)

        self.closeOpenDialogs()
        wx.CallAfter(self.Close, True)


class SomeDialog(wx.Dialog):
    def __init__(self, parent):
        wx.Dialog.__init__(self, parent, id=-1, title='Some Dialog')
        self.SetSize((300, 300))
        self.__anotherDialog = None
        self.__okButton = wx.Button(self, -1, "Press me")

        self.Bind(wx.EVT_BUTTON, self.__onOK)
        wx.EVT_CLOSE(self, self.__on_btn_cancel)

    def __onOK(self, evt):
        self.__anotherDialog = AnotherDialog(self)
        self.__anotherDialog.ShowModal()

    def __on_btn_cancel(self, event):
        self.EndModal(wx.ID_CANCEL)


class AnotherDialog(wx.Dialog):
    def __init__(self, parent):
        wx.Dialog.__init__(self, None, id=-1, title='Another Dialog')
        self.SetSize((200, 200))
        wx.EVT_CLOSE(self, self.__on_btn_cancel)

    def __on_btn_cancel(self, event):
        self.EndModal(wx.ID_CANCEL)


if __name__ == "__main__":

    app = wx.App()

    mainFrame = MainFrame()

    app.MainLoop()
用户2682863

我认为这里发生的是,第一次调用ShowModal()在应用程序级别(而不仅仅是框架级别)阻止,这阻止了第二个对话框完全初始化。要变通解决此问题,我将Show()代替ShowModal()并添加wx.FRAME_FLOAT_ON_PARENT到对话框样式标志中。您也可以Disable()在对话框打开时调用您不希望用户与之交互的程序部分。

编辑:这是一个工作示例:

from threading import Thread
from time import sleep
import wx


class MainFrame(wx.Frame):
    def __init__(self):
        wx.Frame.__init__(self, None, title="TEST", size=(400, 400))
        self.Show()
        self.__someDialog = None
        self.__myThread = None

        self.__okButton = wx.Button(self, -1, "Press me")
        self.Bind(wx.EVT_BUTTON, self.__onOK)

        self.__myThread = Thread(target=self.__waitThenClose, name="Closer")
        self.__myThread.setDaemon(True)
        self.__myThread.start()

    def __onOK(self, evt):
        self.__someDialog = SomeDialog(self)
        self.__someDialog.ShowModal()

    def closeOpenDialogs(self, evt=None):
        lst = wx.GetTopLevelWindows()

        for i in range(len(lst) - 1, 0, -1):
            dialog = lst[i]
            if isinstance(dialog, wx.Dialog):
                print "Closing " + str(dialog)
                # dialog.Close(True)
                wx.CallAfter(dialog.Close)
                # sleep(1)
                # dialog.Destroy()

    def __waitThenClose(self):

        for x in range(0, 10):
            print "Sleeping..."
            sleep(1)

        wx.CallAfter(self.closeOpenDialogs)
        wx.CallAfter(self.Close, True)


class SomeDialog(wx.Dialog):
    def __init__(self, parent):
        wx.Dialog.__init__(self, parent, id=-1, title='Some Dialog')
        self.SetSize((300, 300))
        self.__anotherDialog = None
        self.__okButton = wx.Button(self, -1, "Press me")

        self.Bind(wx.EVT_BUTTON, self.__onOK)
        wx.EVT_CLOSE(self, self.__on_btn_cancel)

    def __onOK(self, evt):
        self.__anotherDialog = AnotherDialog(self)
        self.__anotherDialog.SetWindowStyleFlag(wx.FRAME_FLOAT_ON_PARENT|wx.DEFAULT_DIALOG_STYLE)
        self.__anotherDialog.Show()

    def __on_btn_cancel(self, event):
        event.Skip()
        self.EndModal(wx.ID_CANCEL)


class AnotherDialog(wx.Dialog):
    def __init__(self, parent):
        wx.Dialog.__init__(self, parent, id=-1, title='Another Dialog')
        self.SetSize((200, 200))
        wx.EVT_CLOSE(self, self.__on_btn_cancel)
        parent.Disable()

    def __on_btn_cancel(self, event):
        event.Skip()
        self.GetParent().Enable()
        # self.EndModal(wx.ID_CANCEL)


if __name__ == "__main__":

    app = wx.App()

    mainFrame = MainFrame()

    app.MainLoop()

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章

来自分类Dev

如何停止用Cmd + C关闭的wxPython对话框

来自分类Dev

WXPYTHON自定义对话框

来自分类Dev

wxpython 中的打印对话框错误

来自分类Dev

wxPython:如果销毁模式对话框,则无法使用wx.PostEvent设置焦点

来自分类Dev

Wxpython在主机启动时显示对话框

来自分类Dev

Wxpython在主机启动时显示对话框

来自分类Dev

wxPython-显示打印在第三个对话框上的两个对话框中的文本

来自分类Dev

wxPython,创建设置对话框的有效方法

来自分类Dev

如何使用wxPython构造一个交互式对话框?

来自分类Dev

WxPython:在面板中嵌套面板

来自分类Dev

wxPython StaticText转义嵌套BoxSizer

来自分类Dev

在wxPython中自动安排面板

来自分类Dev

在wxPython中自动安排面板

来自分类Dev

如何使文本对话框出现在wxpython中

来自分类Dev

防止纸张对话框自动关闭

来自分类Dev

如何自动关闭对话框?

来自分类Dev

Mahapps Metro:在窗口底部显示非模式自动关闭消息对话框

来自分类Dev

wxPython:为什么无模非模态对话框会保留在父窗口的顶部?

来自分类Dev

Qt:关闭模式对话框关闭程序

来自分类Dev

无法在Mac上关闭wxPython窗口

来自分类Dev

如何使wxpython网格自动适合窗口

来自分类Dev

wxPython:添加一个关于框。

来自分类Dev

mdc 关闭所有嵌套对话框而不是活动对话框

来自分类Dev

如何关闭和删除无模式qt对话框

来自分类Dev

在按钮单击事件上关闭模式对话框

来自分类Dev

在Sitecore 7.1中关闭模式对话框?

来自分类Dev

jQuery完全关闭引导程序模式对话框

来自分类Dev

关闭和重置一个模式对话框

来自分类Dev

验证失败应防止关闭模式对话框

Related 相关文章

热门标签

归档