import homebank-5.1.2
[chaz/homebank] / src / ui-assign.c
1 /* HomeBank -- Free, easy, personal ruleing for everyone.
2 * Copyright (C) 1995-2016 Maxime DOYEN
3 *
4 * This file is part of HomeBank.
5 *
6 * HomeBank is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * HomeBank is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program. If not, see <http://www.gnu.org/licenses/>.
18 */
19
20 #include "homebank.h"
21
22 #include "ui-assign.h"
23
24 #include "ui-category.h"
25 #include "ui-payee.h"
26
27 #define MYDEBUG 0
28
29 #if MYDEBUG
30 #define DB(x) (x);
31 #else
32 #define DB(x);
33 #endif
34
35 /* our global datas */
36 extern struct HomeBank *GLOBALS;
37
38 gchar *CYA_ASG_FIELD[] = {
39 N_("Memo"),
40 N_("Payee"),
41 NULL
42 };
43
44 /* = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = */
45
46
47 /* = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = */
48
49
50 static void
51 ui_asg_listview_toggled_cb (GtkCellRendererToggle *cell,
52 gchar *path_str,
53 gpointer data)
54 {
55 GtkTreeModel *model = (GtkTreeModel *)data;
56 GtkTreeIter iter;
57 GtkTreePath *path = gtk_tree_path_new_from_string (path_str);
58 gboolean fixed;
59
60 /* get toggled iter */
61 gtk_tree_model_get_iter (model, &iter, path);
62 gtk_tree_model_get (model, &iter, LST_DEFASG_TOGGLE, &fixed, -1);
63
64 /* do something with the value */
65 fixed ^= 1;
66
67 /* set new value */
68 gtk_list_store_set (GTK_LIST_STORE (model), &iter, LST_DEFASG_TOGGLE, fixed, -1);
69
70 /* clean up */
71 gtk_tree_path_free (path);
72 }
73
74 static gint
75 ui_asg_listview_compare_func (GtkTreeModel *model, GtkTreeIter *a, GtkTreeIter *b, gpointer userdata)
76 {
77 Assign *entry1, *entry2;
78
79 gtk_tree_model_get(model, a, LST_DEFASG_DATAS, &entry1, -1);
80 gtk_tree_model_get(model, b, LST_DEFASG_DATAS, &entry2, -1);
81
82 return hb_string_utf8_compare(entry1->text, entry2->text);
83 }
84
85 static void
86 ui_asg_listview_name_cell_data_function (GtkTreeViewColumn *col,
87 GtkCellRenderer *renderer,
88 GtkTreeModel *model,
89 GtkTreeIter *iter,
90 gpointer user_data)
91 {
92 Assign *entry;
93 gchar *name;
94 #if MYDEBUG
95 gchar *string;
96 #endif
97
98 gtk_tree_model_get(model, iter, LST_DEFASG_DATAS, &entry, -1);
99 if(entry->text == NULL)
100 name = _("(none)"); // can never occurs also
101 else
102 name = entry->text;
103
104 #if MYDEBUG
105 string = g_strdup_printf ("[%d] %s", entry->key, name );
106 g_object_set(renderer, "text", string, NULL);
107 g_free(string);
108 #else
109 g_object_set(renderer, "text", name, NULL);
110 #endif
111
112 }
113
114
115
116 /* = = = = = = = = = = = = = = = = */
117
118 /**
119 * rul_list_add:
120 *
121 * Add a single element (useful for dynamics add)
122 *
123 * Return value: --
124 *
125 */
126 void
127 ui_asg_listview_add(GtkTreeView *treeview, Assign *item)
128 {
129 if( item->text != NULL )
130 {
131 GtkTreeModel *model;
132 GtkTreeIter iter;
133
134 model = gtk_tree_view_get_model(treeview);
135
136 gtk_list_store_append (GTK_LIST_STORE(model), &iter);
137 gtk_list_store_set (GTK_LIST_STORE(model), &iter,
138 LST_DEFASG_TOGGLE, FALSE,
139 LST_DEFASG_DATAS, item,
140 -1);
141
142 gtk_tree_selection_select_iter (gtk_tree_view_get_selection(GTK_TREE_VIEW(treeview)), &iter);
143
144 }
145 }
146
147 guint32
148 ui_asg_listview_get_selected_key(GtkTreeView *treeview)
149 {
150 GtkTreeSelection *selection;
151 GtkTreeModel *model;
152 GtkTreeIter iter;
153
154 selection = gtk_tree_view_get_selection(treeview);
155 if (gtk_tree_selection_get_selected(selection, &model, &iter))
156 {
157 Assign *item;
158
159 gtk_tree_model_get(model, &iter, LST_DEFASG_DATAS, &item, -1);
160
161 if( item!= NULL )
162 return item->key;
163 }
164 return 0;
165 }
166
167 void
168 ui_asg_listview_remove_selected(GtkTreeView *treeview)
169 {
170 GtkTreeSelection *selection;
171 GtkTreeModel *model;
172 GtkTreeIter iter;
173
174 selection = gtk_tree_view_get_selection(treeview);
175 if (gtk_tree_selection_get_selected(selection, &model, &iter))
176 {
177 gtk_list_store_remove(GTK_LIST_STORE(model), &iter);
178 }
179 }
180
181 /*
182 static gint ui_asg_glist_compare_func(Assign *a, Assign *b)
183 {
184 return 0; //((gint)a->pos - b->pos);
185 }
186 */
187
188 void ui_asg_listview_populate(GtkWidget *view)
189 {
190 GtkTreeModel *model;
191 GtkTreeIter iter;
192 GList *lrul, *list;
193
194 model = gtk_tree_view_get_model(GTK_TREE_VIEW(view));
195
196 gtk_list_store_clear (GTK_LIST_STORE(model));
197
198 g_object_ref(model); /* Make sure the model stays with us after the tree view unrefs it */
199 gtk_tree_view_set_model(GTK_TREE_VIEW(view), NULL); /* Detach model from view */
200
201 /* populate */
202 //g_hash_table_foreach(GLOBALS->h_rul, (GHFunc)ui_asg_listview_populate_ghfunc, model);
203 lrul = list = g_hash_table_get_values(GLOBALS->h_rul);
204
205 //list = g_list_sort(list, (GCompareFunc)ui_asg_glist_compare_func);
206 while (list != NULL)
207 {
208 Assign *item = list->data;
209
210 DB( g_print(" populate: %d\n", item->key) );
211
212 gtk_list_store_append (GTK_LIST_STORE(model), &iter);
213 gtk_list_store_set (GTK_LIST_STORE(model), &iter,
214 LST_DEFASG_TOGGLE , FALSE,
215 LST_DEFASG_DATAS, item,
216 -1);
217
218 list = g_list_next(list);
219 }
220 g_list_free(lrul);
221
222 gtk_tree_view_set_model(GTK_TREE_VIEW(view), model); /* Re-attach model to view */
223 g_object_unref(model);
224 }
225
226
227 GtkWidget *
228 ui_asg_listview_new(gboolean withtoggle)
229 {
230 GtkListStore *store;
231 GtkWidget *treeview;
232 GtkCellRenderer *renderer;
233 GtkTreeViewColumn *column;
234
235 // create list store
236 store = gtk_list_store_new(NUM_LST_DEFASG,
237 G_TYPE_BOOLEAN,
238 G_TYPE_POINTER
239 );
240
241 // treeview
242 treeview = gtk_tree_view_new_with_model(GTK_TREE_MODEL(store));
243 g_object_unref(store);
244
245 // column 1: toggle
246 if( withtoggle == TRUE )
247 {
248 renderer = gtk_cell_renderer_toggle_new ();
249 column = gtk_tree_view_column_new_with_attributes (_("Visible"),
250 renderer,
251 "active", LST_DEFASG_TOGGLE,
252 NULL);
253 gtk_tree_view_append_column (GTK_TREE_VIEW(treeview), column);
254
255 g_signal_connect (renderer, "toggled",
256 G_CALLBACK (ui_asg_listview_toggled_cb), store);
257
258 }
259
260 // column 2: name
261 renderer = gtk_cell_renderer_text_new ();
262 g_object_set(renderer,
263 "ellipsize", PANGO_ELLIPSIZE_END,
264 "ellipsize-set", TRUE,
265 NULL);
266
267 column = gtk_tree_view_column_new();
268 gtk_tree_view_column_set_title(column, _("Text"));
269 gtk_tree_view_column_pack_start(column, renderer, TRUE);
270 gtk_tree_view_column_set_cell_data_func(column, renderer, ui_asg_listview_name_cell_data_function, GINT_TO_POINTER(LST_DEFASG_DATAS), NULL);
271 gtk_tree_view_column_set_alignment (column, 0.5);
272 gtk_tree_view_column_set_resizable(column, TRUE);
273 gtk_tree_view_append_column (GTK_TREE_VIEW(treeview), column);
274
275 // treeviewattribute
276 //gtk_tree_view_set_headers_visible (GTK_TREE_VIEW(treeview), FALSE);
277 gtk_tree_view_set_reorderable (GTK_TREE_VIEW(treeview), TRUE);
278
279 gtk_tree_sortable_set_default_sort_func(GTK_TREE_SORTABLE(store), ui_asg_listview_compare_func, NULL, NULL);
280 gtk_tree_sortable_set_sort_column_id(GTK_TREE_SORTABLE(store), GTK_TREE_SORTABLE_DEFAULT_SORT_COLUMN_ID, GTK_SORT_ASCENDING);
281
282 return treeview;
283 }
284
285 /* = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = */
286 //todo move this
287 static gboolean
288 assign_rename(Assign *item, gchar *newname)
289 {
290 Assign *existitem;
291
292 existitem = da_asg_get_by_name(newname);
293 if( existitem == NULL )
294 {
295 g_free(item->text);
296 item->text = g_strdup(newname);
297 return TRUE;
298 }
299
300 return FALSE;
301 }
302
303
304
305 static void ui_asg_manage_getlast(struct ui_asg_manage_data *data)
306 {
307 Assign *item;
308 gint active;
309
310 DB( g_print("\n(ui_asg_manage_getlast)\n") );
311
312 DB( g_print(" -> for assign id=%d\n", data->lastkey) );
313
314 item = da_asg_get(data->lastkey);
315 if(item != NULL)
316 {
317 data->change++;
318
319 item->field = radio_get_active(GTK_CONTAINER(data->CY_field));
320
321 /*txt = (gchar *)gtk_entry_get_text(GTK_ENTRY(data->ST_text));
322 if (txt && *txt)
323 {
324 bool = assign_rename(item, txt);
325 if(bool)
326 {
327 gtk_tree_view_columns_autosize (GTK_TREE_VIEW(data->LV_rul));
328 }
329 else
330 {
331 gtk_entry_set_text(GTK_ENTRY(data->ST_text), item->text);
332 }
333 }*/
334
335 item->flags = 0;
336
337 active = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(data->CM_exact));
338 if(active == 1) item->flags |= ASGF_EXACT;
339
340 active = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(data->CM_re));
341 if(active == 1) item->flags |= ASGF_REGEX;
342
343 active = radio_get_active (GTK_CONTAINER(data->RA_pay));
344 if(active == 1) item->flags |= ASGF_DOPAY;
345 else
346 if(active == 2) item->flags |= ASGF_OVWPAY;
347
348 active = radio_get_active (GTK_CONTAINER(data->RA_cat));
349 if(active == 1) item->flags |= ASGF_DOCAT;
350 else
351 if(active == 2) item->flags |= ASGF_OVWCAT;
352
353 active = radio_get_active (GTK_CONTAINER(data->RA_mod));
354 if(active == 1) item->flags |= ASGF_DOMOD;
355 else
356 if(active == 2) item->flags |= ASGF_OVWMOD;
357
358 item->kcat = ui_cat_comboboxentry_get_key_add_new(GTK_COMBO_BOX(data->PO_cat));
359 item->kpay = ui_pay_comboboxentry_get_key_add_new(GTK_COMBO_BOX(data->PO_pay));
360 item->paymode = gtk_combo_box_get_active(GTK_COMBO_BOX(data->NU_mod));
361
362 }
363
364 }
365
366
367
368 /*
369 ** set widgets contents from the selected assign
370 */
371 static void ui_asg_manage_set(GtkWidget *widget, gpointer user_data)
372 {
373 struct ui_asg_manage_data *data;
374 GtkTreeSelection *selection;
375 GtkTreeModel *model;
376 GtkTreeIter iter;
377 Assign *item;
378 gint active;
379
380 DB( g_print("\n(ui_asg_manage_set)\n") );
381
382 data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW)), "inst_data");
383
384 selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(data->LV_rul));
385 //if true there is a selected node
386 if (gtk_tree_selection_get_selected(selection, &model, &iter))
387 {
388 gtk_tree_model_get(model, &iter, LST_DEFASG_DATAS, &item, -1);
389
390 DB( g_print(" -> set rul id=%d\n", item->key) );
391
392 radio_set_active(GTK_CONTAINER(data->CY_field), item->field);
393
394 gtk_entry_set_text(GTK_ENTRY(data->ST_text), item->text);
395
396 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(data->CM_exact), (item->flags & ASGF_EXACT) ? 1 : 0);
397 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(data->CM_re), (item->flags & ASGF_REGEX) ? 1 : 0);
398
399 active = 0;
400 if(item->flags & ASGF_DOPAY) active = 1;
401 else if(item->flags & ASGF_OVWPAY) active = 2;
402 radio_set_active(GTK_CONTAINER(data->RA_pay), active);
403 ui_pay_comboboxentry_set_active(GTK_COMBO_BOX(data->PO_pay), item->kpay);
404
405 active = 0;
406 if(item->flags & ASGF_DOCAT) active = 1;
407 else if(item->flags & ASGF_OVWCAT) active = 2;
408 radio_set_active(GTK_CONTAINER(data->RA_cat), active);
409 ui_cat_comboboxentry_set_active(GTK_COMBO_BOX(data->PO_cat), item->kcat);
410
411 active = 0;
412 if(item->flags & ASGF_DOMOD) active = 1;
413 else if(item->flags & ASGF_OVWMOD) active = 2;
414 radio_set_active(GTK_CONTAINER(data->RA_mod), active);
415 gtk_combo_box_set_active(GTK_COMBO_BOX(data->NU_mod), item->paymode);
416
417 }
418
419 }
420
421 /*
422 static gboolean ui_asg_manage_focus_out(GtkWidget *widget, GdkEventFocus *event, gpointer user_data)
423 {
424 ui_asg_manage_get(widget, user_data);
425 return FALSE;
426 }
427 */
428
429 static void ui_asg_manage_update_assignments(GtkWidget *widget, gpointer user_data)
430 {
431 struct ui_asg_manage_data *data;
432 gboolean sensitive;
433
434 DB( g_print("\n(ui_asg_manage_update_assignments)\n") );
435
436 data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW)), "inst_data");
437
438 sensitive = (radio_get_active (GTK_CONTAINER(data->RA_pay)) > 0) ? TRUE : FALSE;
439 gtk_widget_set_sensitive(data->LB_pay, sensitive);
440 gtk_widget_set_sensitive(data->PO_pay, sensitive);
441
442 sensitive = (radio_get_active (GTK_CONTAINER(data->RA_cat)) > 0) ? TRUE : FALSE;
443 gtk_widget_set_sensitive(data->LB_cat, sensitive);
444 gtk_widget_set_sensitive(data->PO_cat, sensitive);
445
446 sensitive = (radio_get_active (GTK_CONTAINER(data->RA_mod)) > 0) ? TRUE : FALSE;
447 gtk_widget_set_sensitive(data->LB_mod, sensitive);
448 gtk_widget_set_sensitive(data->NU_mod, sensitive);
449
450 }
451
452 /*
453 ** update the widgets status and contents from action/selection value
454 */
455 static void ui_asg_manage_update(GtkWidget *widget, gpointer user_data)
456 {
457 struct ui_asg_manage_data *data;
458 GtkTreeModel *model;
459 GtkTreeIter iter;
460 gboolean selected, sensitive;
461 guint32 key;
462 //gboolean is_new;
463
464 DB( g_print("\n(ui_asg_manage_update)\n") );
465
466 data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW)), "inst_data");
467 //window = gtk_widget_get_ancestor(GTK_WIDGET(treeview), GTK_TYPE_WINDOW);
468 //DB( g_print("(defpayee) widget=%08lx, window=%08lx, inst_data=%08lx\n", treeview, window, data) );
469
470 //if true there is a selected node
471 selected = gtk_tree_selection_get_selected(gtk_tree_view_get_selection(GTK_TREE_VIEW(data->LV_rul)), &model, &iter);
472 key = ui_asg_listview_get_selected_key(GTK_TREE_VIEW(data->LV_rul));
473
474 DB( g_print(" -> selected = %d action = %d key = %d\n", selected, data->action, key) );
475
476
477 sensitive = (selected == TRUE) ? TRUE : FALSE;
478 gtk_widget_set_sensitive(data->GR_condition, sensitive);
479 gtk_widget_set_sensitive(data->GR_pay, sensitive);
480 gtk_widget_set_sensitive(data->GR_cat, sensitive);
481 gtk_widget_set_sensitive(data->GR_mod, sensitive);
482
483 //sensitive = (data->action == 0) ? TRUE : FALSE;
484 //gtk_widget_set_sensitive(data->LV_rul, sensitive);
485 //gtk_widget_set_sensitive(data->BT_add, sensitive);
486
487 sensitive = (selected == TRUE && data->action == 0) ? TRUE : FALSE;
488 //gtk_widget_set_sensitive(data->BT_mod, sensitive);
489 gtk_widget_set_sensitive(data->BT_rem, sensitive);
490
491 if(selected)
492 {
493 if(key != data->lastkey)
494 {
495 DB( g_print(" -> should first do a get for assign %d\n", data->lastkey) );
496 ui_asg_manage_getlast(data);
497 }
498
499 ui_asg_manage_set(widget, NULL);
500 ui_asg_manage_update_assignments(widget, NULL);
501 }
502
503 data->lastkey = key;
504
505 }
506
507
508 /*
509 ** add an empty new assign to our temp GList and treeview
510 */
511 static void ui_asg_manage_add(GtkWidget *widget, gpointer user_data)
512 {
513 struct ui_asg_manage_data *data;
514 Assign *item;
515
516 data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW)), "inst_data");
517 DB( g_print("\n(ui_asg_manage_add) (data=%x)\n", (guint)data) );
518
519 item = da_asg_malloc();
520 item->text = g_strdup_printf( _("(assignment %d)"), da_asg_length()+1);
521
522 da_asg_append(item);
523 ui_asg_listview_add(GTK_TREE_VIEW(data->LV_rul), item);
524
525 data->change++;
526 }
527
528 /*
529 ** delete the selected assign to our treeview and temp GList
530 */
531 static void ui_asg_manage_delete(GtkWidget *widget, gpointer user_data)
532 {
533 struct ui_asg_manage_data *data;
534 guint32 key;
535 gint result;
536
537 data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW)), "inst_data");
538 DB( g_print("\n(ui_asg_manage_remove) (data=%x)\n", (guint)data) );
539
540 key = ui_asg_listview_get_selected_key(GTK_TREE_VIEW(data->LV_rul));
541 if( key > 0 )
542 {
543 Assign *item = da_asg_get(key);
544 gchar *title = NULL;
545 gchar *secondtext;
546
547 title = g_strdup_printf (
548 _("Are you sure you want to permanently delete '%s'?"), item->text);
549
550 secondtext = _("If you delete an assignment, it will be permanently lost.");
551
552 result = ui_dialog_msg_confirm_alert(
553 GTK_WINDOW(data->window),
554 title,
555 secondtext,
556 _("_Delete")
557 );
558
559 g_free(title);
560
561 if( result == GTK_RESPONSE_OK )
562 {
563 da_asg_remove(key);
564 ui_asg_listview_remove_selected(GTK_TREE_VIEW(data->LV_rul));
565 data->change++;
566 }
567 }
568 }
569
570 /*
571 ** rename the selected assign to our treeview and temp GList
572 */
573 static void ui_asg_manage_rename(GtkWidget *widget, gpointer user_data)
574 {
575 struct ui_asg_manage_data *data;
576 guint32 key;
577 gboolean error;
578 gchar *txt;
579
580 data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW)), "inst_data");
581 DB( g_print("\n(ui_asg_manage_rename) (data=%x)\n", (guint)data) );
582
583 error = FALSE;
584
585 key = ui_asg_listview_get_selected_key(GTK_TREE_VIEW(data->LV_rul));
586 if( key > 0 )
587 {
588 Assign *item = da_asg_get(key);
589
590 txt = (gchar *)gtk_entry_get_text(GTK_ENTRY(data->ST_text));
591 if( txt == NULL || *txt == '\0' )
592 {
593 error = TRUE;
594 goto end;
595 }
596
597 if( strcmp(txt, item->text) )
598 {
599 if( assign_rename(item, txt) == TRUE )
600 {
601 //todo: review this count
602 data->change++;
603 gtk_tree_view_columns_autosize (GTK_TREE_VIEW(data->LV_rul));
604 }
605 else
606 error = TRUE;
607 }
608 }
609
610 end:
611 gtk_style_context_remove_class (gtk_widget_get_style_context (GTK_WIDGET(data->ST_text)), GTK_STYLE_CLASS_ERROR);
612
613 if( error == TRUE )
614 gtk_style_context_add_class (gtk_widget_get_style_context (GTK_WIDGET(data->ST_text)), GTK_STYLE_CLASS_ERROR);
615 }
616
617
618 /*
619 **
620 */
621 static void ui_asg_manage_selection(GtkTreeSelection *treeselection, gpointer user_data)
622 {
623 ui_asg_manage_update(GTK_WIDGET(gtk_tree_selection_get_tree_view (treeselection)), NULL);
624 }
625
626 //gint ui_asg_manage_list_sort(struct _Assign *a, struct _Assign *b) { return( a->rul_Id - b->rul_Id); }
627
628 /*
629 **
630 */
631 static gboolean ui_asg_manage_cleanup(struct ui_asg_manage_data *data, gint result)
632 {
633 guint32 key;
634 gboolean doupdate = FALSE;
635
636 DB( g_print("\n(ui_asg_manage_cleanup) %x\n", (guint)data) );
637
638 key = ui_asg_listview_get_selected_key(GTK_TREE_VIEW(data->LV_rul));
639 if(key > 0)
640 {
641 data->lastkey = key;
642 DB( g_print(" -> should first do a get for assign %d\n", data->lastkey) );
643 ui_asg_manage_getlast(data);
644 }
645
646 // test for change & store new position
647 /*
648 model = gtk_tree_view_get_model(GTK_TREE_VIEW(data->LV_rul));
649 i=1; valid = gtk_tree_model_get_iter_first(GTK_TREE_MODEL(model), &iter);
650 while (valid)
651 {
652 Assign *item;
653
654 gtk_tree_model_get(GTK_TREE_MODEL(model), &iter,
655 LST_DEFASG_DATAS, &item,
656 -1);
657
658 DB( g_print(" -> check rul %d, pos is %d, %s\n", i, item->pos, item->text) );
659
660 if(item->pos != i)
661 data->change++;
662
663 item->pos = i;
664
665 // Make iter point to the next row in the list store
666 i++; valid = gtk_tree_model_iter_next(GTK_TREE_MODEL(model), &iter);
667 }
668 */
669
670 GLOBALS->changes_count += data->change;
671
672 return doupdate;
673 }
674
675 /*
676 **
677 */
678 static void ui_asg_manage_setup(struct ui_asg_manage_data *data)
679 {
680
681 DB( g_print("\n(ui_asg_manage_setup)\n") );
682
683 //init GList
684 data->tmp_list = NULL; //hb-glist_clone_list(GLOBALS->rul_list, sizeof(struct _Assign));
685 data->action = 0;
686 data->change = 0;
687 data->lastkey = 0;
688
689 ui_asg_listview_populate(data->LV_rul);
690
691 ui_pay_comboboxentry_populate(GTK_COMBO_BOX(data->PO_pay), GLOBALS->h_pay);
692 ui_cat_comboboxentry_populate(GTK_COMBO_BOX(data->PO_cat), GLOBALS->h_cat);
693 }
694
695 static gchar *CYA_ASG_ACTION[] = {
696 N_("Disabled"),
697 N_("If empty"),
698 N_("Overwrite"),
699 NULL
700 };
701
702
703
704 /*
705 **
706 */
707 GtkWidget *ui_asg_manage_dialog (void)
708 {
709 struct ui_asg_manage_data data;
710 GtkWidget *window, *content, *mainbox;
711 GtkWidget *content_grid, *group_grid;
712 GtkWidget *table, *label, *entry1;
713 GtkWidget *scrollwin;
714 GtkWidget *widget, *hpaned;
715 gint w, h, crow, row;
716
717 window = gtk_dialog_new_with_buttons (_("Manage Assignments"),
718 GTK_WINDOW(GLOBALS->mainwindow),
719 0,
720 _("_Close"),
721 GTK_RESPONSE_ACCEPT,
722 NULL);
723
724 data.window = window;
725
726 //set the window icon
727 gtk_window_set_icon_name(GTK_WINDOW (window), ICONNAME_HB_ASSIGN);
728
729 //set a nice dialog size
730 gtk_window_get_size(GTK_WINDOW(GLOBALS->mainwindow), &w, &h);
731 gtk_window_set_default_size (GTK_WINDOW(window), -1, h/PHI);
732
733 //store our window private data
734 g_object_set_data(G_OBJECT(window), "inst_data", (gpointer)&data);
735 DB( g_print("(ui_asg_manage_) window=%x, inst_data=%x\n", (guint)window, (guint)&data) );
736
737 //window contents
738 content = gtk_dialog_get_content_area(GTK_DIALOG (window)); // return a vbox
739
740
741 mainbox = gtk_box_new (GTK_ORIENTATION_HORIZONTAL, SPACING_SMALL);
742 gtk_box_pack_start (GTK_BOX (content), mainbox, TRUE, TRUE, 0);
743 gtk_container_set_border_width (GTK_CONTAINER(mainbox), SPACING_MEDIUM);
744
745 hpaned = gtk_paned_new(GTK_ORIENTATION_HORIZONTAL);
746 gtk_box_pack_start (GTK_BOX (mainbox), hpaned, TRUE, TRUE, 0);
747
748 /* left area */
749 table = gtk_grid_new ();
750 gtk_grid_set_row_spacing (GTK_GRID (table), SPACING_SMALL);
751 gtk_grid_set_column_spacing (GTK_GRID (table), SPACING_MEDIUM);
752 //gtk_box_pack_start (GTK_BOX (mainbox), table, FALSE, FALSE, 0);
753 gtk_widget_set_margin_right(table, SPACING_SMALL);
754 gtk_paned_pack1 (GTK_PANED(hpaned), table, FALSE, FALSE);
755
756 row = 0;
757 scrollwin = gtk_scrolled_window_new(NULL,NULL);
758 gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(scrollwin), GTK_POLICY_NEVER, GTK_POLICY_AUTOMATIC);
759 gtk_scrolled_window_set_shadow_type (GTK_SCROLLED_WINDOW (scrollwin), GTK_SHADOW_ETCHED_IN);
760 data.LV_rul = ui_asg_listview_new(FALSE);
761 gtk_widget_set_size_request(data.LV_rul, HB_MINWIDTH_LIST, -1);
762 gtk_container_add(GTK_CONTAINER(scrollwin), data.LV_rul);
763 gtk_widget_set_vexpand (scrollwin, TRUE);
764 gtk_widget_set_hexpand (scrollwin, TRUE);
765 gtk_grid_attach (GTK_GRID(table), scrollwin, 0, row, 2, 1);
766
767 row++;
768 widget = gtk_button_new_with_mnemonic(_("_Add"));
769 data.BT_add = widget;
770 gtk_grid_attach (GTK_GRID(table), widget, 0, row, 1, 1);
771
772 widget = gtk_button_new_with_mnemonic(_("_Delete"));
773 data.BT_rem = widget;
774 gtk_grid_attach (GTK_GRID(table), widget, 1, row, 1, 1);
775
776
777 /* right area */
778 content_grid = gtk_grid_new();
779 gtk_grid_set_row_spacing (GTK_GRID (content_grid), SPACING_LARGE);
780 gtk_orientable_set_orientation(GTK_ORIENTABLE(content_grid), GTK_ORIENTATION_VERTICAL);
781 //gtk_container_set_border_width (GTK_CONTAINER(content_grid), SPACING_MEDIUM);
782 gtk_widget_set_margin_left(content_grid, SPACING_SMALL);
783 gtk_paned_pack2 (GTK_PANED(hpaned), content_grid, FALSE, FALSE);
784
785 // group :: Condition
786 crow = 0;
787 group_grid = gtk_grid_new ();
788 data.GR_condition = group_grid;
789 gtk_grid_set_row_spacing (GTK_GRID (group_grid), SPACING_SMALL);
790 gtk_grid_set_column_spacing (GTK_GRID (group_grid), SPACING_MEDIUM);
791 gtk_grid_attach (GTK_GRID (content_grid), group_grid, 0, crow, 1, 1);
792
793 row = 0;
794 label = make_label_group(_("Condition"));
795 gtk_grid_attach (GTK_GRID (group_grid), label, 0, row, 3, 1);
796
797 row++;
798 label = make_label_widget(_("Search _in:"));
799 gtk_grid_attach (GTK_GRID (group_grid), label, 1, row, 1, 1);
800 widget = make_radio(CYA_ASG_FIELD, FALSE, GTK_ORIENTATION_HORIZONTAL);
801 data.CY_field = widget;
802 gtk_grid_attach (GTK_GRID (group_grid), widget, 2, row, 2, 1);
803
804 row++;
805 //label = make_label_widget(_("Con_tains:"));
806 label = make_label_widget(_("Fi_nd:"));
807 gtk_grid_attach (GTK_GRID (group_grid), label, 1, row, 1, 1);
808 entry1 = make_string(label);
809 data.ST_text = entry1;
810 gtk_widget_set_hexpand(entry1, TRUE);
811 gtk_grid_attach (GTK_GRID (group_grid), entry1, 2, row, 2, 1);
812
813 row++;
814 widget = gtk_check_button_new_with_mnemonic (_("Match _case"));
815 data.CM_exact = widget;
816 gtk_grid_attach (GTK_GRID (group_grid), widget, 2, row, 2, 1);
817
818 row++;
819 widget = gtk_check_button_new_with_mnemonic (_("Use _regular expressions"));
820 data.CM_re = widget;
821 gtk_grid_attach (GTK_GRID (group_grid), widget, 2, row, 2, 1);
822
823 // Assignments
824
825 // group :: Assign payee
826 crow++;
827 group_grid = gtk_grid_new ();
828 data.GR_pay = group_grid;
829 gtk_grid_set_row_spacing (GTK_GRID (group_grid), SPACING_SMALL);
830 gtk_grid_set_column_spacing (GTK_GRID (group_grid), SPACING_MEDIUM);
831 gtk_grid_attach (GTK_GRID (content_grid), group_grid, 0, crow, 1, 1);
832
833 row = 0;
834 label = make_label_group(_("Assign payee"));
835 gtk_grid_attach (GTK_GRID (group_grid), label, 0, row, 3, 1);
836
837 row++;
838 widget = make_radio(CYA_ASG_ACTION, FALSE, GTK_ORIENTATION_HORIZONTAL);
839 data.RA_pay = widget;
840 gtk_grid_attach (GTK_GRID (group_grid), widget, 2, row, 1, 1);
841
842 row++;
843 label = make_label_widget (_("_Payee:"));
844 data.LB_pay = label;
845 gtk_grid_attach (GTK_GRID (group_grid), label, 1, row, 1, 1);
846
847 widget = ui_pay_comboboxentry_new(label);
848 data.PO_pay = widget;
849 gtk_widget_set_hexpand(widget, TRUE);
850 gtk_grid_attach (GTK_GRID (group_grid), widget, 2, row, 1, 1);
851
852
853 //gtk_widget_set_tooltip_text(widget, _("Autocompletion and direct seizure\nis available for Payee"));
854
855 crow++;
856 group_grid = gtk_grid_new ();
857 data.GR_cat = group_grid;
858 gtk_grid_set_row_spacing (GTK_GRID (group_grid), SPACING_SMALL);
859 gtk_grid_set_column_spacing (GTK_GRID (group_grid), SPACING_MEDIUM);
860 gtk_grid_attach (GTK_GRID (content_grid), group_grid, 0, crow, 1, 1);
861
862 row = 0;
863 label = make_label_group(_("Assign category"));
864 gtk_grid_attach (GTK_GRID (group_grid), label, 0, row, 3, 1);
865
866 row++;
867 widget = make_radio(CYA_ASG_ACTION, FALSE, GTK_ORIENTATION_HORIZONTAL);
868 data.RA_cat = widget;
869 gtk_grid_attach (GTK_GRID (group_grid), widget, 2, row, 1, 1);
870
871 row++;
872 label = make_label_widget (_("_Category:"));
873 data.LB_cat = label;
874 gtk_grid_attach (GTK_GRID (group_grid), label, 1, row, 1, 1);
875
876 widget = ui_cat_comboboxentry_new(label);
877 data.PO_cat = widget;
878 gtk_widget_set_hexpand(widget, TRUE);
879 gtk_grid_attach (GTK_GRID (group_grid), widget, 2, row, 1, 1);
880
881 //gtk_widget_set_tooltip_text(widget, _("Autocompletion and direct seizure\nis available for Category"));
882
883 crow++;
884 group_grid = gtk_grid_new ();
885 data.GR_mod = group_grid;
886 gtk_grid_set_row_spacing (GTK_GRID (group_grid), SPACING_SMALL);
887 gtk_grid_set_column_spacing (GTK_GRID (group_grid), SPACING_MEDIUM);
888 gtk_grid_attach (GTK_GRID (content_grid), group_grid, 0, crow, 1, 1);
889
890 row = 0;
891 label = make_label_group(_("Assign payment"));
892 gtk_grid_attach (GTK_GRID (group_grid), label, 0, row, 3, 1);
893
894 row++;
895 widget = make_radio(CYA_ASG_ACTION, FALSE, GTK_ORIENTATION_HORIZONTAL);
896 data.RA_mod = widget;
897 gtk_grid_attach (GTK_GRID (group_grid), widget, 2, row, 1, 1);
898
899 row++;
900 label = make_label_widget (_("Pay_ment:"));
901 data.LB_mod = label;
902 gtk_grid_attach (GTK_GRID (group_grid), label, 1, row, 1, 1);
903
904 widget = make_paymode_nointxfer (label);
905 data.NU_mod = widget;
906 gtk_widget_set_hexpand(widget, TRUE);
907 gtk_grid_attach (GTK_GRID (group_grid), widget, 2, row, 1, 1);
908
909 //ugly hack
910 //gtk_widget_set_tooltip_text(widget, _("Internal transfer unsupported\nin auto assignments"));
911
912
913 //connect all our signals
914 g_signal_connect (window, "destroy", G_CALLBACK (gtk_widget_destroyed), &window);
915
916 g_signal_connect (gtk_tree_view_get_selection(GTK_TREE_VIEW(data.LV_rul)), "changed", G_CALLBACK (ui_asg_manage_selection), NULL);
917
918 g_signal_connect (G_OBJECT (data.ST_text), "changed", G_CALLBACK (ui_asg_manage_rename), NULL);
919
920 widget = radio_get_nth_widget(GTK_CONTAINER(data.RA_pay), 0);
921 if(widget)
922 g_signal_connect (widget, "toggled", G_CALLBACK (ui_asg_manage_update_assignments), NULL);
923
924 widget = radio_get_nth_widget(GTK_CONTAINER(data.RA_cat), 0);
925 if(widget)
926 g_signal_connect (widget, "toggled", G_CALLBACK (ui_asg_manage_update_assignments), NULL);
927
928 widget = radio_get_nth_widget(GTK_CONTAINER(data.RA_mod), 0);
929 if(widget)
930 g_signal_connect (widget, "toggled", G_CALLBACK (ui_asg_manage_update_assignments), NULL);
931
932 g_signal_connect (G_OBJECT (data.BT_add), "clicked", G_CALLBACK (ui_asg_manage_add), NULL);
933 g_signal_connect (G_OBJECT (data.BT_rem), "clicked", G_CALLBACK (ui_asg_manage_delete), NULL);
934
935 //setup, init and show window
936 ui_asg_manage_setup(&data);
937 ui_asg_manage_update(data.LV_rul, NULL);
938
939 // gtk_window_set_default_size (GTK_WINDOW (window), 640, 480);
940
941 gtk_widget_show_all (window);
942
943 //wait for the user
944 gint result = gtk_dialog_run (GTK_DIALOG (window));
945
946 // cleanup and destroy
947 ui_asg_manage_cleanup(&data, result);
948 gtk_widget_destroy (window);
949
950 return NULL;
951 }
952
953
This page took 0.100307 seconds and 4 git commands to generate.