Fri, 17 Oct 2025 20:18:29 +0200
implement sourcelist item popup menu (GTK)
| application/main.c | file | annotate | diff | comparison | revisions | |
| ui/gtk/list.c | file | annotate | diff | comparison | revisions |
--- a/application/main.c Fri Oct 17 16:02:56 2025 +0200 +++ b/application/main.c Fri Oct 17 20:18:29 2025 +0200 @@ -460,6 +460,7 @@ } UiMenuBuilder *menubuilder; +UiMenuBuilder *sourcelist_menu; void* table_getvalue(void *row, int col) { switch(col) { @@ -501,6 +502,7 @@ void sourcelist_getvalue(UiList *list, void *sublistdata, void *rowdata, int index, UiSubListItem *item, void *userdata) { item->label = strdup(rowdata); item->button_icon = strdup("view-more-horizontal"); + item->button_menu = sourcelist_menu; item->eventdata = sublistdata; } @@ -832,6 +834,11 @@ } } + ui_contextmenu(&sourcelist_menu) { + ui_menuitem(.label = "Item 1"); + ui_menuitem(.label = "Item 2"); + } + ui_menu("Edit") { ui_menuitem(.label = "Undo"); ui_menuseparator();
--- a/ui/gtk/list.c Fri Oct 17 16:02:56 2025 +0200 +++ b/ui/gtk/list.c Fri Oct 17 20:18:29 2025 +0200 @@ -2301,7 +2301,7 @@ } } -static void listbox_button_clicked(GtkWidget *widget, UiEventDataExt *data) { +static void listbox_button_clicked(GtkWidget *button, UiEventDataExt *data) { UiListBoxSubList *sublist = data->customdata0; UiSubListEventData eventdata; @@ -2324,8 +2324,24 @@ if(data->callback2) { data->callback2(&event, data->userdata2); } + + if(data->customdata3) { + UIMENU menu = data->customdata3; + g_object_set_data(G_OBJECT(button), "ui-button-popup", menu); + gtk_popover_popup(GTK_POPOVER(menu)); + } } +#if GTK_CHECK_VERSION(3, 0, 0) +static void button_popover_closed(GtkPopover *popover, GtkWidget *button) { + g_object_set_data(G_OBJECT(button), "ui-button-popup", NULL); + if(g_object_get_data(G_OBJECT(button), "ui-button-invisible")) { + g_object_set_data(G_OBJECT(button), "ui-button-invisible", NULL); + gtk_widget_set_visible(button, FALSE); + } +} +#endif + static void listbox_fill_row(UiListBox *listbox, GtkWidget *row, UiListBoxSubList *sublist, UiSubListItem *item, int index) { UiBool is_header = index < 0; @@ -2398,6 +2414,13 @@ gtk_widget_set_visible(button, FALSE); g_object_set_data(G_OBJECT(row), "ui-listbox-row-button", button); + + // menu + if(item->button_menu) { + UIMENU menu = ui_contextmenu_create(item->button_menu, listbox->obj, button); + event->customdata3 = menu; + g_signal_connect(menu, "closed", G_CALLBACK(button_popover_closed), button); + } } } @@ -2441,8 +2464,12 @@ static void listbox_row_on_leave(GtkWidget *row) { GtkWidget *button = g_object_get_data(G_OBJECT(row), "ui-listbox-row-button"); - if(button) { - gtk_widget_set_visible(button, FALSE); + if(button) { + if(!g_object_get_data(G_OBJECT(button), "ui-button-popup")) { + gtk_widget_set_visible(button, FALSE); + } else { + g_object_set_data(G_OBJECT(button), "ui-button-invisible", (void*)1); + } } }