使用 PyGtk 时 GUI 未从另一个线程更新
我正在使用 PyGTK 构建 GUI 应用程序。我想从另一个线程更新文本视图小部件,但每次我尝试更新时该小部件都没有更新。我应该怎么做才能获得可靠的 GUI 更新?
I am using PyGTK to build a GUI application. I want to update the textview widget from another thread but the widget is not getting updated everytime i try an update. What should i do to get a reliable GUI updating?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
GTK+ 不是线程安全的,因此您不应该简单地从其他线程调用 GUI 更新方法。 glib.idle_add (或 gobject.idle_add在较旧的 PyGTK 版本中)可用于此目的。
不要写:,而是
写::
这会导致函数调用在 GTK+ 中排队。
如果您需要运行多个语句,将它们包装在一个函数中通常更容易:
确保传递给
idle_add
的函数不返回True
;否则会再次排队。编辑:正如 Daniel 指出的,您需要首先在程序中的任何位置调用
gtk.gdk.threads_init()
。GTK+ is not thread-safe, so you should not simply call GUI update methods from other threads. glib.idle_add (or gobject.idle_add in older PyGTK versions) can be used for this purpose.
Instead of writing:
you would write:
which causes the function call to be queued in GTK+.
If you need to run multiple statements, it's often easier to wrap them in a function:
Make sure that the function passed to
idle_add
does not returnTrue
; otherwise it will be queued again.Edit: As Daniel pointed out, you need to call
gtk.gdk.threads_init()
anywhere in your program first.正如前面的答案所述,GTK 不是“线程安全”的,但它是“线程感知的” - 请参阅有关线程的此页面: https://developer.gnome.org/gdk2/stable/gdk2-Threads.html
为了从另一个线程修改 GTK 小部件,您必须使用GTK的锁定。导入 gtk 模块后立即调用 gtk.threads_init() ,然后您可以像这样更新:
请注意,上述内容在 Windows 上不起作用(请参阅上面的链接)。在 Windows 上,您必须按照上面的说明使用
gobject.idle_add()
,不过不要忘记在代码中导入 gobject 后直接放置gobject.threads_init()
! idle_add() 函数将在主线程(运行 gtk.main() 的线程)中执行更新本身。As stated in the previous answers, GTK is not "thread safe," but it is "thread-aware" - see this page on Threads: https://developer.gnome.org/gdk2/stable/gdk2-Threads.html
In order to modify GTK widgets from another thread you have to use GTK's locking. Call
gtk.threads_init()
immediately after importing the gtk module, and then you can update like so:Note that the above will not work on Windows (see the link above). On Windows you must use
gobject.idle_add()
as explained above, though don't forget to putgobject.threads_init()
directly after importing gobject in your code! The idle_add() function will execute the update itself in the main thread (the thread running gtk.main()).使用 gobject.idle_add 方法可以实现相同的效果,其语法与上面相同,您必须导入模块 gobject
the same may be achieved using gobject.idle_add method whose syntax is same as above,you have to import the module gobject
Johannes 所说的是正确的,但是由于 GTK 是 glib 和 gobject 事物的包装器,因此您实际上需要使用 gtk.idle_add()。不需要不必要的进口。
What Johannes said is correct, however since GTK is a wrapper for the glib and gobject things, you would actually want to use gtk.idle_add(). No need for the unnecessary imports.