]> Pileus Git - ~andy/gtk/blob - demos/gtk-demo/menus.c
Formatting cleanups
[~andy/gtk] / demos / gtk-demo / menus.c
1 /* Menus
2  *
3  * There are several widgets involved in displaying menus. The
4  * GtkMenuBar widget is a menu bar, which normally appears horizontally
5  * at the top of an application, but can also be layed out vertically.
6  * The GtkMenu widget is the actual menu that pops up. Both GtkMenuBar
7  * and GtkMenu are subclasses of GtkMenuShell; a GtkMenuShell contains
8  * menu items (GtkMenuItem). Each menu item contains text and/or images
9  * and can be selected by the user.
10  *
11  * There are several kinds of menu item, including plain GtkMenuItem,
12  * GtkCheckMenuItem which can be checked/unchecked, GtkRadioMenuItem
13  * which is a check menu item that's in a mutually exclusive group,
14  * GtkSeparatorMenuItem which is a separator bar, GtkTearoffMenuItem
15  * which allows a GtkMenu to be torn off, and GtkImageMenuItem which
16  * can place a GtkImage or other widget next to the menu text.
17  *
18  * A GtkMenuItem can have a submenu, which is simply a GtkMenu to pop
19  * up when the menu item is selected. Typically, all menu items in a menu bar
20  * have submenus.
21  *
22  * GtkUIManager provides a higher-level interface for creating menu bars
23  * and menus; while you can construct menus manually, most people don't
24  * do that. There's a separate demo for GtkUIManager.
25  */
26
27 #include <gtk/gtk.h>
28 #include <gdk/gdkkeysyms.h>
29
30 #include <stdio.h>
31
32 static GtkWidget *
33 create_menu (gint     depth,
34              gboolean tearoff)
35 {
36   GtkWidget *menu;
37   GtkWidget *menuitem;
38   GSList *group;
39   char buf[32];
40   int i, j;
41
42   if (depth < 1)
43     return NULL;
44
45   menu = gtk_menu_new ();
46   group = NULL;
47
48   if (tearoff)
49     {
50       menuitem = gtk_tearoff_menu_item_new ();
51       gtk_menu_shell_append (GTK_MENU_SHELL (menu), menuitem);
52       gtk_widget_show (menuitem);
53     }
54
55   for (i = 0, j = 1; i < 5; i++, j++)
56     {
57       sprintf (buf, "item %2d - %d", depth, j);
58       menuitem = gtk_radio_menu_item_new_with_label (group, buf);
59       group = gtk_radio_menu_item_get_group (GTK_RADIO_MENU_ITEM (menuitem));
60
61       gtk_menu_shell_append (GTK_MENU_SHELL (menu), menuitem);
62       gtk_widget_show (menuitem);
63       if (i == 3)
64         gtk_widget_set_sensitive (menuitem, FALSE);
65
66       gtk_menu_item_set_submenu (GTK_MENU_ITEM (menuitem), create_menu (depth - 1, TRUE));
67     }
68
69   return menu;
70 }
71
72 static void
73 change_orientation (GtkWidget *button,
74                     GtkWidget *menubar)
75 {
76   GtkWidget *parent;
77   GtkOrientation orientation;
78
79   parent = gtk_widget_get_parent (menubar);
80   orientation = gtk_orientable_get_orientation (GTK_ORIENTABLE (parent));
81   gtk_orientable_set_orientation (GTK_ORIENTABLE (parent), 1 - orientation);
82
83   if (orientation == GTK_ORIENTATION_VERTICAL)
84     g_object_set (menubar, "pack-direction", GTK_PACK_DIRECTION_TTB, NULL);
85   else
86     g_object_set (menubar, "pack-direction", GTK_PACK_DIRECTION_LTR, NULL);
87
88 }
89
90 static GtkWidget *window = NULL;
91
92 GtkWidget *
93 do_menus (GtkWidget *do_widget)
94 {
95   GtkWidget *box;
96   GtkWidget *box1;
97   GtkWidget *box2;
98   GtkWidget *button;
99
100   if (!window)
101     {
102       GtkWidget *menubar;
103       GtkWidget *menu;
104       GtkWidget *menuitem;
105       GtkAccelGroup *accel_group;
106
107       window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
108       gtk_window_set_screen (GTK_WINDOW (window),
109                              gtk_widget_get_screen (do_widget));
110       gtk_window_set_title (GTK_WINDOW (window), "Menus");
111       g_signal_connect (window, "destroy",
112                         G_CALLBACK(gtk_widget_destroyed), &window);
113
114       accel_group = gtk_accel_group_new ();
115       gtk_window_add_accel_group (GTK_WINDOW (window), accel_group);
116
117       gtk_container_set_border_width (GTK_CONTAINER (window), 0);
118
119       box = gtk_box_new (GTK_ORIENTATION_HORIZONTAL, 0);
120       gtk_container_add (GTK_CONTAINER (window), box);
121       gtk_widget_show (box);
122
123       box1 = gtk_box_new (GTK_ORIENTATION_VERTICAL, 0);
124       gtk_container_add (GTK_CONTAINER (box), box1);
125       gtk_widget_show (box1);
126
127       menubar = gtk_menu_bar_new ();
128       gtk_box_pack_start (GTK_BOX (box1), menubar, FALSE, TRUE, 0);
129       gtk_widget_show (menubar);
130
131       menu = create_menu (2, TRUE);
132
133       menuitem = gtk_menu_item_new_with_label ("test\nline2");
134       gtk_menu_item_set_submenu (GTK_MENU_ITEM (menuitem), menu);
135       gtk_menu_shell_append (GTK_MENU_SHELL (menubar), menuitem);
136       gtk_widget_show (menuitem);
137
138       menuitem = gtk_menu_item_new_with_label ("foo");
139       gtk_menu_item_set_submenu (GTK_MENU_ITEM (menuitem), create_menu (3, TRUE));
140       gtk_menu_shell_append (GTK_MENU_SHELL (menubar), menuitem);
141       gtk_widget_show (menuitem);
142
143       menuitem = gtk_menu_item_new_with_label ("bar");
144       gtk_menu_item_set_submenu (GTK_MENU_ITEM (menuitem), create_menu (4, TRUE));
145       gtk_menu_shell_append (GTK_MENU_SHELL (menubar), menuitem);
146       gtk_widget_show (menuitem);
147
148       box2 = gtk_box_new (GTK_ORIENTATION_VERTICAL, 10);
149       gtk_container_set_border_width (GTK_CONTAINER (box2), 10);
150       gtk_box_pack_start (GTK_BOX (box1), box2, FALSE, TRUE, 0);
151       gtk_widget_show (box2);
152
153       button = gtk_button_new_with_label ("Flip");
154       g_signal_connect (button, "clicked",
155                         G_CALLBACK (change_orientation), menubar);
156       gtk_box_pack_start (GTK_BOX (box2), button, TRUE, TRUE, 0);
157       gtk_widget_show (button);
158
159       button = gtk_button_new_with_label ("Close");
160       g_signal_connect_swapped (button, "clicked",
161                                 G_CALLBACK(gtk_widget_destroy), window);
162       gtk_box_pack_start (GTK_BOX (box2), button, TRUE, TRUE, 0);
163       gtk_widget_set_can_default (button, TRUE);
164       gtk_widget_grab_default (button);
165       gtk_widget_show (button);
166     }
167
168   if (!gtk_widget_get_visible (window))
169     {
170       gtk_widget_show (window);
171     }
172   else
173     {
174       gtk_widget_destroy (window);
175       window = NULL;
176     }
177
178   return window;
179 }