gwenhywfar 5.14.1
gtk2/w_listbox.c
Go to the documentation of this file.
1/***************************************************************************
2 begin : Fri Jul 09 2010
3 copyright : (C) 2010 by Martin Preuss
4 email : martin@libchipcard.de
5
6 ***************************************************************************
7 * Please see toplevel file COPYING for license details *
8 ***************************************************************************/
9
10
11#define W_LISTBOX_MAX_TYPES 256
12
13
14
15static GWENHYWFAR_CB
18 int index,
19 int value,
20 GWEN_UNUSED int doSignal)
21{
22 GtkWidget *g;
23
25 assert(g);
26
27 switch (prop) {
29 gtk_widget_set_sensitive(GTK_WIDGET(g), (value==0)?FALSE:TRUE);
30 return 0;
31
33 gtk_widget_grab_focus(GTK_WIDGET(g));
34 return 0;
35
37 GtkTreePath *path;
38
39 path=gtk_tree_path_new_from_indices(value, -1);
40 gtk_tree_view_set_cursor(GTK_TREE_VIEW(g), path, NULL, FALSE);
41 gtk_tree_path_free(path);
42 return 0;
43 }
44
46 GtkTreeSelection *sel;
47
48 sel=gtk_tree_view_get_selection(GTK_TREE_VIEW(g));
49 if (sel) {
50 switch (value) {
52 gtk_tree_selection_set_mode(sel, GTK_SELECTION_NONE);
53 return 0;
55 gtk_tree_selection_set_mode(sel, GTK_SELECTION_SINGLE);
56 return 0;
58 gtk_tree_selection_set_mode(sel, GTK_SELECTION_MULTIPLE);
59 return 0;
60 }
61 DBG_ERROR(GWEN_LOGDOMAIN, "Unknown SelectionMode %d", value);
62 return GWEN_ERROR_INVALID;
63 }
64 break;
65 }
66
68 GtkTreeViewColumn *col;
69
70 col=gtk_tree_view_get_column(GTK_TREE_VIEW(g), index);
71 if (col) {
72 gtk_tree_view_column_set_fixed_width(col, value);
73 return 0;
74 }
75
76 /* no width */
77 return GWEN_ERROR_INVALID;
78 }
79
81 GtkTreeViewColumn *col;
82 int i;
83 int cols;
84
85 /* remove sort indicator from all columns */
87 for (i=0; i<cols; i++) {
88 col=gtk_tree_view_get_column(GTK_TREE_VIEW(g), index);
89 if (col) {
90 if (gtk_tree_view_column_get_sort_indicator(col)==TRUE)
91 gtk_tree_view_column_set_sort_indicator(col, FALSE);
92 }
93 }
94
96 /* set sort indicator on given column */
97 col=gtk_tree_view_get_column(GTK_TREE_VIEW(g), index);
98 if (col) {
99 switch (value) {
101 gtk_tree_view_column_set_sort_order(col, GTK_SORT_ASCENDING);
102 break;
104 gtk_tree_view_column_set_sort_order(col, GTK_SORT_DESCENDING);
105 break;
106 default:
107 break;
108 }
109 }
110 }
111
112 return 0;
113 }
114
116 GtkListStore *sto;
117
118 sto=GTK_LIST_STORE(gtk_tree_view_get_model(GTK_TREE_VIEW(g)));
119 if (sto)
120 gtk_list_store_clear(sto);
121 return 0;
122 }
123
125 /* NOOP, we use auto-sorting for now (TODO: figure out how to manually sort) */
126 return 0;
127
128 default:
129 break;
130 }
131
133 "Function is not appropriate for this type of widget (%s)",
135 return GWEN_ERROR_INVALID;
136}
137
138
139
140
141static GWENHYWFAR_CB
144 int index,
145 int defaultValue)
146{
147 GtkWidget *g;
148
150 assert(g);
151
152 switch (prop) {
154 return (gtk_widget_get_sensitive(GTK_WIDGET(g))==TRUE)?1:0;
155
157 return (gtk_widget_has_focus(GTK_WIDGET(g))==TRUE)?1:0;
158 return 0;
159
161 GtkTreePath *path=NULL;
162
163 gtk_tree_view_get_cursor(GTK_TREE_VIEW(g), &path, NULL);
164 if (path!=NULL) {
165 gint *idxlist;
166
167 idxlist=gtk_tree_path_get_indices(path);
168 if (idxlist!=NULL) {
169 int res;
170
171 res=idxlist[0];
172 gtk_tree_path_free(path);
173 return res;
174 }
175 gtk_tree_path_free(path);
176 }
177
178 /* no cursor */
179 return -1;
180 }
181
183 GtkTreeViewColumn *col;
184
185 col=gtk_tree_view_get_column(GTK_TREE_VIEW(g), index);
186 if (col)
187 return gtk_tree_view_column_get_width(col);
188
189 /* no width */
190 return -1;
191 }
192
194 GtkTreeViewColumn *col;
195
196 col=gtk_tree_view_get_column(GTK_TREE_VIEW(g), index);
197 if (col) {
198 if (gtk_tree_view_column_get_sort_indicator(col)==TRUE) {
199 switch (gtk_tree_view_column_get_sort_order(col)) {
200 case GTK_SORT_ASCENDING:
202 case GTK_SORT_DESCENDING:
204 default:
205 break;
206 }
207 }
208 /*break; <- this is wrong here, isn't it? */
209 }
210
212 }
213
214 default:
215 break;
216 }
217
219 "Function %d is not appropriate for this type of widget (%s)",
220 prop,
222 return defaultValue;
223}
224
225
226
227static GWENHYWFAR_CB
230 GWEN_UNUSED int index,
231 const char *value,
232 GWEN_UNUSED int doSignal)
233{
234 GtkWidget *g;
235
237 assert(g);
238
239 switch (prop) {
241 int cols=0;
242 if (value && *value) {
243 int i;
244 int l;
245
246 l=strlen(value);
247 cols=1;
248 for (i=0; i<l; i++) {
249 if (value[i]=='\t')
250 cols++;
251 }
252 }
253
254 if (cols) {
255 GType types[W_LISTBOX_MAX_TYPES];
256 GtkListStore *sto;
257 int i;
258 /*const char *s;*/
259 GtkTreeViewColumn *col;
260 char *vcopy;
261 char *p;
262
263 if (cols>W_LISTBOX_MAX_TYPES)
265 for (i=0; i<cols; i++)
266 types[i]=G_TYPE_STRING;
267 sto=gtk_list_store_newv(cols, types);
268 /*s=value;*/
269
270 /* clear current headers in tree view */
271 while ((col=gtk_tree_view_get_column(GTK_TREE_VIEW(g), 0)))
272 gtk_tree_view_remove_column(GTK_TREE_VIEW(g), col);
273
274 /* set new model */
275 gtk_tree_view_set_model(GTK_TREE_VIEW(g), GTK_TREE_MODEL(sto));
276
277 /* insert new headers */
278 i=0;
279 vcopy=strdup(value);
280 p=vcopy;
281 while (*p && i<cols) {
282 char *pT;
283 GtkCellRenderer *renderer;
284
285 pT=strchr(p, '\t');
286 if (pT)
287 *pT=0;
288
289 renderer=gtk_cell_renderer_text_new();
290 col=gtk_tree_view_column_new();
291 gtk_tree_view_column_set_title(col, p);
292 gtk_tree_view_column_pack_start(col, renderer, TRUE);
293 gtk_tree_view_column_set_sort_column_id(col, i);
294 gtk_tree_view_column_set_resizable(col, TRUE);
295 gtk_tree_view_column_set_sizing(col, GTK_TREE_VIEW_COLUMN_FIXED);
296 gtk_tree_view_column_set_attributes(col, renderer, "text", i, NULL);
297
298 gtk_tree_view_append_column(GTK_TREE_VIEW(g), col);
299
300 if (pT)
301 p=pT+1;
302 else
303 /* no more tab, all columns done */
304 break;
305 i++;
306 }
307 free(vcopy);
308 GWEN_Widget_SetColumns(w, cols);
309 gtk_tree_view_set_headers_visible(GTK_TREE_VIEW(g), TRUE);
310 }
311 else {
312 DBG_ERROR(GWEN_LOGDOMAIN, "No columns (empty title)");
313 return GWEN_ERROR_INVALID;
314 }
315
316 return 0;
317 }
318
320 GtkListStore *sto;
321
322 sto=GTK_LIST_STORE(gtk_tree_view_get_model(GTK_TREE_VIEW(g)));
323 if (sto)
324 gtk_list_store_clear(sto);
325 return 0;
326 }
327
329 GtkListStore *sto;
330
331 sto=GTK_LIST_STORE(gtk_tree_view_get_model(GTK_TREE_VIEW(g)));
332 if (sto) {
333 GtkTreeIter iter;
334 int cols;
335 int i;
336 char *vcopy;
337 char *p;
338
340
341 vcopy=strdup(value);
342 p=vcopy;
343 i=0;
344 gtk_list_store_append(sto, &iter);
345 while (*p && i<cols) {
346 char *pT;
347 GValue val= {0};
348
349 g_value_init(&val, G_TYPE_STRING);
350
351 pT=strchr(p, '\t');
352 if (pT)
353 *pT=0;
354 g_value_set_string(&val, p);
355 gtk_list_store_set_value(sto, &iter, i, &val);
356 g_value_unset(&val);
357
358 if (pT)
359 p=pT+1;
360 else
361 /* no more tabs, all columns done */
362 break;
363 i++;
364 }
365 free(vcopy);
366 }
367
368 return 0;
369 }
370
371 default:
372 break;
373 }
374
376 "Function is not appropriate for this type of widget (%s)",
378 return GWEN_ERROR_INVALID;
379}
380
381
382
383static GWENHYWFAR_CB
386 int index,
387 const char *defaultValue)
388{
389 GtkWidget *g;
390
392 assert(g);
393
394 switch (prop) {
396 GList *cols;
397
398 cols=gtk_tree_view_get_columns(GTK_TREE_VIEW(g));
399 if (cols) {
400 GList *le;
401 GWEN_BUFFER *tbuf;
402 int cnt=0;
403
404 tbuf=GWEN_Buffer_new(0, 256, 0, 1);
405 le=g_list_first(cols);
406 while (le) {
407 const gchar *s;
408
409 if (cnt)
410 GWEN_Buffer_AppendByte(tbuf, '\t');
411 s=gtk_tree_view_column_get_title(GTK_TREE_VIEW_COLUMN(le->data));
412 if (s && *s)
414 cnt++;
415 le=g_list_next(le);
416 } /* while */
418 GWEN_Buffer_free(tbuf);
419
420 g_list_free(cols);
422 }
423 return defaultValue;
424 }
425
427 GtkTreePath *path;
428
429 path=gtk_tree_path_new_from_indices(index, -1);
430 if (path!=NULL) {
431 GtkListStore *sto;
432 GtkTreeIter iter;
433
434 sto=GTK_LIST_STORE(gtk_tree_view_get_model(GTK_TREE_VIEW(g)));
435 if (gtk_tree_model_get_iter(GTK_TREE_MODEL(sto), &iter, path)) {
436 GList *cols;
437
438 cols=gtk_tree_view_get_columns(GTK_TREE_VIEW(g));
439 if (cols) {
440 GList *le;
441 GWEN_BUFFER *tbuf;
442 int cnt=0;
443
444 tbuf=GWEN_Buffer_new(0, 256, 0, 1);
445 le=g_list_first(cols);
446 while (le) {
447 gchar *s;
448
449 if (cnt)
450 GWEN_Buffer_AppendByte(tbuf, '\t');
451 gtk_tree_model_get(GTK_TREE_MODEL(sto), &iter, cnt, &s, -1, NULL);
452 if (s) {
454 g_free(s);
455 }
456 cnt++;
457 le=g_list_next(le);
458 } /* while */
460 GWEN_Buffer_free(tbuf);
461
462 g_list_free(cols);
464 }
465 }
466
467 gtk_tree_path_free(path);
468 }
469 return defaultValue;
470 }
471
472 default:
473 break;
474 }
475
477 "Function is not appropriate for this type of widget (%s)",
479 return defaultValue;
480}
481
482
483
499
500
501
503{
504 GtkWidget *g;
505 GtkWidget *gScroll;
506 /*uint32_t flags;*/
507 GWEN_WIDGET *wParent;
508 /*gulong changed_handler_id;*/
509
510 /*flags=GWEN_Widget_GetFlags(w);*/
511 wParent=GWEN_Widget_Tree_GetParent(w);
512
513 gScroll=gtk_scrolled_window_new(NULL, NULL);
514 gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(gScroll),
515 GTK_POLICY_AUTOMATIC,
516 GTK_POLICY_AUTOMATIC);
517 g=gtk_tree_view_new();
518 gtk_tree_view_set_headers_clickable(GTK_TREE_VIEW(g), TRUE);
519 gtk_tree_view_set_rules_hint(GTK_TREE_VIEW(g), TRUE);
520 gtk_container_add(GTK_CONTAINER(gScroll), GTK_WIDGET(g));
521
524
529
530 /*changed_handler_id=*/g_signal_connect(g,
531 "cursor-changed",
533 w);
534
535 if (wParent)
537
538 return 0;
539}
540
541
#define NULL
Definition binreloc.c:300
GWEN_BUFFER * GWEN_Buffer_new(char *buffer, uint32_t size, uint32_t used, int take)
Definition buffer.c:42
void GWEN_Buffer_free(GWEN_BUFFER *bf)
Definition buffer.c:89
int GWEN_Buffer_AppendString(GWEN_BUFFER *bf, const char *buffer)
Definition buffer.c:992
char * GWEN_Buffer_GetStart(const GWEN_BUFFER *bf)
Definition buffer.c:235
int GWEN_Buffer_AppendByte(GWEN_BUFFER *bf, char c)
Definition buffer.c:393
#define DBG_ERROR(dbg_logger, format,...)
Definition debug.h:97
#define DBG_WARN(dbg_logger, format,...)
Definition debug.h:125
int GWEN_Dialog_EmitSignal(GWEN_DIALOG *dlg, GWEN_DIALOG_EVENTTYPE t, const char *sender)
Definition dialog.c:321
@ GWEN_DialogSortDirection_None
Definition dialog.h:297
@ GWEN_DialogSortDirection_Up
Definition dialog.h:298
@ GWEN_DialogSortDirection_Down
Definition dialog.h:299
GWEN_DIALOG_PROPERTY
Definition dialog.h:260
@ GWEN_DialogProperty_AddValue
Definition dialog.h:268
@ GWEN_DialogProperty_ColumnWidth
Definition dialog.h:271
@ GWEN_DialogProperty_Title
Definition dialog.h:263
@ GWEN_DialogProperty_Sort
Definition dialog.h:279
@ GWEN_DialogProperty_ClearValues
Definition dialog.h:269
@ GWEN_DialogProperty_SelectionMode
Definition dialog.h:274
@ GWEN_DialogProperty_SortDirection
Definition dialog.h:278
@ GWEN_DialogProperty_Enabled
Definition dialog.h:267
@ GWEN_DialogProperty_Value
Definition dialog.h:264
@ GWEN_DialogProperty_Focus
Definition dialog.h:276
@ GWEN_DialogEvent_TypeActivated
Definition dialog.h:102
@ GWEN_DialogEvent_ResultAccept
Definition dialog.h:122
@ GWEN_DialogEvent_ResultReject
Definition dialog.h:123
@ GWEN_Dialog_SelectionMode_None
Definition dialog.h:290
@ GWEN_Dialog_SelectionMode_Multi
Definition dialog.h:292
@ GWEN_Dialog_SelectionMode_Single
Definition dialog.h:291
#define GWEN_ERROR_INVALID
Definition error.h:67
struct GWEN_BUFFER GWEN_BUFFER
A dynamically resizeable text buffer.
Definition buffer.h:38
static void Gtk2Gui_WListBox_CursorChanged_handler(GWEN_UNUSED GtkTreeView *g, gpointer data)
int Gtk2Gui_WListBox_Setup(GWEN_WIDGET *w)
static GWENHYWFAR_CB const char * Gtk2Gui_WListBox_GetCharProperty(GWEN_WIDGET *w, GWEN_DIALOG_PROPERTY prop, int index, const char *defaultValue)
static GWENHYWFAR_CB int Gtk2Gui_WListBox_GetIntProperty(GWEN_WIDGET *w, GWEN_DIALOG_PROPERTY prop, int index, int defaultValue)
static GWENHYWFAR_CB int Gtk2Gui_WListBox_SetIntProperty(GWEN_WIDGET *w, GWEN_DIALOG_PROPERTY prop, int index, int value, GWEN_UNUSED int doSignal)
static GWENHYWFAR_CB int Gtk2Gui_WListBox_SetCharProperty(GWEN_WIDGET *w, GWEN_DIALOG_PROPERTY prop, GWEN_UNUSED int index, const char *value, GWEN_UNUSED int doSignal)
#define GTK2_DIALOG_WIDGET_REAL
#define GTK2_DIALOG_WIDGET_CONTENT
#define GTK2_DIALOG_STRING_TITLE
#define GTK2_DIALOG_STRING_VALUE
void Gtk2Gui_Dialog_Leave(GWEN_DIALOG *dlg, int result)
#define GWEN_UNUSED
#define GWENHYWFAR_CB
#define GWEN_LOGDOMAIN
Definition logger.h:32
#define W_LISTBOX_MAX_TYPES
Definition w_listbox.mm:14
GWEN_WIDGET_GETCHARPROPERTY_FN GWEN_Widget_SetGetCharPropertyFn(GWEN_WIDGET *w, GWEN_WIDGET_GETCHARPROPERTY_FN fn)
Definition widget.c:740
void GWEN_Widget_SetColumns(GWEN_WIDGET *w, int i)
Definition widget.c:212
GWEN_DIALOG * GWEN_Widget_GetTopDialog(const GWEN_WIDGET *w)
Definition widget.c:102
int GWEN_Widget_GetColumns(const GWEN_WIDGET *w)
Definition widget.c:203
const char * GWEN_Widget_GetName(const GWEN_WIDGET *w)
Definition widget.c:320
GWEN_WIDGET_GETINTPROPERTY_FN GWEN_Widget_SetGetIntPropertyFn(GWEN_WIDGET *w, GWEN_WIDGET_GETINTPROPERTY_FN fn)
Definition widget.c:710
int GWEN_Widget_AddChildGuiWidget(GWEN_WIDGET *w, GWEN_WIDGET *wChild)
Definition widget.c:836
void GWEN_Widget_SetImplData(GWEN_WIDGET *w, int index, void *ptr)
Store a pointer with the widget.
Definition widget.c:136
void * GWEN_Widget_GetImplData(const GWEN_WIDGET *w, int index)
Definition widget.c:122
GWEN_WIDGET_SETINTPROPERTY_FN GWEN_Widget_SetSetIntPropertyFn(GWEN_WIDGET *w, GWEN_WIDGET_SETINTPROPERTY_FN fn)
Definition widget.c:695
void GWEN_Widget_SetText(GWEN_WIDGET *w, int idx, const char *s)
Definition widget.c:304
const char * GWEN_Widget_GetText(const GWEN_WIDGET *w, int idx)
Definition widget.c:293
const char * GWEN_Widget_Type_toString(GWEN_WIDGET_TYPE t)
Definition widget.c:456
GWEN_DIALOG * GWEN_Widget_GetDialog(const GWEN_WIDGET *w)
Definition widget.c:92
GWEN_WIDGET_TYPE GWEN_Widget_GetType(const GWEN_WIDGET *w)
Definition widget.c:185
GWEN_WIDGET_SETCHARPROPERTY_FN GWEN_Widget_SetSetCharPropertyFn(GWEN_WIDGET *w, GWEN_WIDGET_SETCHARPROPERTY_FN fn)
Definition widget.c:725
struct GWEN_WIDGET GWEN_WIDGET
Definition widget_be.h:34