【问题标题】:wxPython main thread other than 0 leads to wxWidgets Debug Alert on exitwxPython 主线程不是 0 导致 wxWidgets Debug Alert on exit
【发布时间】:2018-03-15 16:18:26
【问题描述】:

我想在控制台会话中同时使用交互式 wxPython GUI(如交互式模式下的 matplotlib)。这要求控制台继续在线程 0 上运行,并且所有 wx 交互都在单独的线程上运行。 (我很清楚只有一个线程应该访问 wx。)

我下面的演示代码可以工作(通过python -i 启动时),但是当我退出 Python(例如通过exit())时会弹出一个 wxWidgets 调试警报(看起来像一个崩溃对话框)。 wx主线程不是线程0时退出Python时如何避免提示?

import threading

class GUI(threading.Thread):
    def __init__(self):
        threading.Thread.__init__(self)
        self.daemon = True

    def run(self):
        import wx 
        app = wx.App() 
        window = wx.Frame(None, title="Hello World!", size=(200, 100)) 
        panel = wx.Panel(window) 
        text = wx.StaticText(panel, label="Hello World!", pos=(0, 0)) 
        window.Show(True) 
        app.MainLoop()     

gui_thread = GUI()
gui_thread.start()

Others 报告在旧版本的 wxPython 中使用此类策略成功,但他们的代码(案例 3)在关闭时给我与上述相同的崩溃。

我在退出时遇到的错误(可能来自自动注册的atexit 处理程序?)与您尝试从第二个线程访问 wx 时遇到的错误相同:assert "wxIsMathThread()" failed in wxSocketBase::IsInitialized(): unsafe to call from other threads [in thread 1b68]

具体来说,我在使用 Anaconda Python 3.6.3 在 Windows 10 上运行 wxPython 4.0.1(又名 Phoenix)时收到 wxWidgets 调试警报。我没有测试过其他平台和版本。

【问题讨论】:

  • 在终止进程之前,您是否正在努力结束 GUI?我认为您关于自动注册处理程序的理论可能是正确的。如果它发生在 exit() 之后,真的会崩溃吗?
  • 导入 wx 注册了两个 atexit 处理程序,所以这可能是故事的一部分。我修改了问题以显示弹出的消息被标记为“wxWidgets 调试警报”,因此可以说不是崩溃。注意:这些警报默认启用;见:docs.wxwidgets.org/trunk/…

标签: python multithreading exit wxpython


【解决方案1】:

警报来自通过导入wx 自动插入的atexit 处理程序。为了避免这种情况,同时仍然允许常规调试,可以在加载 wx 后禁用警报 atexit

import threading
import atexit

class GUI(threading.Thread):
    def __init__(self):
        threading.Thread.__init__(self)
        self.daemon = True

    def run(self):
        import wx 
        atexit.register(disable_asserts)
        app = wx.App() 
        window = wx.Frame(None, title="Hello World!", size=(200, 100)) 
        panel = wx.Panel(window) 
        text = wx.StaticText(panel, label="Hello World!", pos=(0, 0)) 
        window.Show(True) 
        app.MainLoop()

def disable_asserts():
    import wx
    wx.DisableAsserts()

gui_thread = GUI()
gui_thread.start()

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2015-08-29
    • 1970-01-01
    • 2010-11-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多