pygtk中的线程有问题。我的应用程序包含一个程序,可以从互联网上下载图片,然后用pygtk显示它。问题是,为了做到这一点并保持GUI响应,我需要使用线程。
所以我在用户点击“下载图片”按钮后进入回调,然后我调用该方法下载同一类中的图片。
thread.start_new_thread(self.images_download,(path,pages)
这不起作用。我让程序进入线程的唯一方法是使用
gtk.threads_init()
在开始任何线程之前。现在它下载图片但GUI仍然没有响应。 我用Google搜索了一下,我尝试将gtk.threads_enter和gtk.threads_leave放在线程周围,但它不起作用。
答案 0 :(得分:12)
你的问题有点模糊,如果没有参考你的实际代码,就很难推测你做错了什么。
所以我会给你一些阅读的指示,然后根据经验疯狂推测。
首先,您似乎认为只能通过使用线程来保持GUI响应。这不是真的。您还可以异步编写代码,并在单线程应用程序中执行所有操作。 Twisted建立在此编程模型之上。我最近made a blog post解释了我如何创建异步任务接口,以及CLI和GTK +的示例运行器。您可以查看这些示例,了解如何异步实现任务,并且UI仍然会更新。
其次,如果您因某些原因喜欢使用线程,则需要稍微了解GTK +线程模型。
您应首先阅读The PyGTK FAQ entry on the subject,您可能会发现this blog post也很容易理解。
现在,关于猜测。我猜你正在尝试从线程更新你的GTK UI,而不是正确处理锁定。如果是这种情况,那么现在最好通过使用gobject.idle_add()将您想要做的所有UI更新从线程推迟到主线程。这样,所有UI调用都将从主线程进行。在你的编程中,这是一个更容易理解的心智模型。
一旦您认为自己真正理解了线程和锁定模型,就可以考虑从线程更新UI,但很容易错过threads_enter()/ threads_leave()
答案 1 :(得分:1)
您可以使用gtk.gdk.threads_init()以允许任何线程使用尊重的gtk.gdk.threads_enter()和gtk.gdk.theads_leave()锁定修改UI,但是,这个问题是在Windows上不能很好地工作。我已经在Linux上测试了它并且表现相当不错,但我没有运气让它在win32上工作。
===编辑===
我一直在浏览这个,你可以利用gobject.io_add_watch检查套接字中是否有东西,抓住它然后更新GUI。查看我的帖子: Sockets (and some other files) and PyGTK without threads.