]> Pileus Git - ~andy/gtk/blob - tests/testcombochange.c
Merge branch 'gdk-backend-wayland'
[~andy/gtk] / tests / testcombochange.c
1 /* testcombochange.c
2  * Copyright (C) 2004  Red Hat, Inc.
3  * Author: Owen Taylor
4  *
5  * This library is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU Library General Public
7  * License as published by the Free Software Foundation; either
8  * version 2 of the License, or (at your option) any later version.
9  *
10  * This library is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  * Library General Public License for more details.
14  *
15  * You should have received a copy of the GNU Library General Public
16  * License along with this library; if not, write to the
17  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
18  * Boston, MA 02111-1307, USA.
19  */
20
21 #include "config.h"
22 #include <gtk/gtk.h>
23 #include <stdarg.h>
24
25 GtkWidget *text_view;
26 GtkListStore *model;
27 GArray *contents;
28
29 static char next_value = 'A';
30
31 static void
32 test_init (void)
33 {
34   if (g_file_test ("../modules/input/immodules.cache", G_FILE_TEST_EXISTS))
35     g_setenv ("GTK_IM_MODULE_FILE", "../modules/input/immodules.cache", TRUE);
36 }
37
38 static void
39 combochange_log (const char *fmt,
40      ...)
41 {
42   GtkTextBuffer *buffer = gtk_text_view_get_buffer (GTK_TEXT_VIEW (text_view));
43   GtkTextIter iter;
44   va_list vap;
45   char *msg;
46   GString *order_string;
47   GtkTextMark *tmp_mark;
48   int i;
49
50   va_start (vap, fmt);
51   
52   msg = g_strdup_vprintf (fmt, vap);
53
54   gtk_text_buffer_get_end_iter (buffer, &iter);
55   gtk_text_buffer_insert (buffer, &iter, msg, -1);
56
57   order_string = g_string_new ("\n  ");
58   for (i = 0; i < contents->len; i++)
59     {
60       if (i)
61         g_string_append_c (order_string, ' ');
62       g_string_append_c (order_string, g_array_index (contents, char, i));
63     }
64   g_string_append_c (order_string, '\n');
65   gtk_text_buffer_insert (buffer, &iter, order_string->str, -1);
66   g_string_free (order_string, TRUE);
67
68   tmp_mark = gtk_text_buffer_create_mark (buffer, NULL, &iter, FALSE);
69   gtk_text_view_scroll_mark_onscreen (GTK_TEXT_VIEW (text_view), tmp_mark);
70   gtk_text_buffer_delete_mark (buffer, tmp_mark);
71
72   g_free (msg);
73 }
74
75 static GtkWidget *
76 align_button_new (const char *text)
77 {
78   GtkWidget *button = gtk_button_new ();
79   GtkWidget *label = gtk_label_new (text);
80
81   gtk_container_add (GTK_CONTAINER (button), label);
82   gtk_misc_set_alignment (GTK_MISC (label), 0.0, 0.5);
83
84   return button;
85 }
86
87 static GtkWidget *
88 create_combo (const char *name,
89               gboolean is_list)
90 {
91   GtkCellRenderer *cell_renderer;
92   GtkWidget *combo;
93   GtkCssProvider *provider;
94   GtkStyleContext *context;
95   gchar *css_data;
96
97   combo = gtk_combo_box_new_with_model (GTK_TREE_MODEL (model));
98   cell_renderer = gtk_cell_renderer_text_new ();
99   gtk_cell_layout_pack_start (GTK_CELL_LAYOUT (combo), cell_renderer, TRUE);
100   gtk_cell_layout_set_attributes (GTK_CELL_LAYOUT (combo), cell_renderer,
101                                   "text", 0, NULL);
102
103   gtk_widget_set_name (combo, name);
104
105   context = gtk_widget_get_style_context (combo);
106
107   provider = gtk_css_provider_new ();
108   css_data = g_strdup_printf ("#%s { -GtkComboBox-appears-as-list: %s }",
109                               name, is_list ? "true" : "false");
110   gtk_css_provider_load_from_data (provider, css_data, -1, NULL);
111   g_free (css_data);
112
113   gtk_style_context_add_provider (context,
114                                   GTK_STYLE_PROVIDER (provider),
115                                   GTK_STYLE_PROVIDER_PRIORITY_APPLICATION);
116
117   return combo;
118 }
119
120 static void
121 on_insert (void)
122 {
123   GtkTreeIter iter;
124   
125   int insert_pos;
126   char new_value[2];
127
128   new_value[0] = next_value++;
129   new_value[1] = '\0';
130
131   if (next_value > 'Z')
132     next_value = 'A';
133   
134   if (contents->len)
135     insert_pos = g_random_int_range (0, contents->len + 1);
136   else
137     insert_pos = 0;
138   
139   gtk_list_store_insert (model, &iter, insert_pos);
140   gtk_list_store_set (model, &iter, 0, new_value, -1);
141
142   g_array_insert_val (contents, insert_pos, new_value);
143
144   combochange_log ("Inserted '%c' at position %d", new_value[0], insert_pos);
145 }
146
147 static void
148 on_delete (void)
149 {
150   GtkTreeIter iter;
151   
152   int delete_pos;
153   char old_val;
154
155   if (!contents->len)
156     return;
157   
158   delete_pos = g_random_int_range (0, contents->len);
159   gtk_tree_model_iter_nth_child (GTK_TREE_MODEL (model), &iter, NULL, delete_pos);
160   
161   gtk_list_store_remove (model, &iter);
162
163   old_val = g_array_index (contents, char, delete_pos);
164   g_array_remove_index (contents, delete_pos);
165   combochange_log ("Deleted '%c' from position %d", old_val, delete_pos);
166 }
167
168 static void
169 on_reorder (void)
170 {
171   GArray *new_contents;
172   gint *shuffle_array;
173   gint i;
174
175   shuffle_array = g_new (int, contents->len);
176   
177   for (i = 0; i < contents->len; i++)
178     shuffle_array[i] = i;
179
180   for (i = 0; i + 1 < contents->len; i++)
181     {
182       gint pos = g_random_int_range (i, contents->len);
183       gint tmp;
184
185       tmp = shuffle_array[i];
186       shuffle_array[i] = shuffle_array[pos];
187       shuffle_array[pos] = tmp;
188     }
189
190   gtk_list_store_reorder (model, shuffle_array);
191
192   new_contents = g_array_new (FALSE, FALSE, sizeof (char));
193   for (i = 0; i < contents->len; i++)
194     g_array_append_val (new_contents,
195                         g_array_index (contents, char, shuffle_array[i]));
196   g_array_free (contents, TRUE);
197   contents = new_contents;
198
199   combochange_log ("Reordered array");
200     
201   g_free (shuffle_array);
202 }
203
204 static int n_animations = 0;
205 static int timer = 0;
206
207 static gint
208 animation_timer (gpointer data)
209 {
210   switch (g_random_int_range (0, 3)) 
211     {
212     case 0: 
213       on_insert ();
214       break;
215     case 1:
216       on_delete ();
217       break;
218     case 2:
219       on_reorder ();
220       break;
221     }
222
223   n_animations--;
224   return n_animations > 0;
225 }
226
227 static void
228 on_animate (void)
229 {
230   n_animations += 20;
231  
232   timer = gdk_threads_add_timeout (1000, (GSourceFunc) animation_timer, NULL);
233 }
234
235 int
236 main (int argc, char **argv)
237 {
238   GtkWidget *content_area;
239   GtkWidget *dialog;
240   GtkWidget *scrolled_window;
241   GtkWidget *hbox;
242   GtkWidget *button_vbox;
243   GtkWidget *combo_vbox;
244   GtkWidget *button;
245   GtkWidget *menu_combo;
246   GtkWidget *alignment;
247   GtkWidget *label;
248   GtkWidget *list_combo;
249   
250   test_init ();
251
252   gtk_init (&argc, &argv);
253
254   model = gtk_list_store_new (1, G_TYPE_STRING);
255   contents = g_array_new (FALSE, FALSE, sizeof (char));
256   
257   dialog = gtk_dialog_new_with_buttons ("GtkComboBox model changes",
258                                         NULL, 0,
259                                         GTK_STOCK_CLOSE, GTK_RESPONSE_CLOSE,
260                                         NULL);
261
262   content_area = gtk_dialog_get_content_area (GTK_DIALOG (dialog));
263
264   hbox = gtk_box_new (GTK_ORIENTATION_HORIZONTAL, 12);
265   gtk_container_set_border_width (GTK_CONTAINER (hbox), 12);
266   gtk_box_pack_start (GTK_BOX (content_area), hbox, TRUE, TRUE, 0);
267
268   combo_vbox = gtk_box_new (GTK_ORIENTATION_VERTICAL, 8);
269   gtk_box_pack_start (GTK_BOX (hbox), combo_vbox, FALSE, FALSE, 0);
270
271   label = gtk_label_new (NULL);
272   gtk_label_set_markup (GTK_LABEL (label), "<b>Menu mode</b>");
273   gtk_misc_set_alignment (GTK_MISC (label), 0.0, 0.5);
274   gtk_box_pack_start (GTK_BOX (combo_vbox), label, FALSE, FALSE, 0);
275
276   alignment = g_object_new (GTK_TYPE_ALIGNMENT, "left-padding", 12, NULL);
277   gtk_box_pack_start (GTK_BOX (combo_vbox), alignment, FALSE, FALSE, 0);
278
279   menu_combo = create_combo ("menu-combo", FALSE);
280   gtk_container_add (GTK_CONTAINER (alignment), menu_combo);
281
282   label = gtk_label_new (NULL);
283   gtk_label_set_markup (GTK_LABEL (label), "<b>List mode</b>");
284   gtk_misc_set_alignment (GTK_MISC (label), 0.0, 0.5);
285   gtk_box_pack_start (GTK_BOX (combo_vbox), label, FALSE, FALSE, 0);
286
287   alignment = g_object_new (GTK_TYPE_ALIGNMENT, "left-padding", 12, NULL);
288   gtk_box_pack_start (GTK_BOX (combo_vbox), alignment, FALSE, FALSE, 0);
289
290   list_combo = create_combo ("list-combo", TRUE);
291   gtk_container_add (GTK_CONTAINER (alignment), list_combo);
292
293   scrolled_window = gtk_scrolled_window_new (NULL, NULL);
294   gtk_box_pack_start (GTK_BOX (hbox), scrolled_window, TRUE, TRUE, 0);
295   gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (scrolled_window),
296                                   GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC);
297
298   text_view = gtk_text_view_new ();
299   gtk_text_view_set_editable (GTK_TEXT_VIEW (text_view), FALSE);
300   gtk_text_view_set_cursor_visible (GTK_TEXT_VIEW (text_view), FALSE);
301
302   gtk_container_add (GTK_CONTAINER (scrolled_window), text_view);
303
304   button_vbox = gtk_box_new (GTK_ORIENTATION_VERTICAL, 8);
305   gtk_box_pack_start (GTK_BOX (hbox), button_vbox, FALSE, FALSE, 0);
306   
307   gtk_window_set_default_size (GTK_WINDOW (dialog), 500, 300);
308
309   button = align_button_new ("Insert");
310   gtk_box_pack_start (GTK_BOX (button_vbox), button, FALSE, FALSE, 0);
311   g_signal_connect (button, "clicked", G_CALLBACK (on_insert), NULL);
312   
313   button = align_button_new ("Delete");
314   gtk_box_pack_start (GTK_BOX (button_vbox), button, FALSE, FALSE, 0);
315   g_signal_connect (button, "clicked", G_CALLBACK (on_delete), NULL);
316
317   button = align_button_new ("Reorder");
318   gtk_box_pack_start (GTK_BOX (button_vbox), button, FALSE, FALSE, 0);
319   g_signal_connect (button, "clicked", G_CALLBACK (on_reorder), NULL);
320
321   button = align_button_new ("Animate");
322   gtk_box_pack_start (GTK_BOX (button_vbox), button, FALSE, FALSE, 0);
323   g_signal_connect (button, "clicked", G_CALLBACK (on_animate), NULL);
324
325   gtk_widget_show_all (dialog);
326   gtk_dialog_run (GTK_DIALOG (dialog));
327
328   return 0;
329 }