Getting started: Add an example for property actions
This example demonstrates property actions and object binding.
This commit is contained in:
		| @ -1804,6 +1804,7 @@ examples/application5/Makefile | ||||
| examples/application6/Makefile | ||||
| examples/application7/Makefile | ||||
| examples/application8/Makefile | ||||
| examples/application9/Makefile | ||||
| tests/Makefile | ||||
| tests/visuals/Makefile | ||||
| testsuite/Makefile | ||||
|  | ||||
| @ -1,7 +1,7 @@ | ||||
| SUBDIRS = \ | ||||
| 	application1 application2 application3 \ | ||||
| 	application4 application5 application6 \ | ||||
| 	application7 application8 | ||||
| 	application7 application8 application9 | ||||
|  | ||||
| AM_CPPFLAGS = \ | ||||
| 	-I$(top_srcdir)				\ | ||||
|  | ||||
							
								
								
									
										48
									
								
								examples/application9/Makefile.am
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										48
									
								
								examples/application9/Makefile.am
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,48 @@ | ||||
| AM_CPPFLAGS = \ | ||||
| 	-I$(top_srcdir)			\ | ||||
| 	-I$(top_srcdir)/gdk		\ | ||||
| 	-I$(top_builddir)/gdk		\ | ||||
| 	$(GTK_DEBUG_FLAGS)		\ | ||||
| 	$(GTK_DEP_CFLAGS) | ||||
|  | ||||
| LDADD = \ | ||||
|         $(top_builddir)/gtk/libgtk-3.la \ | ||||
|         $(top_builddir)/gdk/libgdk-3.la \ | ||||
|         $(GTK_DEP_LIBS) | ||||
|  | ||||
|  | ||||
| noinst_PROGRAMS = exampleapp | ||||
|  | ||||
| exampleapp_SOURCES = \ | ||||
| 	main.c \ | ||||
| 	exampleapp.c exampleapp.h \ | ||||
| 	exampleappwin.c exampleappwin.h \ | ||||
| 	exampleappprefs.c exampleappprefs.h \ | ||||
| 	resources.c | ||||
|  | ||||
| BUILT_SOURCES = \ | ||||
| 	resources.c \ | ||||
| 	gschemas.compiled | ||||
|  | ||||
| resources.c: exampleapp.gresource.xml $(shell $(GLIB_COMPILE_RESOURCES) --sourcedir=$(srcdir) --generate-dependencies $(srcdir)/exampleapp.gresource.xml) | ||||
| 	$(AM_V_GEN) $(GLIB_COMPILE_RESOURCES) $(srcdir)/exampleapp.gresource.xml \ | ||||
| 		--target=$@ --sourcedir=$(srcdir) --generate-source | ||||
|  | ||||
| gsettings_SCHEMAS = \ | ||||
| 	org.gtk.exampleapp.gschema.xml | ||||
|  | ||||
| @GSETTINGS_RULES@ | ||||
|  | ||||
| gschemas.compiled: org.gtk.exampleapp.gschema.xml | ||||
| 	$(GLIB_COMPILE_SCHEMAS) . | ||||
|  | ||||
| EXTRA_DIST = \ | ||||
| 	window.ui \ | ||||
| 	app-menu.ui \ | ||||
| 	prefs.ui \ | ||||
| 	gears-menu.ui \ | ||||
| 	exampleapp.gresource.xml \ | ||||
| 	org.gtk.exampleapp.gschema.xml | ||||
|  | ||||
| CLEANFILES = \ | ||||
| 	gschemas.compiled | ||||
							
								
								
									
										19
									
								
								examples/application9/app-menu.ui
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										19
									
								
								examples/application9/app-menu.ui
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,19 @@ | ||||
| <?xml version="1.0"?> | ||||
| <interface> | ||||
|   <!-- interface-requires gtk+ 3.0 --> | ||||
|   <menu id="appmenu"> | ||||
|     <section> | ||||
|       <item> | ||||
|         <attribute name="label" translatable="yes">_Preferences</attribute> | ||||
|         <attribute name="action">app.preferences</attribute> | ||||
|       </item> | ||||
|     </section> | ||||
|     <section> | ||||
|       <item> | ||||
|         <attribute name="label" translatable="yes">_Quit</attribute> | ||||
|         <attribute name="action">app.quit</attribute> | ||||
|         <attribute name="accel"><![CDATA[<Ctrl>Q]]></attribute> | ||||
|       </item> | ||||
|     </section> | ||||
|   </menu> | ||||
| </interface> | ||||
							
								
								
									
										115
									
								
								examples/application9/exampleapp.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										115
									
								
								examples/application9/exampleapp.c
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,115 @@ | ||||
| #include <gtk/gtk.h> | ||||
|  | ||||
| #include "exampleapp.h" | ||||
| #include "exampleappwin.h" | ||||
| #include "exampleappprefs.h" | ||||
|  | ||||
| struct _ExampleApp | ||||
| { | ||||
|   GtkApplication parent; | ||||
| }; | ||||
|  | ||||
| struct _ExampleAppClass | ||||
| { | ||||
|   GtkApplicationClass parent_class; | ||||
| }; | ||||
|  | ||||
| G_DEFINE_TYPE(ExampleApp, example_app, GTK_TYPE_APPLICATION); | ||||
|  | ||||
| static void | ||||
| example_app_init (ExampleApp *app) | ||||
| { | ||||
| } | ||||
|  | ||||
| static void | ||||
| preferences_activated (GSimpleAction *action, | ||||
|                        GVariant      *parameter, | ||||
|                        gpointer       app) | ||||
| { | ||||
|   ExampleAppPrefs *prefs; | ||||
|   GtkWindow *win; | ||||
|  | ||||
|   win = gtk_application_get_active_window (GTK_APPLICATION (app)); | ||||
|   prefs = example_app_prefs_new (EXAMPLE_APP_WINDOW (win)); | ||||
|   gtk_window_present (GTK_WINDOW (prefs)); | ||||
| } | ||||
|  | ||||
| static void | ||||
| quit_activated (GSimpleAction *action, | ||||
|                 GVariant      *parameter, | ||||
|                 gpointer       app) | ||||
| { | ||||
|   g_application_quit (G_APPLICATION (app)); | ||||
| } | ||||
|  | ||||
| static GActionEntry app_entries[] = | ||||
| { | ||||
|   { "preferences", preferences_activated, NULL, NULL, NULL }, | ||||
|   { "quit", quit_activated, NULL, NULL, NULL } | ||||
| }; | ||||
|  | ||||
| static void | ||||
| example_app_startup (GApplication *app) | ||||
| { | ||||
|   GtkBuilder *builder; | ||||
|   GMenuModel *app_menu; | ||||
|  | ||||
|   G_APPLICATION_CLASS (example_app_parent_class)->startup (app); | ||||
|  | ||||
|   g_action_map_add_action_entries (G_ACTION_MAP (app), | ||||
|                                    app_entries, G_N_ELEMENTS (app_entries), | ||||
|                                    app); | ||||
|  | ||||
|   builder = gtk_builder_new_from_resource ("/org/gtk/exampleapp/app-menu.ui"); | ||||
|   app_menu = G_MENU_MODEL (gtk_builder_get_object (builder, "appmenu")); | ||||
|   gtk_application_set_app_menu (GTK_APPLICATION (app), app_menu); | ||||
|   g_object_unref (builder); | ||||
| } | ||||
|  | ||||
| static void | ||||
| example_app_activate (GApplication *app) | ||||
| { | ||||
|   ExampleAppWindow *win; | ||||
|  | ||||
|   win = example_app_window_new (EXAMPLE_APP (app)); | ||||
|   gtk_window_present (GTK_WINDOW (win)); | ||||
| } | ||||
|  | ||||
| static void | ||||
| example_app_open (GApplication  *app, | ||||
|                   GFile        **files, | ||||
|                   gint           n_files, | ||||
|                   const gchar   *hint) | ||||
| { | ||||
|   GList *windows; | ||||
|   ExampleAppWindow *win; | ||||
|   int i; | ||||
|  | ||||
|   windows = gtk_application_get_windows (GTK_APPLICATION (app)); | ||||
|   if (windows) | ||||
|     win = EXAMPLE_APP_WINDOW (windows->data); | ||||
|   else | ||||
|     win = example_app_window_new (EXAMPLE_APP (app)); | ||||
|  | ||||
|   for (i = 0; i < n_files; i++) | ||||
|     example_app_window_open (win, files[i]); | ||||
|  | ||||
|   gtk_window_present (GTK_WINDOW (win)); | ||||
| } | ||||
|  | ||||
| static void | ||||
| example_app_class_init (ExampleAppClass *class) | ||||
| { | ||||
|   G_APPLICATION_CLASS (class)->startup = example_app_startup; | ||||
|   G_APPLICATION_CLASS (class)->activate = example_app_activate; | ||||
|   G_APPLICATION_CLASS (class)->open = example_app_open; | ||||
| } | ||||
|  | ||||
| ExampleApp * | ||||
| example_app_new (void) | ||||
| { | ||||
|   return g_object_new (EXAMPLE_APP_TYPE, | ||||
|                        "application-id", "org.gtk.exampleapp", | ||||
|                        "flags", G_APPLICATION_HANDLES_OPEN, | ||||
|                        NULL); | ||||
| } | ||||
							
								
								
									
										9
									
								
								examples/application9/exampleapp.gresource.xml
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										9
									
								
								examples/application9/exampleapp.gresource.xml
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,9 @@ | ||||
| <?xml version="1.0" encoding="UTF-8"?> | ||||
| <gresources> | ||||
|   <gresource prefix="/org/gtk/exampleapp"> | ||||
|     <file preprocess="xml-stripblanks">window.ui</file> | ||||
|     <file preprocess="xml-stripblanks">app-menu.ui</file> | ||||
|     <file preprocess="xml-stripblanks">gears-menu.ui</file> | ||||
|     <file preprocess="xml-stripblanks">prefs.ui</file> | ||||
|   </gresource> | ||||
| </gresources> | ||||
							
								
								
									
										19
									
								
								examples/application9/exampleapp.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										19
									
								
								examples/application9/exampleapp.h
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,19 @@ | ||||
| #ifndef __EXAMPLEAPP_H | ||||
| #define __EXAMPLEAPP_H | ||||
|  | ||||
| #include <gtk/gtk.h> | ||||
|  | ||||
|  | ||||
| #define EXAMPLE_APP_TYPE (example_app_get_type ()) | ||||
| #define EXAMPLE_APP(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), EXAMPLE_APP_TYPE, ExampleApp)) | ||||
|  | ||||
|  | ||||
| typedef struct _ExampleApp       ExampleApp; | ||||
| typedef struct _ExampleAppClass  ExampleAppClass; | ||||
|  | ||||
|  | ||||
| GType           example_app_get_type    (void); | ||||
| ExampleApp     *example_app_new         (void); | ||||
|  | ||||
|  | ||||
| #endif /* __EXAMPLEAPP_H */ | ||||
							
								
								
									
										75
									
								
								examples/application9/exampleappprefs.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										75
									
								
								examples/application9/exampleappprefs.c
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,75 @@ | ||||
| #include <gtk/gtk.h> | ||||
|  | ||||
| #include "exampleapp.h" | ||||
| #include "exampleappwin.h" | ||||
| #include "exampleappprefs.h" | ||||
|  | ||||
| struct _ExampleAppPrefs | ||||
| { | ||||
|   GtkDialog parent; | ||||
| }; | ||||
|  | ||||
| struct _ExampleAppPrefsClass | ||||
| { | ||||
|   GtkDialogClass parent_class; | ||||
| }; | ||||
|  | ||||
| typedef struct _ExampleAppPrefsPrivate ExampleAppPrefsPrivate; | ||||
|  | ||||
| struct _ExampleAppPrefsPrivate | ||||
| { | ||||
|   GSettings *settings; | ||||
|   GtkWidget *font; | ||||
|   GtkWidget *transition; | ||||
|   GtkWidget *close; | ||||
| }; | ||||
|  | ||||
| G_DEFINE_TYPE_WITH_PRIVATE(ExampleAppPrefs, example_app_prefs, GTK_TYPE_DIALOG) | ||||
|  | ||||
| static void | ||||
| example_app_prefs_init (ExampleAppPrefs *prefs) | ||||
| { | ||||
|   ExampleAppPrefsPrivate *priv; | ||||
|  | ||||
|   priv = example_app_prefs_get_instance_private (prefs); | ||||
|   gtk_widget_init_template (GTK_WIDGET (prefs)); | ||||
|   priv->settings = g_settings_new ("org.gtk.exampleapp"); | ||||
|  | ||||
|   g_settings_bind (priv->settings, "font", | ||||
|                    priv->font, "font", | ||||
|                    G_SETTINGS_BIND_DEFAULT); | ||||
|   g_settings_bind (priv->settings, "transition", | ||||
|                    priv->transition, "active-id", | ||||
|                    G_SETTINGS_BIND_DEFAULT); | ||||
|   g_signal_connect_swapped (priv->close, "clicked", | ||||
|                             G_CALLBACK (gtk_widget_destroy), prefs); | ||||
| } | ||||
|  | ||||
| static void | ||||
| example_app_prefs_dispose (GObject *object) | ||||
| { | ||||
|   ExampleAppPrefsPrivate *priv; | ||||
|  | ||||
|   priv = example_app_prefs_get_instance_private (EXAMPLE_APP_PREFS (object)); | ||||
|   g_clear_object (&priv->settings); | ||||
|  | ||||
|   G_OBJECT_CLASS (example_app_prefs_parent_class)->dispose (object); | ||||
| } | ||||
|  | ||||
| static void | ||||
| example_app_prefs_class_init (ExampleAppPrefsClass *class) | ||||
| { | ||||
|   G_OBJECT_CLASS (class)->dispose = example_app_prefs_dispose; | ||||
|  | ||||
|   gtk_widget_class_set_template_from_resource (GTK_WIDGET_CLASS (class), | ||||
|                                                "/org/gtk/exampleapp/prefs.ui"); | ||||
|   gtk_widget_class_bind_child (GTK_WIDGET_CLASS (class), ExampleAppPrefsPrivate, font); | ||||
|   gtk_widget_class_bind_child (GTK_WIDGET_CLASS (class), ExampleAppPrefsPrivate, transition); | ||||
|   gtk_widget_class_bind_child (GTK_WIDGET_CLASS (class), ExampleAppPrefsPrivate, close); | ||||
| } | ||||
|  | ||||
| ExampleAppPrefs * | ||||
| example_app_prefs_new (ExampleAppWindow *win) | ||||
| { | ||||
|   return g_object_new (EXAMPLE_APP_PREFS_TYPE, "transient-for", win, NULL); | ||||
| } | ||||
							
								
								
									
										20
									
								
								examples/application9/exampleappprefs.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										20
									
								
								examples/application9/exampleappprefs.h
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,20 @@ | ||||
| #ifndef __EXAMPLEAPPPREFS_H | ||||
| #define __EXAMPLEAPPPREFS_H | ||||
|  | ||||
| #include <gtk/gtk.h> | ||||
| #include "exampleappwin.h" | ||||
|  | ||||
|  | ||||
| #define EXAMPLE_APP_PREFS_TYPE (example_app_prefs_get_type ()) | ||||
| #define EXAMPLE_APP_PREFS(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), EXAMPLE_APP_PREFS_TYPE, ExampleAppPrefs)) | ||||
|  | ||||
|  | ||||
| typedef struct _ExampleAppPrefs          ExampleAppPrefs; | ||||
| typedef struct _ExampleAppPrefsClass     ExampleAppPrefsClass; | ||||
|  | ||||
|  | ||||
| GType                   example_app_prefs_get_type     (void); | ||||
| ExampleAppPrefs        *example_app_prefs_new          (ExampleAppWindow *win); | ||||
|  | ||||
|  | ||||
| #endif /* __EXAMPLEAPPPREFS_H */ | ||||
							
								
								
									
										335
									
								
								examples/application9/exampleappwin.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										335
									
								
								examples/application9/exampleappwin.c
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,335 @@ | ||||
| #include "exampleapp.h" | ||||
| #include "exampleappwin.h" | ||||
| #include <gtk/gtk.h> | ||||
|  | ||||
| struct _ExampleAppWindow | ||||
| { | ||||
|   GtkApplicationWindow parent; | ||||
| }; | ||||
|  | ||||
| struct _ExampleAppWindowClass | ||||
| { | ||||
|   GtkApplicationWindowClass parent_class; | ||||
| }; | ||||
|  | ||||
| typedef struct _ExampleAppWindowPrivate ExampleAppWindowPrivate; | ||||
|  | ||||
| struct _ExampleAppWindowPrivate | ||||
| { | ||||
|   GSettings *settings; | ||||
|   GtkWidget *stack; | ||||
|   GtkWidget *search; | ||||
|   GtkWidget *searchbar; | ||||
|   GtkWidget *searchentry; | ||||
|   GtkWidget *gears; | ||||
|   GtkWidget *sidebar; | ||||
|   GtkWidget *words; | ||||
|   GtkWidget *lines; | ||||
|   GtkWidget *lines_label; | ||||
| }; | ||||
|  | ||||
| G_DEFINE_TYPE_WITH_PRIVATE(ExampleAppWindow, example_app_window, GTK_TYPE_APPLICATION_WINDOW); | ||||
|  | ||||
| static void | ||||
| search_text_changed (GtkEntry         *entry, | ||||
|                      ExampleAppWindow *win) | ||||
| { | ||||
|   ExampleAppWindowPrivate *priv; | ||||
|   const gchar *text; | ||||
|   GtkWidget *tab; | ||||
|   GtkWidget *view; | ||||
|   GtkTextBuffer *buffer; | ||||
|   GtkTextIter start, match_start, match_end; | ||||
|  | ||||
|   text = gtk_entry_get_text (entry); | ||||
|  | ||||
|   if (text[0] == '\0') | ||||
|     return; | ||||
|  | ||||
|   priv = example_app_window_get_instance_private (win); | ||||
|  | ||||
|   tab = gtk_stack_get_visible_child (GTK_STACK (priv->stack)); | ||||
|   view = gtk_bin_get_child (GTK_BIN (tab)); | ||||
|   buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (view)); | ||||
|  | ||||
|   /* Very simple-minded search implementation */ | ||||
|   gtk_text_buffer_get_start_iter (buffer, &start); | ||||
|   if (gtk_text_iter_forward_search (&start, text, GTK_TEXT_SEARCH_CASE_INSENSITIVE, | ||||
|                                     &match_start, &match_end, NULL)) | ||||
|     { | ||||
|       gtk_text_buffer_select_range (buffer, &match_start, &match_end); | ||||
|       gtk_text_view_scroll_to_iter (GTK_TEXT_VIEW (view), &match_start, | ||||
|                                     0.0, FALSE, 0.0, 0.0); | ||||
|     } | ||||
| } | ||||
|  | ||||
| static void | ||||
| find_word (GtkButton        *button, | ||||
|            ExampleAppWindow *win) | ||||
| { | ||||
|   ExampleAppWindowPrivate *priv; | ||||
|   const gchar *word; | ||||
|  | ||||
|   priv = example_app_window_get_instance_private (win); | ||||
|  | ||||
|   word = gtk_button_get_label (button); | ||||
|   gtk_entry_set_text (GTK_ENTRY (priv->searchentry), word); | ||||
| } | ||||
|  | ||||
| static void | ||||
| update_words (ExampleAppWindow *win) | ||||
| { | ||||
|   ExampleAppWindowPrivate *priv; | ||||
|   GHashTable *strings; | ||||
|   GHashTableIter iter; | ||||
|   GtkWidget *tab, *view, *row; | ||||
|   GtkTextBuffer *buffer; | ||||
|   GtkTextIter start, end; | ||||
|   GList *children, *l; | ||||
|   gchar *word, *key; | ||||
|  | ||||
|   priv = example_app_window_get_instance_private (win); | ||||
|  | ||||
|   tab = gtk_stack_get_visible_child (GTK_STACK (priv->stack)); | ||||
|  | ||||
|   if (tab == NULL) | ||||
|     return; | ||||
|  | ||||
|   view = gtk_bin_get_child (GTK_BIN (tab)); | ||||
|   buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (view)); | ||||
|  | ||||
|   strings = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL); | ||||
|  | ||||
|   gtk_text_buffer_get_start_iter (buffer, &start); | ||||
|   while (!gtk_text_iter_is_end (&start)) | ||||
|     { | ||||
|       while (!gtk_text_iter_starts_word (&start)) | ||||
|         { | ||||
|           if (!gtk_text_iter_forward_char (&start)) | ||||
|             goto done; | ||||
|         } | ||||
|       end = start; | ||||
|       if (!gtk_text_iter_forward_word_end (&end)) | ||||
|         goto done; | ||||
|       word = gtk_text_buffer_get_text (buffer, &start, &end, FALSE); | ||||
|       g_hash_table_add (strings, g_utf8_strdown (word, -1)); | ||||
|       g_free (word); | ||||
|       start = end; | ||||
|     } | ||||
|  | ||||
| done: | ||||
|   children = gtk_container_get_children (GTK_CONTAINER (priv->words)); | ||||
|   for (l = children; l; l = l->next) | ||||
|     gtk_container_remove (GTK_CONTAINER (priv->words), GTK_WIDGET (l->data)); | ||||
|   g_list_free (children); | ||||
|  | ||||
|   g_hash_table_iter_init (&iter, strings); | ||||
|   while (g_hash_table_iter_next (&iter, (gpointer *)&key, NULL)) | ||||
|     { | ||||
|       row = gtk_button_new_with_label (key); | ||||
|       g_signal_connect (row, "clicked", | ||||
|                         G_CALLBACK (find_word), win); | ||||
|       gtk_widget_show (row); | ||||
|       gtk_container_add (GTK_CONTAINER (priv->words), row); | ||||
|     } | ||||
|  | ||||
|   g_hash_table_unref (strings); | ||||
| } | ||||
|  | ||||
| static void | ||||
| update_lines (ExampleAppWindow *win) | ||||
| { | ||||
|   ExampleAppWindowPrivate *priv; | ||||
|   GtkWidget *tab, *view; | ||||
|   GtkTextBuffer *buffer; | ||||
|   GtkTextIter iter; | ||||
|   int count; | ||||
|   gchar *lines; | ||||
|  | ||||
|   priv = example_app_window_get_instance_private (win); | ||||
|  | ||||
|   tab = gtk_stack_get_visible_child (GTK_STACK (priv->stack)); | ||||
|  | ||||
|   if (tab == NULL) | ||||
|     return; | ||||
|  | ||||
|   view = gtk_bin_get_child (GTK_BIN (tab)); | ||||
|   buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (view)); | ||||
|  | ||||
|   count = 0; | ||||
|  | ||||
|   gtk_text_buffer_get_start_iter (buffer, &iter); | ||||
|   while (!gtk_text_iter_is_end (&iter)) | ||||
|     { | ||||
|       count++; | ||||
|       if (!gtk_text_iter_forward_line (&iter)) | ||||
|         break; | ||||
|     } | ||||
|  | ||||
|   lines = g_strdup_printf ("%d", count); | ||||
|   gtk_label_set_text (GTK_LABEL (priv->lines), lines); | ||||
|   g_free (lines); | ||||
| } | ||||
|  | ||||
| static void | ||||
| visible_child_changed (GObject          *stack, | ||||
|                        GParamSpec       *pspec, | ||||
|                        ExampleAppWindow *win) | ||||
| { | ||||
|   ExampleAppWindowPrivate *priv; | ||||
|  | ||||
|   if (gtk_widget_in_destruction (GTK_WIDGET (win))) | ||||
|     return; | ||||
|  | ||||
|   priv = example_app_window_get_instance_private (win); | ||||
|   gtk_search_bar_set_search_mode (GTK_SEARCH_BAR (priv->searchbar), FALSE); | ||||
|   update_words (win); | ||||
|   update_lines (win); | ||||
| } | ||||
|  | ||||
| static void | ||||
| words_changed (GObject          *sidebar, | ||||
|                GParamSpec       *pspec, | ||||
|                ExampleAppWindow *win) | ||||
| { | ||||
|   update_words (win); | ||||
| } | ||||
|  | ||||
| static void | ||||
| example_app_window_init (ExampleAppWindow *win) | ||||
| { | ||||
|   ExampleAppWindowPrivate *priv; | ||||
|   GtkBuilder *builder; | ||||
|   GMenuModel *menu; | ||||
|   GAction *action; | ||||
|  | ||||
|   priv = example_app_window_get_instance_private (win); | ||||
|   gtk_widget_init_template (GTK_WIDGET (win)); | ||||
|   priv->settings = g_settings_new ("org.gtk.exampleapp"); | ||||
|  | ||||
|   g_settings_bind (priv->settings, "transition", | ||||
|                    priv->stack, "transition-type", | ||||
|                    G_SETTINGS_BIND_DEFAULT); | ||||
|  | ||||
|   g_settings_bind (priv->settings, "show-words", | ||||
|                    priv->sidebar, "reveal-child", | ||||
|                    G_SETTINGS_BIND_DEFAULT); | ||||
|  | ||||
|   g_object_bind_property (priv->search, "active", | ||||
|                           priv->searchbar, "search-mode-enabled", | ||||
|                           G_BINDING_BIDIRECTIONAL); | ||||
|  | ||||
|   g_signal_connect (priv->searchentry, "changed", | ||||
|                     G_CALLBACK (search_text_changed), win); | ||||
|   g_signal_connect (priv->stack, "notify::visible-child", | ||||
|                     G_CALLBACK (visible_child_changed), win); | ||||
|   g_signal_connect (priv->sidebar, "notify::reveal-child", | ||||
|                     G_CALLBACK (words_changed), win); | ||||
|  | ||||
|   builder = gtk_builder_new_from_resource ("/org/gtk/exampleapp/gears-menu.ui"); | ||||
|   menu = G_MENU_MODEL (gtk_builder_get_object (builder, "menu")); | ||||
|   gtk_menu_button_set_menu_model (GTK_MENU_BUTTON (priv->gears), menu); | ||||
|   g_object_unref (builder); | ||||
|  | ||||
|   action = g_settings_create_action (priv->settings, "show-words"); | ||||
|   g_action_map_add_action (G_ACTION_MAP (win), action); | ||||
|   g_object_unref (action); | ||||
|  | ||||
|   action = (GAction*) g_property_action_new ("show-lines", priv->lines, "visible"); | ||||
|   g_action_map_add_action (G_ACTION_MAP (win), action); | ||||
|   g_object_unref (action); | ||||
|  | ||||
|   g_object_bind_property (priv->lines, "visible", | ||||
|                           priv->lines_label, "visible", | ||||
|                           G_BINDING_DEFAULT); | ||||
| } | ||||
|  | ||||
| static void | ||||
| example_app_window_dispose (GObject *object) | ||||
| { | ||||
|   ExampleAppWindow *win; | ||||
|   ExampleAppWindowPrivate *priv; | ||||
|  | ||||
|   win = EXAMPLE_APP_WINDOW (object); | ||||
|   priv = example_app_window_get_instance_private (win); | ||||
|  | ||||
|   g_clear_object (&priv->settings); | ||||
|  | ||||
|   G_OBJECT_CLASS (example_app_window_parent_class)->dispose (object); | ||||
| } | ||||
|  | ||||
| static void | ||||
| example_app_window_class_init (ExampleAppWindowClass *class) | ||||
| { | ||||
|   G_OBJECT_CLASS (class)->dispose = example_app_window_dispose; | ||||
|  | ||||
|   gtk_widget_class_set_template_from_resource (GTK_WIDGET_CLASS (class), | ||||
|                                                "/org/gtk/exampleapp/window.ui"); | ||||
|   gtk_widget_class_bind_child (GTK_WIDGET_CLASS (class), ExampleAppWindowPrivate, stack); | ||||
|   gtk_widget_class_bind_child (GTK_WIDGET_CLASS (class), ExampleAppWindowPrivate, search); | ||||
|   gtk_widget_class_bind_child (GTK_WIDGET_CLASS (class), ExampleAppWindowPrivate, searchbar); | ||||
|   gtk_widget_class_bind_child (GTK_WIDGET_CLASS (class), ExampleAppWindowPrivate, searchentry); | ||||
|   gtk_widget_class_bind_child (GTK_WIDGET_CLASS (class), ExampleAppWindowPrivate, gears); | ||||
|   gtk_widget_class_bind_child (GTK_WIDGET_CLASS (class), ExampleAppWindowPrivate, words); | ||||
|   gtk_widget_class_bind_child (GTK_WIDGET_CLASS (class), ExampleAppWindowPrivate, sidebar); | ||||
|   gtk_widget_class_bind_child (GTK_WIDGET_CLASS (class), ExampleAppWindowPrivate, lines); | ||||
|   gtk_widget_class_bind_child (GTK_WIDGET_CLASS (class), ExampleAppWindowPrivate, lines_label); | ||||
| } | ||||
|  | ||||
| ExampleAppWindow * | ||||
| example_app_window_new (ExampleApp *app) | ||||
| { | ||||
|   return g_object_new (EXAMPLE_APP_WINDOW_TYPE, "application", app, NULL); | ||||
| } | ||||
|  | ||||
| void | ||||
| example_app_window_open (ExampleAppWindow *win, | ||||
|                          GFile            *file) | ||||
| { | ||||
|   ExampleAppWindowPrivate *priv; | ||||
|   gchar *basename; | ||||
|   GtkWidget *scrolled, *view; | ||||
|   gchar *contents; | ||||
|   gsize length; | ||||
|   GtkTextBuffer *buffer; | ||||
|   GtkTextTag *tag; | ||||
|   GtkTextIter start_iter, end_iter; | ||||
|  | ||||
|   priv = example_app_window_get_instance_private (win); | ||||
|   basename = g_file_get_basename (file); | ||||
|  | ||||
|   scrolled = gtk_scrolled_window_new (NULL, NULL); | ||||
|   gtk_widget_show (scrolled); | ||||
|   gtk_widget_set_hexpand (scrolled, TRUE); | ||||
|   gtk_widget_set_vexpand (scrolled, TRUE); | ||||
|   view = gtk_text_view_new (); | ||||
|   gtk_text_view_set_editable (GTK_TEXT_VIEW (view), FALSE); | ||||
|   gtk_text_view_set_cursor_visible (GTK_TEXT_VIEW (view), FALSE); | ||||
|   gtk_widget_show (view); | ||||
|   gtk_container_add (GTK_CONTAINER (scrolled), view); | ||||
|   gtk_stack_add_titled (GTK_STACK (priv->stack), scrolled, basename, basename); | ||||
|  | ||||
|   buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (view)); | ||||
|  | ||||
|   if (g_file_load_contents (file, NULL, &contents, &length, NULL, NULL)) | ||||
|     { | ||||
|       gtk_text_buffer_set_text (buffer, contents, length); | ||||
|       g_free (contents); | ||||
|     } | ||||
|  | ||||
|   tag = gtk_text_buffer_create_tag (buffer, NULL, NULL); | ||||
|   g_settings_bind (priv->settings, "font", | ||||
|                    tag, "font", | ||||
|                    G_SETTINGS_BIND_DEFAULT); | ||||
|  | ||||
|   gtk_text_buffer_get_start_iter (buffer, &start_iter); | ||||
|   gtk_text_buffer_get_end_iter (buffer, &end_iter); | ||||
|   gtk_text_buffer_apply_tag (buffer, tag, &start_iter, &end_iter); | ||||
|  | ||||
|   g_free (basename); | ||||
|  | ||||
|   gtk_widget_set_sensitive (priv->search, TRUE); | ||||
|  | ||||
|   update_words (win); | ||||
|   update_lines (win); | ||||
| } | ||||
							
								
								
									
										22
									
								
								examples/application9/exampleappwin.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										22
									
								
								examples/application9/exampleappwin.h
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,22 @@ | ||||
| #ifndef __EXAMPLEAPPWIN_H | ||||
| #define __EXAMPLEAPPWIN_H | ||||
|  | ||||
| #include <gtk/gtk.h> | ||||
| #include "exampleapp.h" | ||||
|  | ||||
|  | ||||
| #define EXAMPLE_APP_WINDOW_TYPE (example_app_window_get_type ()) | ||||
| #define EXAMPLE_APP_WINDOW(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), EXAMPLE_APP_WINDOW_TYPE, ExampleAppWindow)) | ||||
|  | ||||
|  | ||||
| typedef struct _ExampleAppWindow         ExampleAppWindow; | ||||
| typedef struct _ExampleAppWindowClass    ExampleAppWindowClass; | ||||
|  | ||||
|  | ||||
| GType                   example_app_window_get_type     (void); | ||||
| ExampleAppWindow       *example_app_window_new          (ExampleApp *app); | ||||
| void                    example_app_window_open         (ExampleAppWindow *win, | ||||
|                                                          GFile            *file); | ||||
|  | ||||
|  | ||||
| #endif /* __EXAMPLEAPPWIN_H */ | ||||
							
								
								
									
										16
									
								
								examples/application9/gears-menu.ui
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										16
									
								
								examples/application9/gears-menu.ui
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,16 @@ | ||||
| <?xml version="1.0"?> | ||||
| <interface> | ||||
|   <!-- interface-requires gtk+ 3.0 --> | ||||
|   <menu id="menu"> | ||||
|     <section> | ||||
|       <item> | ||||
|         <attribute name="label" translatable="yes">_Words</attribute> | ||||
|         <attribute name="action">win.show-words</attribute> | ||||
|       </item> | ||||
|       <item> | ||||
|         <attribute name="label" translatable="yes">_Lines</attribute> | ||||
|         <attribute name="action">win.show-lines</attribute> | ||||
|       </item> | ||||
|     </section> | ||||
|   </menu> | ||||
| </interface> | ||||
							
								
								
									
										15
									
								
								examples/application9/main.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										15
									
								
								examples/application9/main.c
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,15 @@ | ||||
| #include <gtk/gtk.h> | ||||
| #include <exampleapp.h> | ||||
|  | ||||
| int | ||||
| main (int argc, char *argv[]) | ||||
| { | ||||
|   /* Since this example is running uninstalled, | ||||
|    * we have to help it find its schema. This | ||||
|    * is *not* necessary in properly installed | ||||
|    * application. | ||||
|    */ | ||||
|   g_setenv ("GSETTINGS_SCHEMA_DIR", ".", FALSE); | ||||
|  | ||||
|   return g_application_run (G_APPLICATION (example_app_new ()), argc, argv); | ||||
| } | ||||
							
								
								
									
										25
									
								
								examples/application9/org.gtk.exampleapp.gschema.xml
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										25
									
								
								examples/application9/org.gtk.exampleapp.gschema.xml
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,25 @@ | ||||
| <?xml version="1.0" encoding="UTF-8"?> | ||||
| <schemalist> | ||||
|   <schema path="/org/gtk/exampleapp/" id="org.gtk.exampleapp"> | ||||
|     <key name="font" type="s"> | ||||
|       <default>'Monospace 12'</default> | ||||
|       <summary>Font</summary> | ||||
|       <description>The font to be used for content.</description> | ||||
|     </key> | ||||
|     <key name="transition" type="s"> | ||||
|       <choices> | ||||
|         <choice value='none'/> | ||||
|         <choice value='crossfade'/> | ||||
|         <choice value='slide-left-right'/> | ||||
|       </choices> | ||||
|       <default>'none'</default> | ||||
|       <summary>Transition</summary> | ||||
|       <description>The transition to use when switching tabs.</description> | ||||
|     </key> | ||||
|     <key name="show-words" type="b"> | ||||
|       <default>false</default> | ||||
|       <summary>Show words</summary> | ||||
|       <description>Whether to show a word list in the sidebar</description> | ||||
|     </key> | ||||
|   </schema> | ||||
| </schemalist> | ||||
							
								
								
									
										82
									
								
								examples/application9/prefs.ui
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										82
									
								
								examples/application9/prefs.ui
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,82 @@ | ||||
| <?xml version="1.0" encoding="UTF-8"?> | ||||
| <interface> | ||||
|   <!-- interface-requires gtk+ 3.8 --> | ||||
|   <template class="ExampleAppPrefs" parent="GtkDialog"> | ||||
|     <property name="title" translatable="yes">Preferences</property> | ||||
|     <property name="resizable">False</property> | ||||
|     <property name="modal">True</property> | ||||
|     <child internal-child="vbox"> | ||||
|       <object class="GtkBox" id="vbox"> | ||||
|         <child> | ||||
|           <object class="GtkGrid" id="grid"> | ||||
|             <property name="visible">True</property> | ||||
|             <property name="margin">6</property> | ||||
|             <property name="row-spacing">12</property> | ||||
|             <property name="column-spacing">6</property> | ||||
|             <child> | ||||
|               <object class="GtkLabel" id="fontlabel"> | ||||
|                 <property name="visible">True</property> | ||||
|                 <property name="label">_Font:</property> | ||||
|                 <property name="use-underline">True</property> | ||||
|                 <property name="mnemonic-widget">font</property> | ||||
|                 <property name="xalign">1</property> | ||||
|               </object> | ||||
|               <packing> | ||||
|                 <property name="left-attach">0</property> | ||||
|                 <property name="top-attach">0</property> | ||||
|               </packing> | ||||
|             </child> | ||||
|             <child> | ||||
|               <object class="GtkFontButton" id="font"> | ||||
|                 <property name="visible">True</property> | ||||
|               </object> | ||||
|               <packing> | ||||
|                 <property name="left-attach">1</property> | ||||
|                 <property name="top-attach">0</property> | ||||
|               </packing> | ||||
|             </child> | ||||
|             <child> | ||||
|               <object class="GtkLabel" id="transitionlabel"> | ||||
|                 <property name="visible">True</property> | ||||
|                 <property name="label">_Transition:</property> | ||||
|                 <property name="use-underline">True</property> | ||||
|                 <property name="mnemonic-widget">transition</property> | ||||
|                 <property name="xalign">1</property> | ||||
|               </object> | ||||
|               <packing> | ||||
|                 <property name="left-attach">0</property> | ||||
|                 <property name="top-attach">1</property> | ||||
|               </packing> | ||||
|             </child> | ||||
|             <child> | ||||
|               <object class="GtkComboBoxText" id="transition"> | ||||
|                 <property name="visible">True</property> | ||||
|                 <items> | ||||
|                   <item translatable="yes" id="none">None</item> | ||||
|                   <item translatable="yes" id="crossfade">Fade</item> | ||||
|                   <item translatable="yes" id="slide-left-right">Slide</item> | ||||
|                 </items> | ||||
|               </object> | ||||
|               <packing> | ||||
|                 <property name="left-attach">1</property> | ||||
|                 <property name="top-attach">1</property> | ||||
|               </packing> | ||||
|             </child> | ||||
|           </object> | ||||
|         </child> | ||||
|         <child internal-child="action_area"> | ||||
|           <object class="GtkButtonBox" id="action_area"> | ||||
|             <property name="visible">True</property> | ||||
|             <child> | ||||
|               <object class="GtkButton" id="close"> | ||||
|                 <property name="visible">True</property> | ||||
|                 <property name="label">_Close</property> | ||||
|                 <property name="use-underline">True</property> | ||||
|               </object> | ||||
|             </child> | ||||
|           </object> | ||||
|         </child> | ||||
|       </object> | ||||
|     </child> | ||||
|   </template> | ||||
| </interface> | ||||
							
								
								
									
										113
									
								
								examples/application9/window.ui
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										113
									
								
								examples/application9/window.ui
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,113 @@ | ||||
| <?xml version="1.0" encoding="UTF-8"?> | ||||
| <interface> | ||||
|   <!-- interface-requires gtk+ 3.8 --> | ||||
|   <template class="ExampleAppWindow" parent="GtkApplicationWindow"> | ||||
|     <property name="title" translatable="yes">Example Application</property> | ||||
|     <property name="default-width">600</property> | ||||
|     <property name="default-height">400</property> | ||||
|     <child> | ||||
|       <object class="GtkBox" id="content_box"> | ||||
|         <property name="visible">True</property> | ||||
|         <property name="orientation">vertical</property> | ||||
|         <child> | ||||
|           <object class="GtkHeaderBar" id="header"> | ||||
|             <property name="visible">True</property> | ||||
|             <child> | ||||
|               <object class="GtkLabel" id="lines_label"> | ||||
|                 <property name="visible">False</property> | ||||
|                 <property name="label" translatable="yes">Lines:</property> | ||||
|               </object> | ||||
|               <packing> | ||||
|                 <property name="pack-type">start</property> | ||||
|               </packing> | ||||
|             </child> | ||||
|             <child> | ||||
|               <object class="GtkLabel" id="lines"> | ||||
|                 <property name="visible">False</property> | ||||
|               </object> | ||||
|               <packing> | ||||
|                 <property name="pack-type">start</property> | ||||
|               </packing> | ||||
|             </child> | ||||
|             <child type="title"> | ||||
|               <object class="GtkStackSwitcher" id="tabs"> | ||||
|                 <property name="visible">True</property> | ||||
|                 <property name="stack">stack</property> | ||||
|               </object> | ||||
|             </child> | ||||
|             <child> | ||||
|               <object class="GtkToggleButton" id="search"> | ||||
|                 <property name="visible">True</property> | ||||
|                 <property name="sensitive">False</property> | ||||
|                 <child> | ||||
|                   <object class="GtkImage" id="search-icon"> | ||||
|                     <property name="visible">True</property> | ||||
|                     <property name="icon-name">edit-find-symbolic</property> | ||||
|                     <property name="icon-size">1</property> | ||||
|                   </object> | ||||
|                 </child> | ||||
|               </object> | ||||
|               <packing> | ||||
|                 <property name="pack-type">end</property> | ||||
|               </packing> | ||||
|             </child> | ||||
|             <child> | ||||
|               <object class="GtkMenuButton" id="gears"> | ||||
|                 <property name="visible">True</property> | ||||
|                 <child> | ||||
|                   <object class="GtkImage" id="gears-icon"> | ||||
|                     <property name="visible">True</property> | ||||
|                     <property name="icon-name">emblem-system-symbolic</property> | ||||
|                     <property name="icon-size">1</property> | ||||
|                   </object> | ||||
|                 </child> | ||||
|               </object> | ||||
|               <packing> | ||||
|                 <property name="pack-type">end</property> | ||||
|               </packing> | ||||
|             </child> | ||||
|           </object> | ||||
|         </child> | ||||
|         <child> | ||||
|           <object class="GtkSearchBar" id="searchbar"> | ||||
|             <property name="visible">True</property> | ||||
|             <child> | ||||
|               <object class="GtkSearchEntry" id="searchentry"> | ||||
|                 <property name="visible">True</property> | ||||
|               </object> | ||||
|             </child> | ||||
|           </object> | ||||
|         </child> | ||||
|         <child> | ||||
|           <object class="GtkBox" id="hbox"> | ||||
|             <property name="visible">True</property> | ||||
|             <child> | ||||
|               <object class="GtkRevealer" id="sidebar"> | ||||
|                 <property name="visible">True</property> | ||||
|                 <property name="transition-type">slide-right</property> | ||||
|                 <child> | ||||
|                  <object class="GtkScrolledWindow" id="sidebar-sw"> | ||||
|                    <property name="visible">True</property> | ||||
|                    <property name="hscrollbar-policy">never</property> | ||||
|                    <property name="vscrollbar-policy">automatic</property> | ||||
|                    <child> | ||||
|                      <object class="GtkListBox" id="words"> | ||||
|                        <property name="visible">True</property> | ||||
|                        <property name="selection-mode">none</property> | ||||
|                      </object> | ||||
|                    </child> | ||||
|                  </object> | ||||
|                 </child> | ||||
|               </object> | ||||
|             </child> | ||||
|             <child> | ||||
|               <object class="GtkStack" id="stack"> | ||||
|                 <property name="visible">True</property> | ||||
|               </object> | ||||
|             </child> | ||||
|           </object> | ||||
|         </child> | ||||
|       </object> | ||||
|     </child> | ||||
|   </template> | ||||
| </interface> | ||||
		Reference in New Issue
	
	Block a user
	 Matthias Clasen
					Matthias Clasen