MODULE test_popover ; (* m2-GTK4 test - GtkPopover, GtkPopoverMenu and GtkMenuButton popovers. Presents a window, then (from a timeout, once widgets are mapped) opens and closes a popover. Requires a display. *) FROM Gio IMPORT g_application_run, g_application_quit; FROM GtkApplication IMPORT gtk_application_new; FROM GtkWindow IMPORT gtk_application_window_new, gtk_window_set_child, gtk_window_present; FROM GtkBox IMPORT gtk_box_new, gtk_box_append; FROM GtkEnums IMPORT GtkVertical; FROM GtkButton IMPORT gtk_button_new_with_label; FROM GtkLabel IMPORT gtk_label_new; FROM GtkPopover IMPORT gtk_popover_new, gtk_popover_set_child, gtk_popover_get_child, gtk_popover_popup, gtk_popover_popdown, gtk_popover_set_autohide, gtk_popover_get_autohide, gtk_popover_set_has_arrow, gtk_popover_set_offset, gtk_popover_get_offset; FROM GtkPopoverMenu IMPORT gtk_popover_menu_new_from_model, gtk_popover_menu_get_menu_model, gtk_popover_menu_set_flags, gtk_popover_menu_get_flags, GtkPopoverMenuNested; FROM GtkMenuButton IMPORT gtk_menu_button_new, gtk_menu_button_set_popover, gtk_menu_button_get_popover; FROM GtkWidget IMPORT gtk_widget_set_parent, gtk_widget_get_parent; FROM GMenu IMPORT g_menu_new, g_menu_append; FROM GtkUtils IMPORT Connect; FROM GLib IMPORT g_timeout_add, GSourceRemove; FROM SYSTEM IMPORT ADDRESS, ADR; FROM libc IMPORT printf; CONST AppId = "org.example.m2gtk4.TestPopover"; VAR app, popover: ADDRESS; passed: BOOLEAN; PROCEDURE AfterMap (data: ADDRESS) : INTEGER; BEGIN gtk_popover_popup(popover); gtk_popover_popdown(popover); g_application_quit(app); RETURN GSourceRemove END AfterMap; PROCEDURE OnActivate (application: ADDRESS; data: ADDRESS); VAR window, box, button, child, menu, pm, mb: ADDRESS; x, y: INTEGER; ok: BOOLEAN; BEGIN ok := TRUE; child := gtk_label_new("popover content"); popover := gtk_popover_new(); gtk_popover_set_child(popover, child); IF gtk_popover_get_child(popover) # child THEN ok := FALSE END; gtk_popover_set_autohide(popover, 0); IF gtk_popover_get_autohide(popover) # 0 THEN ok := FALSE END; gtk_popover_set_has_arrow(popover, 0); gtk_popover_set_offset(popover, 4, 8); gtk_popover_get_offset(popover, x, y); IF (x # 4) OR (y # 8) THEN printf("popover offset wrong\n"); ok := FALSE END; button := gtk_button_new_with_label("Open"); gtk_widget_set_parent(popover, button); IF gtk_widget_get_parent(popover) # button THEN printf("popover parent wrong\n"); ok := FALSE END; menu := g_menu_new(); g_menu_append(menu, "Item", "app.quit"); pm := gtk_popover_menu_new_from_model(menu); IF gtk_popover_menu_get_menu_model(pm) # menu THEN ok := FALSE END; gtk_popover_menu_set_flags(pm, GtkPopoverMenuNested); IF gtk_popover_menu_get_flags(pm) # GtkPopoverMenuNested THEN ok := FALSE END; mb := gtk_menu_button_new(); gtk_menu_button_set_popover(mb, pm); IF gtk_menu_button_get_popover(mb) # pm THEN printf("menu button popover wrong\n"); ok := FALSE END; box := gtk_box_new(GtkVertical, 6); gtk_box_append(box, button); gtk_box_append(box, mb); window := gtk_application_window_new(application); gtk_window_set_child(window, box); gtk_window_present(window); passed := ok; g_timeout_add(300, AfterMap, NIL) END OnActivate; VAR rc: INTEGER; BEGIN passed := FALSE; app := gtk_application_new(AppId, 0); IF app = NIL THEN printf("test_popover: FAIL (no app)\n"); HALT(1) END; Connect(app, "activate", ADR(OnActivate), NIL); rc := g_application_run(app, 0, NIL); IF passed THEN printf("test_popover: PASS\n"); HALT(0) ELSE printf("test_popover: FAIL\n"); HALT(1) END END test_popover.