我正在创建一个新的GTK应用程序(使用gtkmm),主界面是标签式的,有点像网络浏览器。
我想为用户打开的每个文档创建一个新选项卡,每个选项卡的内容由Glade定义。我是gtkmm的新手,所以我不知道该怎么做。
如果我将Glade中的标签设计为一个独立的窗口,当我调用Gtk::Builder::get_widget()
时,它会返回指向Gtk::Window
的指针,但我无法将其传递给Gtk::Notebook::append_page()
因为该函数需要引用而我只有一个指针。我不想取消引用指针,因为我相信对get_widget()
的每次调用都返回相同的指针 - 所以如果我想要添加相同的五个页面,我需要以某种方式克隆UI结构,然后再将其添加到Gtk::Notebook
- 否则更改一个选项卡上的UI元素将导致其在其他四个选项卡上更改,因为它们都指向相同的UI小部件。
使用Glade设计的窗口并将其多次动态添加到Gtk::Notebook
的最佳方法是什么?
修改
将每个标签的定义放在一个单独的*.glade
文件中,这样我就可以加载多个实例,这样这部分就可以了。
但是我仍然无法将加载的结构添加到Gtk::Notebook
:
Gtk::Builder::get_widget()
从Gtk::Window
文件中检索根.glade
并将其添加为新标签,则无法编译,因为我必须传递{{1}转到Gtk::Widget
并且它不会接受append_page()
参数。如果我告诉它选择最顶级的小部件,那么我会遇到一堆运行时错误:
Gtk::Window
如果我选择最顶层的窗口小部件,而是调用Can't set a parent on widget which has a parent
gtkcontainer.c:858: container class `gtkmm__GtkWindow' has no child property named `tab-expand'
gtkcontainer.c:858: container class `gtkmm__GtkWindow' has no child property named `tab-fill'
gtkcontainer.c:858: container class `gtkmm__GtkWindow' has no child property named `tab-label'
gtkcontainer.c:858: container class `gtkmm__GtkWindow' has no child property named `menu-label'
gtkcontainer.c:858: container class `gtkmm__GtkWindow' has no child property named `position'
Gtk:ERROR:gtkcontainer.c:3541:gtk_container_propagate_draw: assertion failed: (gtk_widget_get_parent (child) == GTK_WIDGET (container))
Aborted (core dumped)
并将reparent()
作为新父窗口传递,则新选项卡会显示正确排列的所有窗口小部件,但随后我无法控制标签的标题。
必须有一种'正确'的方法来做到这一点,我只是无法弄清楚它是什么!
答案 0 :(得分:1)
感谢gtkmm
邮件列表的帮助,我有了解决方案。
在Glade中,我创建了一个Gtk::Window
,其中包含一个Gtk::Box
,并将所有控件都放在Box
中。这在尝试将Box
添加为新标签时会出现问题,因为Box
已经有父级(Gtk::Window
),所以尝试制作Gtk::Notebook
很麻烦新的父母。
相反,我发现您可以右键单击Glade中Gtk::Box
的按钮,然后选择"添加小部件作为顶级"。因此,根本不需要Gtk::Window
,并且由于Box
没有父级,因此调用Gtk::Notebook::append_page()
并传递Gtk::Box
可以完美地运行。然后,我可以使用append_page()
的变体,让我同时设置标签的标题。
然而,仍然需要创建一个新的Gtk::Builder
实例来加载每个选项卡的控件,因为每个选项卡都需要一个新的控件实例。如果你只是在同一个对象上调用Gtk::Builder::get_widget()
,它将返回相同的控件实例。