gtk idle_add没有运行?

Tha*_*tos 4 python gtk pygtk

我有一个双线程应用程序:GUI和一些后台工作.我正在尝试向主线程发送请求以进行GUI更新(移动进度条),但它似乎不起作用.我把它归结为一个非常小的例子:

import pygtk
pygtk.require('2.0')
import glib
import gtk

import threading
import sys
import time

def idle():
    sys.stderr.write('Hello from another world.\n')
    sys.stderr.flush()
    gtk.main_quit()

def another_thread():
    time.sleep(1)
    glib.idle_add(idle)

thread = threading.Thread(target=another_thread)
thread.start()
gtk.main()
Run Code Online (Sandbox Code Playgroud)

我认为,这应该从主/ GUI线程中打印出标准错误,但没有任何反应.并且它也不会退出,因此gtk.main_quit不会被调用.

此外,添加更多的输出以stderr奇怪的行为.如果我将线程的功能更改为:

sys.stderr.write('----\n')
sys.stderr.write('----\n')
sys.stderr.flush()
sys.stderr.write('After.\n')
sys.stderr.flush()
Run Code Online (Sandbox Code Playgroud)

我看到1,有时输出2行.它似乎与主线程进入某种竞争条件gtk.main,但我不知道为什么会这样.

van*_*nza 5

在多线程环境中使用glib之前,需要初始化glib的线程支持.只需致电:

glib.threads_init()
Run Code Online (Sandbox Code Playgroud)

在调用glib函数之前.


Tha*_*tos 0

以下内容使上述内容对我有用:

gtk.gdk.threads_init()在执行任何其他操作之前调用:在启动线程之前、在进入gtk.main(). 我认为实际上,这只需要在进入之前调用gtk.main(),但是调用它很容易,因为一切都是单线程且简单的。

在空闲回调(idle示例中的 )中,在 GTK 内容之前调用gtk.gdk.threads_enter()(很容易在函数顶部完成),并gtk.gdk.threads_leave()在函数结束之前调用 , 。

gtk.gdk.threads_init()似乎还告诉 PyGTK 在进入睡眠状态时不要保留 GIL - 我想我错过了 aux 的一些输出。示例中的线程只是因为睡眠主线程(睡眠中gtk.main())仍然持有 GIL。gtk.gdk.threads_init()据我所知,它为 PyGTK 和 GTK+ 注入了良好的魔力。因此,gtk.gdk.threads_init()即使您启动一个不接触 GTK+、不使用 glib、gobject 等执行任何操作、仅进行基本计算的线程,也是需要的。