--- a/ui/gtk/headerbar.c Sat Jun 13 12:03:09 2026 +0200 +++ b/ui/gtk/headerbar.c Sat Jun 13 14:12:43 2026 +0200 @@ -30,6 +30,9 @@ #include "button.h" #include "menu.h" +#include "../ui/widget.h" + +#include <cx/array_list.h> #include "../ui/properties.h" @@ -66,53 +69,63 @@ } // main toolbar - ui_headerbar_add_items(obj, main_headerbar, left_defaults, UI_TOOLBAR_LEFT); - ui_headerbar_add_items(obj, main_headerbar, center_defaults, UI_TOOLBAR_CENTER); + ui_headerbar_add_items(obj, main_headerbar, left_defaults, UI_TOOLBAR_LEFT, NULL); + ui_headerbar_add_items(obj, main_headerbar, center_defaults, UI_TOOLBAR_CENTER, NULL); if(appmenu && appmenu_pos == UI_TOOLBAR_RIGHT) { ui_add_headerbar_menu(main_headerbar, NULL, appmenu, obj, UI_TOOLBAR_RIGHT); } - ui_headerbar_add_items(obj, main_headerbar, right_defaults, UI_TOOLBAR_RIGHT); + ui_headerbar_add_items(obj, main_headerbar, right_defaults, UI_TOOLBAR_RIGHT, NULL); // sidebar if(sidebar_headerbar) { // ui_headerbar_add_items pos parameter uses only UI_TOOLBAR_LEFT, UI_TOOLBAR_CENTER, UI_TOOLBAR_RIGHT - ui_headerbar_add_items(obj, sidebar_headerbar, sidebar_left_defaults, UI_TOOLBAR_LEFT); + ui_headerbar_add_items(obj, sidebar_headerbar, sidebar_left_defaults, UI_TOOLBAR_LEFT, NULL); if(appmenu && appmenu_pos == UI_TOOLBAR_SIDEBAR_RIGHT) { ui_add_headerbar_menu(sidebar_headerbar, NULL, appmenu, obj, UI_TOOLBAR_RIGHT); } - ui_headerbar_add_items(obj, sidebar_headerbar, sidebar_right_defaults, UI_TOOLBAR_RIGHT); + ui_headerbar_add_items(obj, sidebar_headerbar, sidebar_right_defaults, UI_TOOLBAR_RIGHT, NULL); } // right panel if(right_headerbar) { - ui_headerbar_add_items(obj, right_headerbar, rightpanel_left_defaults, UI_TOOLBAR_LEFT); - ui_headerbar_add_items(obj, right_headerbar, rightpanel_center_defaults, UI_TOOLBAR_CENTER); + // also add central toolbar items, in case the central pane is hidden + CxList *backup_toolbar_widgets = cxArrayListCreate(obj->ctx->allocator, CX_STORE_POINTERS, 16); + ui_headerbar_add_items(obj, right_headerbar, left_defaults, UI_TOOLBAR_LEFT, backup_toolbar_widgets); + ui_headerbar_add_items(obj, right_headerbar, center_defaults, UI_TOOLBAR_LEFT, backup_toolbar_widgets); + ui_headerbar_add_items(obj, right_headerbar, right_defaults, UI_TOOLBAR_LEFT, backup_toolbar_widgets); + CxIterator i = cxListIterator(backup_toolbar_widgets); + cx_foreach(GtkWidget *, w, i) { + ui_set_visible(w, FALSE); + } + g_object_set_data(G_OBJECT(obj->widget), "ui_toolbar_center_backup", backup_toolbar_widgets); + + // main items for the right panel + ui_headerbar_add_items(obj, right_headerbar, rightpanel_left_defaults, UI_TOOLBAR_LEFT, NULL); + ui_headerbar_add_items(obj, right_headerbar, rightpanel_center_defaults, UI_TOOLBAR_CENTER, NULL); if(appmenu && appmenu_pos == UI_TOOLBAR_RIGHTPANEL_RIGHT) { ui_add_headerbar_menu(right_headerbar, NULL, appmenu, obj, UI_TOOLBAR_RIGHT); } - ui_headerbar_add_items(obj, right_headerbar, rightpanel_right_defaults, UI_TOOLBAR_RIGHT); + ui_headerbar_add_items(obj, right_headerbar, rightpanel_right_defaults, UI_TOOLBAR_RIGHT, NULL); } } -static void create_item(UiObject *obj, GtkWidget *headerbar, GtkWidget *box, UiToolbarItemI *i, enum UiToolbarPos pos) { +static GtkWidget* create_item(UiObject *obj, GtkWidget *headerbar, GtkWidget *box, UiToolbarItemI *i, enum UiToolbarPos pos) { switch(i->type) { case UI_TOOLBAR_ITEM: { - ui_add_headerbar_item(headerbar, box, (UiToolbarItem*)i, obj, pos); - break; + return ui_add_headerbar_item(headerbar, box, (UiToolbarItem*)i, obj, pos); } case UI_TOOLBAR_TOGGLEITEM: { - ui_add_headerbar_toggleitem(headerbar, box, (UiToolbarToggleItem*)i, obj, pos); - break; + return ui_add_headerbar_toggleitem(headerbar, box, (UiToolbarToggleItem*)i, obj, pos); } case UI_TOOLBAR_MENU: { - ui_add_headerbar_menu(headerbar, box, (UiToolbarMenuItem*)i, obj, pos); - break; + return ui_add_headerbar_menu(headerbar, box, (UiToolbarMenuItem*)i, obj, pos); } default: fprintf(stderr, "toolbar item type unimplemented: %d\n", (int)i->type); } + return NULL; } static void headerbar_add(GtkWidget *headerbar, GtkWidget *box, GtkWidget *item, enum UiToolbarPos pos) { @@ -137,12 +150,15 @@ } } -void ui_headerbar_add_items(UiObject *obj, GtkWidget *headerbar, CxList *items, enum UiToolbarPos pos) { +void ui_headerbar_add_items(UiObject *obj, GtkWidget *headerbar, CxList *items, enum UiToolbarPos pos, CxList *out_items) { GtkWidget *box = NULL; if(pos == UI_TOOLBAR_CENTER && cxListSize(items) > 0) { box = gtk_box_new(GTK_ORIENTATION_HORIZONTAL, 6); UI_HEADERBAR_SET_TITLE_WIDGET(headerbar, box); + if(out_items) { + cxListAdd(out_items, box); + } } CxIterator i = pos == UI_TOOLBAR_RIGHT ? cxListBackwardsIterator(items) : cxListIterator(items); @@ -152,11 +168,14 @@ fprintf(stderr, "unknown toolbar item: %s\n", def); continue; } - create_item(obj, headerbar, box, item, pos); + GtkWidget *item_widget = create_item(obj, headerbar, box, item, pos); + if(out_items && !box) { + cxListAdd(out_items, item_widget); + } } } -void ui_add_headerbar_item( +GtkWidget* ui_add_headerbar_item( GtkWidget *headerbar, GtkWidget *box, UiToolbarItem *item, @@ -168,9 +187,10 @@ ui_set_widget_visibility_states(obj->ctx, button, item->args.visibility_states); WIDGET_ADD_CSS_CLASS(button, "flat"); headerbar_add(headerbar, box, button, pos); + return button; } -void ui_add_headerbar_toggleitem( +GtkWidget* ui_add_headerbar_toggleitem( GtkWidget *headerbar, GtkWidget *box, UiToolbarToggleItem *item, @@ -183,9 +203,10 @@ WIDGET_ADD_CSS_CLASS(button, "flat"); ui_setup_togglebutton(obj, button, item->args.label, item->args.icon, item->args.tooltip, item->args.varname, NULL, item->args.onchange, item->args.onchangedata, item->args.action, 0); headerbar_add(headerbar, box, button, pos); + return button; } -void ui_add_headerbar_menu( +GtkWidget* ui_add_headerbar_menu( GtkWidget *headerbar, GtkWidget *box, UiToolbarMenuItem *item, @@ -222,6 +243,8 @@ #endif headerbar_add(headerbar, box, menubutton, pos); + + return menubutton; } #endif // GTK_CHECK_VERSION(3, 10, 0)