summaryrefslogtreecommitdiff
path: root/examples
diff options
context:
space:
mode:
authorRyan Lortie <desrt@desrt.ca>2012-08-24 14:11:37 -0400
committerRyan Lortie <desrt@desrt.ca>2012-09-17 12:31:21 -0400
commit338b5f6c2dc6cdb73ec3dfb6973b2269d4664b80 (patch)
treeebde40d433cf55e01be7a5f46d4f5a4a3e9ac22d /examples
parent9480e215062dc8d0319414bc96bab60e85b7f7a0 (diff)
downloadgtk+-338b5f6c2dc6cdb73ec3dfb6973b2269d4664b80.tar.gz
GtkModelMenuItem: add a submenu action attribute
Add support for a stateful action associated with a submenu. The action state is set to TRUE when the menu is shown and FALSE when it is unshown. This is useful to avoid unnecessary processing for menus that have frequently-changing content. A possible future feature is to add support for asynchronously filling the initial state of the menu by waiting until the action actually emits its state-change signal to TRUE before showing the menu. A silly example has been added to Bloatpad to demonstrate the new feature. https://bugzilla.gnome.org/show_bug.cgi?id=682630
Diffstat (limited to 'examples')
-rw-r--r--examples/bloatpad.c82
1 files changed, 80 insertions, 2 deletions
diff --git a/examples/bloatpad.c b/examples/bloatpad.c
index 537b9d7091..fc8e263e1c 100644
--- a/examples/bloatpad.c
+++ b/examples/bloatpad.c
@@ -191,7 +191,14 @@ bloat_pad_open (GApplication *application,
new_window (application, files[i]);
}
-typedef GtkApplication BloatPad;
+typedef struct
+{
+ GtkApplication parent_instance;
+
+ GMenu *time;
+ guint timeout;
+} BloatPad;
+
typedef GtkApplicationClass BloatPadClass;
G_DEFINE_TYPE (BloatPad, bloat_pad, GTK_TYPE_APPLICATION)
@@ -234,15 +241,65 @@ quit_activated (GSimpleAction *action,
g_application_quit (app);
}
+static gboolean
+update_time (gpointer user_data)
+{
+ BloatPad *bloatpad = user_data;
+ GDateTime *now;
+ gchar *time;
+
+ while (g_menu_model_get_n_items (G_MENU_MODEL (bloatpad->time)))
+ g_menu_remove (bloatpad->time, 0);
+
+ g_message ("Updating the time menu (which should be open now)...");
+
+ now = g_date_time_new_now_local ();
+ time = g_date_time_format (now, "%c");
+ g_menu_append (bloatpad->time, time, NULL);
+ g_date_time_unref (now);
+ g_free (time);
+
+ return G_SOURCE_CONTINUE;
+}
+
+static void
+time_active_changed (GSimpleAction *action,
+ GVariant *state,
+ gpointer user_data)
+{
+ BloatPad *bloatpad = user_data;
+
+ if (g_variant_get_boolean (state))
+ {
+ if (!bloatpad->timeout)
+ {
+ bloatpad->timeout = g_timeout_add (1000, update_time, bloatpad);
+ update_time (bloatpad);
+ }
+ }
+ else
+ {
+ if (bloatpad->timeout)
+ {
+ g_source_remove (bloatpad->timeout);
+ bloatpad->timeout = 0;
+ }
+ }
+
+ g_simple_action_set_state (action, state);
+}
+
static GActionEntry app_entries[] = {
{ "new", new_activated, NULL, NULL, NULL },
{ "about", about_activated, NULL, NULL, NULL },
{ "quit", quit_activated, NULL, NULL, NULL },
+ { "time-active", NULL, NULL, "false", time_active_changed }
};
static void
bloat_pad_startup (GApplication *application)
{
+ BloatPad *bloatpad = (BloatPad*) application;
GtkBuilder *builder;
G_APPLICATION_CLASS (bloat_pad_parent_class)
@@ -301,14 +358,34 @@ bloat_pad_startup (GApplication *application)
" </item>"
" </section>"
" </submenu>"
+ " <submenu id='time-menu'>"
+ " <attribute name='label' translatable='yes'>Time</attribute>"
+ " <attribute name='submenu-action'>app.time-active</attribute>"
+ " </submenu>"
" </menu>"
"</interface>", -1, NULL);
gtk_application_set_app_menu (GTK_APPLICATION (application), G_MENU_MODEL (gtk_builder_get_object (builder, "app-menu")));
gtk_application_set_menubar (GTK_APPLICATION (application), G_MENU_MODEL (gtk_builder_get_object (builder, "menubar")));
+ bloatpad->time = G_MENU (gtk_builder_get_object (builder, "time-menu"));
g_object_unref (builder);
}
static void
+bloat_pad_shutdown (GApplication *application)
+{
+ BloatPad *bloatpad = (BloatPad *) application;
+
+ if (bloatpad->timeout)
+ {
+ g_source_remove (bloatpad->timeout);
+ bloatpad->timeout = 0;
+ }
+
+ G_APPLICATION_CLASS (bloat_pad_parent_class)
+ ->shutdown (application);
+}
+
+static void
bloat_pad_init (BloatPad *app)
{
}
@@ -320,6 +397,7 @@ bloat_pad_class_init (BloatPadClass *class)
GObjectClass *object_class = G_OBJECT_CLASS (class);
application_class->startup = bloat_pad_startup;
+ application_class->shutdown = bloat_pad_shutdown;
application_class->activate = bloat_pad_activate;
application_class->open = bloat_pad_open;
@@ -330,7 +408,7 @@ bloat_pad_class_init (BloatPadClass *class)
BloatPad *
bloat_pad_new (void)
{
- GtkApplication *bloat_pad;
+ BloatPad *bloat_pad;
g_type_init ();