I have a GtkPopoverMenuBar
with a GMenu
and another GMenu
inserted as a sub-menu. When I use the basic functionality, the basic items (non sub-menus) in both the main menu and the sub-menu appear as expected:
When I attempt to use custom widgets for both of the basic items, only the one in the main menu appears while the sub-menu item is missing:
I am calling gtk_popover_menu_bar_add_child
to add the custom widget for both of these items to the menubar. This feels maybe wrong and it would seem to explain the behavior I’m seeing. Logically, it seems like the custom widget for the item in the sub-menu should be added to a GtkPopoverMenu
with gtk_popover_menu_add_child
. However I cannot find any documentation that shows a way to get a handle to the GtkPopoverMenu
that backs the sub-menu in order to pass it to gtk_popover_menu_add_child
.
Can anyone point me toward an example of custom widgets in a GMenu sub-menu?
For reference, here is the code for the demo app above (also on github):
#include <stdio.h>
#include <gdk/gdk.h>
#include <gtk/gtk.h>
#ifdef CUSTOM_WIDGETS
GtkWidget *menu_item_widget_new(
const char *text
)
{
GtkWidget *layout = gtk_box_new(GTK_ORIENTATION_HORIZONTAL, 0);
GtkWidget *label = gtk_label_new(text);
gtk_box_append(GTK_BOX(layout), label);
gtk_widget_set_visible(layout, true);
return layout;
}
#endif
int main(
int argc,
char **argv
)
{
gtk_init();
GMenu *main_menu = g_menu_new();
GtkWidget *menubar = gtk_popover_menu_bar_new_from_model(G_MENU_MODEL(main_menu));
GMenu *file_menu = g_menu_new();
GMenuItem *file_item = g_menu_item_new_submenu("File", G_MENU_MODEL(file_menu));
g_menu_insert_item(G_MENU(gtk_popover_menu_bar_get_menu_model(GTK_POPOVER_MENU_BAR(menubar))), 0, file_item);
GMenu *recent_menu = g_menu_new();
GMenuItem *recent_item = g_menu_item_new_submenu("Recent", G_MENU_MODEL(recent_menu));
GMenuItem *filename_item = g_menu_item_new("File.txt", NULL);
#ifdef CUSTOM_WIDGETS
g_menu_item_set_attribute(filename_item, "custom", "s", "filename");
#endif
g_menu_insert_item(recent_menu, 0, filename_item);
#ifdef CUSTOM_WIDGETS
GtkWidget *filename_widget = menu_item_widget_new("CustomFile.txt");
gtk_popover_menu_bar_add_child(GTK_POPOVER_MENU_BAR(menubar), filename_widget, "filename");
#endif
g_menu_insert_item(file_menu, 0, recent_item);
GMenuItem *exit_item = g_menu_item_new("Exit", NULL);
#ifdef CUSTOM_WIDGETS
g_menu_item_set_attribute(exit_item, "custom", "s", "exit");
#endif
g_menu_insert_item(file_menu, 1, exit_item);
#ifdef CUSTOM_WIDGETS
GtkWidget *exit_widget = menu_item_widget_new("Custom Exit");
gtk_popover_menu_bar_add_child(GTK_POPOVER_MENU_BAR(menubar), exit_widget, "exit");
#endif
g_free(exit_item);
g_free(file_item);
g_free(filename_item);
g_free(recent_item);
GtkWidget *mainwin = gtk_window_new();
GtkWidget *win_layout = gtk_box_new(GTK_ORIENTATION_VERTICAL, 0);
gtk_box_append(GTK_BOX(win_layout), menubar);
gtk_window_set_child(GTK_WINDOW(mainwin), win_layout);
gtk_window_present(GTK_WINDOW(mainwin));
while (g_list_model_get_n_items(gtk_window_get_toplevels()) > 0)
g_main_context_iteration(NULL, TRUE);
return 0;
}