编程语言
首页 > 编程语言> > 如何在Python,GTK3和PyGObject中部署GtkWidget?

如何在Python,GTK3和PyGObject中部署GtkWidget?

作者:互联网

我正在为GTK3程序创建一个插件.可以在运行时启用或禁用此插件.启用后,它应在主程序中的给定区域(GtkBin)中填充其GUI.禁用时,它应该从该区域中删除.

这个简单的程序描述了用法:

#!/usr/bin/python2

from gi.repository import Gtk

window = Gtk.Window()

class Plugin(object):
    def __init__(self, host):
        assert(isinstance(host, Gtk.Bin))
        self.host = host
        self.guest = None

    def enable(self):
        box = Gtk.Box(orientation = Gtk.Orientation.VERTICAL)
        for x in range(10):
            box.add(Gtk.Button("Button {}".format(x)))

        self.guest = box
        self.host.add(self.guest)

    def disable(self):
        self.host.remove(self.guest)
        # self.guest.destroy() # is this better?
        self.guest = None

plugin = Plugin(window)

plugin.enable()
#plugin.disable()

window.connect("destroy", Gtk.main_quit)
window.show_all()

Gtk.main()

我希望在禁用插件时,应该正确处理它添加到主机的所有小部件.

我发现这个问题非常相似:Free object/widget in GTK?它提出了gtk_container_remove和gtk_widget_destroy.但我担心的是:

>考虑gtk_container_remove.它删除了主机容器的直接子节点.就我而言,孩子也是许多其他小部件的组合,他们可能互相引用.是否会删除直接的孩子,以便处理所有小部件?
>考虑gtk_widget_destroy.它是递归的,似乎是我需要的,但也似乎太残酷了.这是否真的需要手动销毁小部件?将这份工作留给参考柜台会更好吗?

我愿意听到这个案子的“最佳做法”.

解决方法:

最佳做法是永远不要依赖垃圾收集器来收集及时控制有限资源的对象.它可以无限期地延迟收集任何特定的垃圾.您不希望为垃圾收集器打开文件以进行清理,因为您可以立即打开的文件句柄数量有限制.

碰巧Python的垃圾收集器有一个引用计数器,并且会立即释放没有引用的对象,但这是一个实现细节.如果您使用其他实现,例如PyPy或IronPython,则不适用.当我将它移动到另一个实现时,我有一个程序中断,因为我无意中依赖Python的引用计数来清理资源.此外,您最终可能会因为意外在某处创建循环而发生错误.

我不知道具体的小部件的任何最佳实践.我没有考虑过我应该清理它们的可能性.如果一个小部件有一个与之关联的窗口,那么理论上应该清理一个OS句柄.通常,只有GtkWindow会有一个真实的窗口,但是你的插件可能会创建一个带窗口的窗口小部件.所以,我会说,在一个特定的不太可能的情况下,你理论上应该销毁小部件.否则,如果你不需要它们,可以手动销毁它们,但我会说不要这么做.

标签:python,pygobject,gtk3
来源: https://codeday.me/bug/20190630/1334467.html