X-Git-Url: https://git.dogcows.com/gitweb?p=chaz%2Fhomebank;a=blobdiff_plain;f=src%2Fui-currency.c;fp=src%2Fui-currency.c;h=2f58322d314c8989b8a14edb864edfb41e3210c5;hp=0000000000000000000000000000000000000000;hb=996fa4ab9f6b836001f8ad0eecbfd3821687fea7;hpb=27f6e3b112df235c8e9afc9911b1f6bce208a001 diff --git a/src/ui-currency.c b/src/ui-currency.c new file mode 100644 index 0000000..2f58322 --- /dev/null +++ b/src/ui-currency.c @@ -0,0 +1,1601 @@ +/* HomeBank -- Free, easy, personal accounting for everyone. + * Copyright (C) 1995-2012 Maxime DOYEN + * + * This file is part of HomeBank. + * + * HomeBank is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * HomeBank is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + +#include "homebank.h" + +#include "ui-currency.h" + + +#define MYDEBUG 0 + +#if MYDEBUG +#define DB(x) (x); +#else +#define DB(x); +#endif + +/* our global datas */ +extern struct HomeBank *GLOBALS; +extern struct Preferences *PREFS; + +extern Currency4217 iso4217cur[]; +extern guint n_iso4217cur; + +static void ui_cur_manage_dialog_update(GtkWidget *treeview, gpointer user_data); + +/* = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = */ + +/** + * ui_cur_combobox_get_name: + * + * get the name of the active curee or -1 + * + * Return value: a new allocated name tobe freed with g_free + * + */ +gchar * +ui_cur_combobox_get_name(GtkComboBox *entry_box) +{ +gchar *cbname; +gchar *name = NULL; + + cbname = (gchar *)gtk_entry_get_text(GTK_ENTRY (gtk_bin_get_child(GTK_BIN (entry_box)))); + + if( cbname != NULL) + { + name = g_strdup(cbname); + g_strstrip(name); + } + + return name; +} + + +/** + * ui_cur_combobox_get_key: + * + * get the key of the active curee + * + * Return value: the key or 0 + * + */ +guint32 +ui_cur_combobox_get_key(GtkComboBox *entry_box) +{ +GtkTreeModel *model; +GtkTreeIter iter; +guint32 key = 0; + + if (gtk_combo_box_get_active_iter(entry_box, &iter) == TRUE) + { + model = gtk_combo_box_get_model(entry_box); + gtk_tree_model_get (model, &iter, 1, &key, -1); + } + + return key; +} + + +gboolean +ui_cur_combobox_set_active(GtkComboBox *entry_box, guint32 key) +{ +GtkTreeModel *model; +GtkTreeIter iter; +gboolean valid; +guint32 cbkey; + + model = gtk_combo_box_get_model(entry_box); + valid = gtk_tree_model_get_iter_first(GTK_TREE_MODEL(model), &iter); + while (valid) + { + gtk_tree_model_get (model, &iter, 1, &cbkey, -1); + if(cbkey == key) + break; + + valid = gtk_tree_model_iter_next(GTK_TREE_MODEL(model), &iter); + } + + gtk_combo_box_set_active_iter(entry_box, &iter); + + return FALSE; +} + + + + +/** + * ui_cur_combobox_add: + * + * Add a single element (useful for dynamics add) + * + * Return value: -- + * + */ +void +ui_cur_combobox_add(GtkComboBox *entry_box, Currency *cur) +{ + if( cur->name != NULL ) + { + GtkTreeModel *model; + GtkTreeIter iter; + + model = gtk_combo_box_get_model(GTK_COMBO_BOX(entry_box)); + + gtk_list_store_append (GTK_LIST_STORE(model), &iter); + gtk_list_store_set (GTK_LIST_STORE(model), &iter, 0, cur->name, 1, cur->key, -1); + } +} + +static void +ui_cur_combobox_populate_ghfunc(gpointer key, gpointer value, struct curPopContext *ctx) +{ +GtkTreeIter iter; +Currency *cur = value; + + if( ( cur->key != ctx->except_key ) ) + { + gtk_list_store_append (GTK_LIST_STORE(ctx->model), &iter); + gtk_list_store_set (GTK_LIST_STORE(ctx->model), &iter, 0, cur->name, 1, cur->key, -1); + } +} + +void +ui_cur_combobox_populate_except(GtkComboBox *entry_box, GHashTable *hash, guint32 except_key) +{ +GtkTreeModel *model; +struct curPopContext ctx; + + DB( g_print ("ui_cur_combobox_populate\n") ); + + model = gtk_combo_box_get_model(GTK_COMBO_BOX(entry_box)); + + /* keep our model alive and detach from combobox and completion */ + g_object_ref(model); + gtk_combo_box_set_model(GTK_COMBO_BOX(entry_box), NULL); + + /* clear and populate */ + ctx.model = model; + ctx.except_key = except_key; + gtk_list_store_clear (GTK_LIST_STORE(model)); + g_hash_table_foreach(hash, (GHFunc)ui_cur_combobox_populate_ghfunc, &ctx); + + /* reatach our model */ + gtk_combo_box_set_model(GTK_COMBO_BOX(entry_box), model); + g_object_unref(model); + + gtk_tree_sortable_set_sort_column_id(GTK_TREE_SORTABLE(model), GTK_TREE_SORTABLE_DEFAULT_SORT_COLUMN_ID, GTK_SORT_ASCENDING); + +} + +/** + * ui_cur_combobox_populate: + * + * Populate the list and completion + * + * Return value: -- + * + */ +void +ui_cur_combobox_populate(GtkComboBox *entry_box, GHashTable *hash) +{ + ui_cur_combobox_populate_except(entry_box, hash, -1); +} + + +static gint +ui_cur_combobox_compare_func (GtkTreeModel *model, GtkTreeIter *a, GtkTreeIter *b, gpointer userdata) +{ +gint ret = 0; +gchar *name1, *name2; + + gtk_tree_model_get(model, a, 0, &name1, -1); + gtk_tree_model_get(model, b, 0, &name2, -1); + + if (name1 == NULL || name2 == NULL) + { + if (name1 == NULL && name2 == NULL) + goto end; + + ret = (name1 == NULL) ? -1 : 1; + } + else + { + ret = g_utf8_collate(name1,name2); + } + + + end: + + g_free(name1); + g_free(name2); + + return ret; + } + + +static void +ui_cur_combobox_test (GtkCellLayout *cell_layout, + GtkCellRenderer *cell, + GtkTreeModel *tree_model, + GtkTreeIter *iter, + gpointer data) +{ +gchar *name; + + gtk_tree_model_get(tree_model, iter, + 0, &name, + -1); + + if( !name ) + g_object_set(cell, "text", _("(none)"), NULL); + else + g_object_set(cell, "text", name, NULL); + +} + +/** + * ui_cur_combobox_new: + * + * Create a new curee combobox + * + * Return value: the new widget + * + */ +GtkWidget * +ui_cur_combobox_new(GtkWidget *label) +{ +GtkListStore *store; +GtkWidget *combobox; +GtkCellRenderer *renderer; + + store = gtk_list_store_new (2, + G_TYPE_STRING, + G_TYPE_INT + ); + gtk_tree_sortable_set_default_sort_func(GTK_TREE_SORTABLE(store), ui_cur_combobox_compare_func, NULL, NULL); + + // dothe same for combobox + + combobox = gtk_combo_box_new_with_model(GTK_TREE_MODEL(store)); + + gtk_cell_layout_clear(GTK_CELL_LAYOUT (combobox)); + + renderer = gtk_cell_renderer_text_new (); + gtk_cell_layout_pack_start (GTK_CELL_LAYOUT (combobox), renderer, TRUE); + gtk_cell_layout_set_attributes (GTK_CELL_LAYOUT (combobox), renderer, "text", 0, NULL); + + gtk_cell_layout_set_cell_data_func (GTK_CELL_LAYOUT (combobox), + renderer, + ui_cur_combobox_test, + NULL, NULL); + + g_object_unref(store); + + if(label) + gtk_label_set_mnemonic_widget (GTK_LABEL(label), combobox); + + gtk_widget_set_size_request (combobox, 10, -1); + + return combobox; +} + + + +/* = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = */ + + + + +static void +ui_cur_listview_toggled_cb (GtkCellRendererToggle *cell, + gchar *path_str, + gpointer data) +{ + GtkTreeModel *model = (GtkTreeModel *)data; + GtkTreeIter iter; + GtkTreePath *path = gtk_tree_path_new_from_string (path_str); + gboolean fixed; + + /* get toggled iter */ + gtk_tree_model_get_iter (model, &iter, path); + gtk_tree_model_get (model, &iter, LST_DEFCUR_TOGGLE, &fixed, -1); + + /* do something with the value */ + fixed ^= 1; + + /* set new value */ + gtk_list_store_set (GTK_LIST_STORE (model), &iter, LST_DEFCUR_TOGGLE, fixed, -1); + + /* clean up */ + gtk_tree_path_free (path); +} + +static gint +ui_cur_listview_compare_func (GtkTreeModel *model, GtkTreeIter *a, GtkTreeIter *b, gpointer userdata) +{ +gint result = 0; +Currency *entry1, *entry2; +gchar *name1, *name2; + + gtk_tree_model_get(model, a, LST_DEFCUR_DATAS, &entry1, -1); + gtk_tree_model_get(model, b, LST_DEFCUR_DATAS, &entry2, -1); + + name1 = (entry1->key == GLOBALS->kcur) ? NULL : entry1->iso_code; + name2 = (entry2->key == GLOBALS->kcur) ? NULL : entry2->iso_code; + + result = hb_string_compare(name1,name2); + + return result; +} + +static void +ui_cur_listview_name_cell_data_function (GtkTreeViewColumn *col, + GtkCellRenderer *renderer, + GtkTreeModel *model, + GtkTreeIter *iter, + gpointer user_data) +{ +Currency *entry; +gchar *string; +gint weight; + + gtk_tree_model_get(model, iter, LST_DEFCUR_DATAS, &entry, -1); + + weight = entry->key == GLOBALS->kcur ? PANGO_WEIGHT_BOLD : PANGO_WEIGHT_NORMAL; + + #if MYDEBUG + if( entry->key == GLOBALS->kcur ) + string = g_strdup_printf ("[%d] %s - %s\n(%s)", entry->key, entry->iso_code, entry->name, _("Base currency")); + else + string = g_strdup_printf ("[%d] %s - %s", entry->key, entry->iso_code, entry->name); + g_object_set(renderer, "weight", weight, "markup", string, NULL); + g_free(string); + #else + if( entry->key == GLOBALS->kcur ) + string = g_strdup_printf ("%s - %s\n(%s)", entry->iso_code, entry->name, _("Base currency")); + else + string = g_strdup_printf ("%s - %s", entry->iso_code, entry->name); + g_object_set(renderer, "weight", weight, "markup", string, NULL); + g_free(string); + #endif + +} + + +static void +ui_cur_listview_symbol_cell_data_function (GtkTreeViewColumn *col, + GtkCellRenderer *renderer, + GtkTreeModel *model, + GtkTreeIter *iter, + gpointer user_data) +{ +Currency *entry; +gint weight; + + gtk_tree_model_get(model, iter, LST_DEFCUR_DATAS, &entry, -1); + + weight = entry->key == GLOBALS->kcur ? PANGO_WEIGHT_BOLD : PANGO_WEIGHT_NORMAL; + + g_object_set(renderer, "weight", weight, "text", entry->symbol, NULL); +} + + +static void +ui_cur_listview_lastmodified_cell_data_function (GtkTreeViewColumn *col, + GtkCellRenderer *renderer, + GtkTreeModel *model, + GtkTreeIter *iter, + gpointer user_data) +{ +Currency *entry; +gchar buffer[256]; +GDate date; +gint weight; + + gtk_tree_model_get(model, iter, LST_DEFCUR_DATAS, &entry, -1); + + weight = entry->key == GLOBALS->kcur ? PANGO_WEIGHT_BOLD : PANGO_WEIGHT_NORMAL; + + if(entry->mdate > 0) + { + g_date_set_julian (&date, entry->mdate); + g_date_strftime (buffer, 256-1, PREFS->date_format, &date); + + //g_snprintf(buf, sizeof(buf), "%d", ope->ope_Date); + + g_object_set(renderer, "weight", weight, "text", buffer, NULL); + } + else + g_object_set(renderer, "weight", weight, "text", "-", NULL); +} + + + +static void +ui_cur_listview_rate_cell_data_function (GtkTreeViewColumn *col, + GtkCellRenderer *renderer, + GtkTreeModel *model, + GtkTreeIter *iter, + gpointer user_data) +{ +Currency *entry; +gchar formatd_buf[G_ASCII_DTOSTR_BUF_SIZE]; + + gtk_tree_model_get(model, iter, LST_DEFCUR_DATAS, &entry, -1); + + if(entry->key == GLOBALS->kcur) + g_object_set(renderer, "text", "-", NULL); + else + { + //g_ascii_formatd(formatd_buf, sizeof (formatd_buf), "%.6f", entry->rate); + //g_snprintf(formatd_buf, sizeof (formatd_buf), "%f", entry->rate); + hb_str_rate(formatd_buf, sizeof (formatd_buf), entry->rate); + g_object_set(renderer, "text", formatd_buf, NULL); + } + +} + + +/* = = = = = = = = = = = = = = = = */ + + +void +ui_cur_listview_add(GtkTreeView *treeview, Currency *item) +{ + if( item->name != NULL ) + { + GtkTreeModel *model; + GtkTreeIter iter; + + model = gtk_tree_view_get_model(treeview); + + gtk_list_store_append (GTK_LIST_STORE(model), &iter); + gtk_list_store_set (GTK_LIST_STORE(model), &iter, + LST_DEFCUR_TOGGLE, FALSE, + LST_DEFCUR_DATAS, item, + -1); + } +} + +guint32 +ui_cur_listview_get_selected_key(GtkTreeView *treeview) +{ +GtkTreeSelection *selection; +GtkTreeModel *model; +GtkTreeIter iter; + + selection = gtk_tree_view_get_selection(treeview); + if (gtk_tree_selection_get_selected(selection, &model, &iter)) + { + Currency *item; + + gtk_tree_model_get(model, &iter, LST_DEFCUR_DATAS, &item, -1); + + if( item != NULL ) + return item->key; + } + return 0; +} + +void +ui_cur_listview_remove_selected(GtkTreeView *treeview) +{ +GtkTreeSelection *selection; +GtkTreeModel *model; +GtkTreeIter iter; + + selection = gtk_tree_view_get_selection(treeview); + if (gtk_tree_selection_get_selected(selection, &model, &iter)) + { + gtk_list_store_remove(GTK_LIST_STORE(model), &iter); + } +} + + +static void ui_cur_listview_populate_ghfunc(gpointer key, gpointer value, GtkTreeModel *model) +{ +GtkTreeIter iter; +Currency *item = value; + + gtk_list_store_append (GTK_LIST_STORE(model), &iter); + gtk_list_store_set (GTK_LIST_STORE(model), &iter, + LST_DEFCUR_TOGGLE , FALSE, + LST_DEFCUR_DATAS, item, + -1); +} + +void ui_cur_listview_populate(GtkWidget *view) +{ +GtkTreeModel *model; + + model = gtk_tree_view_get_model(GTK_TREE_VIEW(view)); + + gtk_list_store_clear (GTK_LIST_STORE(model)); + + g_object_ref(model); /* Make sure the model stays with us after the tree view unrefs it */ + gtk_tree_view_set_model(GTK_TREE_VIEW(view), NULL); /* Detach model from view */ + + /* populate */ + g_hash_table_foreach(GLOBALS->h_cur, (GHFunc)ui_cur_listview_populate_ghfunc, model); + + gtk_tree_view_set_model(GTK_TREE_VIEW(view), model); /* Re-attach model to view */ + g_object_unref(model); +} + +/* test */ +/* +static void +ui_cur_listivew_rate_edited_func (GtkCellRendererText *cell, + const gchar *path_string, + const gchar *new_text, + gpointer data) +{ + GtkTreeModel *model = (GtkTreeModel *)data; + GtkTreePath *path = gtk_tree_path_new_from_string (path_string); + GtkTreeIter iter; + + g_print("cell edited '%s' path %s\n", new_text, path_string); + + + gint column = GPOINTER_TO_INT (g_object_get_data (G_OBJECT (cell), "column")); + + gtk_tree_model_get_iter (model, &iter, path); + + Currency *item; + + gtk_tree_model_get(model, &iter, LST_DEFCUR_DATAS, &item, -1); + + item->rate = atof(new_text); + + GLOBALS->changes_count++; + + + gtk_tree_path_free (path); +} +*/ + + +GtkWidget * +ui_cur_listview_new(gboolean withtoggle) +{ +GtkListStore *store; +GtkWidget *treeview; +GtkCellRenderer *renderer; +GtkTreeViewColumn *column; + + // create list store + store = gtk_list_store_new( + NUM_LST_DEFCUR, + G_TYPE_BOOLEAN, + G_TYPE_POINTER + ); + + // treeview + treeview = gtk_tree_view_new_with_model(GTK_TREE_MODEL(store)); + g_object_unref(store); + + // column 1: toggle + if( withtoggle == TRUE ) + { + renderer = gtk_cell_renderer_toggle_new (); + column = gtk_tree_view_column_new_with_attributes (_("Visible"), + renderer, + "active", LST_DEFCUR_TOGGLE, + NULL); + gtk_tree_view_append_column (GTK_TREE_VIEW(treeview), column); + + g_signal_connect (renderer, "toggled", + G_CALLBACK (ui_cur_listview_toggled_cb), store); + + } + + gtk_tree_view_set_grid_lines (GTK_TREE_VIEW (treeview), PREFS->grid_lines); + + + // column 1: name + renderer = gtk_cell_renderer_text_new (); + column = gtk_tree_view_column_new(); + gtk_tree_view_column_set_title(column, _("Name")); + gtk_tree_view_column_set_alignment (column, 0.5); + gtk_tree_view_column_pack_start(column, renderer, TRUE); + gtk_tree_view_column_set_cell_data_func(column, renderer, ui_cur_listview_name_cell_data_function, GINT_TO_POINTER(LST_DEFCUR_DATAS), NULL); + gtk_tree_view_column_set_resizable(column, TRUE); + gtk_tree_view_append_column (GTK_TREE_VIEW(treeview), column); + + // column 2: code + renderer = gtk_cell_renderer_text_new (); + g_object_set(renderer, "xalign", 0.5, NULL); + column = gtk_tree_view_column_new(); + gtk_tree_view_column_set_title(column, _("Symbol")); + gtk_tree_view_column_set_alignment (column, 0.5); + gtk_tree_view_column_pack_start(column, renderer, TRUE); + gtk_tree_view_column_set_cell_data_func(column, renderer, ui_cur_listview_symbol_cell_data_function, GINT_TO_POINTER(LST_DEFCUR_DATAS), NULL); + gtk_tree_view_column_set_resizable(column, TRUE); + gtk_tree_view_append_column (GTK_TREE_VIEW(treeview), column); + + // column 3: base rate + renderer = gtk_cell_renderer_text_new (); + //g_object_set (renderer, "editable", TRUE, NULL); + g_object_set(renderer, "xalign", 1.0, NULL); + column = gtk_tree_view_column_new(); + gtk_tree_view_column_set_title(column, _("Exchange rate")); + gtk_tree_view_column_set_alignment (column, 0.5); + gtk_tree_view_column_pack_start(column, renderer, TRUE); + gtk_tree_view_column_set_cell_data_func(column, renderer, ui_cur_listview_rate_cell_data_function, GINT_TO_POINTER(LST_DEFCUR_DATAS), NULL); + gtk_tree_view_column_set_resizable(column, TRUE); + gtk_tree_view_append_column (GTK_TREE_VIEW(treeview), column); + + //g_signal_connect (renderer, "edited", G_CALLBACK (ui_cur_listivew_rate_edited_func), GTK_TREE_MODEL(store)); + + // column 4: last modified + renderer = gtk_cell_renderer_text_new (); + g_object_set(renderer, "xalign", 0.5, NULL); + column = gtk_tree_view_column_new(); + gtk_tree_view_column_set_title(column, _("Last modfied")); + gtk_tree_view_column_set_alignment (column, 0.5); + gtk_tree_view_column_pack_start(column, renderer, TRUE); + gtk_tree_view_column_set_cell_data_func(column, renderer, ui_cur_listview_lastmodified_cell_data_function, GINT_TO_POINTER(LST_DEFCUR_DATAS), NULL); + gtk_tree_view_column_set_resizable(column, TRUE); + gtk_tree_view_append_column (GTK_TREE_VIEW(treeview), column); + + + // treeview attribute + gtk_tree_view_set_search_column(GTK_TREE_VIEW(treeview), 1); + //gtk_tree_view_set_headers_visible (GTK_TREE_VIEW(treeview), TRUE); + //gtk_tree_view_set_reorderable (GTK_TREE_VIEW(view), TRUE); + gtk_tree_sortable_set_sort_func(GTK_TREE_SORTABLE(store), LST_DEFCUR_DATAS, ui_cur_listview_compare_func, NULL, NULL); + gtk_tree_sortable_set_sort_column_id(GTK_TREE_SORTABLE(store), LST_DEFCUR_DATAS, GTK_SORT_ASCENDING); + + return treeview; +} + + +/* = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = */ +/* +** update the number sample label +*/ +static void ui_cur_edit_dialog_update_sample(GtkWidget *widget, gpointer user_data) +{ +struct ui_cur_edit_dialog_data *data; +Currency cur; +gchar formatd_buf[G_ASCII_DTOSTR_BUF_SIZE]; +gchar buf[128]; + + DB( g_print("\n[ui-pref] number sample\n") ); + + data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW)), "inst_data"); + + cur.symbol = (gchar *)gtk_entry_get_text(GTK_ENTRY(data->ST_symbol)); + cur.sym_prefix = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(data->CM_symisprefix)); + cur.decimal_char = (gchar *)gtk_entry_get_text(GTK_ENTRY(data->ST_decimalchar)); + cur.grouping_char = (gchar *)gtk_entry_get_text(GTK_ENTRY(data->ST_groupingchar)); + cur.frac_digits = gtk_spin_button_get_value(GTK_SPIN_BUTTON(data->NB_fracdigits)); + + da_cur_initformat (&cur); + DB( g_print("fmt: %s\n", cur.format) ); + + g_ascii_formatd(formatd_buf, sizeof (formatd_buf), cur.format, HB_NUMBER_SAMPLE); + + hb_str_formatd(buf, 127, formatd_buf, &cur, TRUE); + gtk_label_set_text(GTK_LABEL(data->LB_sample), buf); + +} + + + +static void ui_cur_edit_dialog_set(GtkWidget *widget, Currency *cur) +{ +struct ui_cur_edit_dialog_data *data; +Currency *base; +gchar formatd_buf[G_ASCII_DTOSTR_BUF_SIZE]; +gchar label[128]; + + data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW)), "inst_data"); + + g_snprintf(label, 127, "%s - %s", cur->iso_code, cur->name); + gtk_label_set_text (GTK_LABEL(data->LB_name), label); + + base = da_cur_get(GLOBALS->kcur); + + g_snprintf(label, 127, "1 %s _=", base->iso_code); + gtk_label_set_text_with_mnemonic (GTK_LABEL(data->LB_rate), label); + gtk_spin_button_set_value(GTK_SPIN_BUTTON(data->NB_rate), cur->rate); + + da_cur_initformat(cur); + g_ascii_formatd(formatd_buf, sizeof (formatd_buf), cur->format, HB_NUMBER_SAMPLE); + hb_str_formatd(label, 127, formatd_buf, cur, TRUE); + gtk_label_set_text (GTK_LABEL(data->LB_sample), label); + + ui_gtk_entry_set_text(data->ST_symbol, cur->symbol); + gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(data->CM_symisprefix), cur->sym_prefix); + ui_gtk_entry_set_text(data->ST_decimalchar, cur->decimal_char); + ui_gtk_entry_set_text(data->ST_groupingchar, cur->grouping_char); + gtk_spin_button_set_value(GTK_SPIN_BUTTON(data->NB_fracdigits), cur->frac_digits); + +} + + + +static void ui_cur_edit_dialog_get(GtkWidget *widget, Currency *cur) +{ +struct ui_cur_edit_dialog_data *data; +gdouble rate; + + data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW)), "inst_data"); + + + ui_gtk_entry_replace_text(data->ST_symbol, &cur->symbol); + cur->sym_prefix = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(data->CM_symisprefix)); + ui_gtk_entry_replace_text(data->ST_decimalchar, &cur->decimal_char); + ui_gtk_entry_replace_text(data->ST_groupingchar, &cur->grouping_char); + cur->frac_digits = gtk_spin_button_get_value(GTK_SPIN_BUTTON(data->NB_fracdigits)); + + da_cur_initformat(cur); + + rate = gtk_spin_button_get_value(GTK_SPIN_BUTTON(data->NB_rate)); + if(cur->rate != rate) + { + cur->rate = rate; + cur->mdate = GLOBALS->today; + } + +} + + +void ui_cur_edit_dialog_new(GtkWindow *parent, Currency *cur) +{ +struct ui_cur_edit_dialog_data data; +GtkWidget *dialog, *content_area, *content_grid, *group_grid; +GtkWidget *label, *widget, *expander; +gint crow, row; + + dialog = gtk_dialog_new_with_buttons ( + _("Edit currency"), + GTK_WINDOW (parent), + 0, + _("_Cancel"), + GTK_RESPONSE_REJECT, + _("_OK"), + GTK_RESPONSE_ACCEPT, + NULL); + + data.window = dialog; + + //store our dialog private data + g_object_set_data(G_OBJECT(dialog), "inst_data", (gpointer)&data); + DB( g_printf("(ui_cur_select_dialog_new) dialog=%x, inst_data=%x\n", (guint)dialog, (guint)&data) ); + + + content_area = gtk_dialog_get_content_area(GTK_DIALOG (dialog)); // return a vbox + + content_grid = gtk_grid_new(); + gtk_grid_set_row_spacing (GTK_GRID (content_grid), SPACING_LARGE); + gtk_orientable_set_orientation(GTK_ORIENTABLE(content_grid), GTK_ORIENTATION_VERTICAL); + gtk_container_set_border_width (GTK_CONTAINER(content_grid), SPACING_MEDIUM); + gtk_box_pack_start (GTK_BOX (content_area), content_grid, TRUE, TRUE, 0); + + crow = 0; + // group :: Currency + group_grid = gtk_grid_new (); + gtk_grid_set_row_spacing (GTK_GRID (group_grid), SPACING_SMALL); + gtk_grid_set_column_spacing (GTK_GRID (group_grid), SPACING_MEDIUM); + gtk_grid_attach (GTK_GRID (content_grid), group_grid, 0, crow++, 1, 1); + + label = make_label_group(_("Currency")); + gtk_grid_attach (GTK_GRID (group_grid), label, 0, 0, 3, 1); + + row = 1; + widget = make_label(NULL, 0, 0.5); + data.LB_name = widget; + gtk_grid_attach (GTK_GRID (group_grid), widget, 1, row, 2, 1); + + // group :: exchange + group_grid = gtk_grid_new (); + gtk_grid_set_row_spacing (GTK_GRID (group_grid), SPACING_SMALL); + gtk_grid_set_column_spacing (GTK_GRID (group_grid), SPACING_MEDIUM); + gtk_grid_attach (GTK_GRID (content_grid), group_grid, 0, crow++, 1, 1); + + label = make_label_group(_("Exchange rate")); + gtk_grid_attach (GTK_GRID (group_grid), label, 0, 0, 3, 1); + + row = 1; + label = make_label(NULL, 0, 0.5); + data.LB_rate = label; + gtk_grid_attach (GTK_GRID (group_grid), label, 1, row, 1, 1); + widget = make_exchange_rate(label); + data.NB_rate = widget; + gtk_grid_attach (GTK_GRID (group_grid), widget, 2, row, 1, 1); + + gtk_widget_set_sensitive(group_grid, (GLOBALS->kcur == cur->key) ? FALSE : TRUE); + + // group :: format + group_grid = gtk_grid_new (); + gtk_grid_set_row_spacing (GTK_GRID (group_grid), SPACING_SMALL); + gtk_grid_set_column_spacing (GTK_GRID (group_grid), SPACING_MEDIUM); + gtk_grid_attach (GTK_GRID (content_grid), group_grid, 0, crow++, 1, 1); + + label = make_label_group(_("Format")); + gtk_grid_attach (GTK_GRID (group_grid), label, 0, 0, 3, 1); + + row++; + widget = make_label(NULL, 0, 0.5); + data.LB_sample = widget; + gtk_grid_attach (GTK_GRID (group_grid), widget, 1, row, 2, 1); + + row++; + expander = gtk_expander_new_with_mnemonic (_("_Customize")); + gtk_grid_attach (GTK_GRID (group_grid), expander, 1, row, 2, 1); + + group_grid = gtk_grid_new (); + gtk_grid_set_row_spacing (GTK_GRID (group_grid), SPACING_SMALL); + gtk_grid_set_column_spacing (GTK_GRID (group_grid), SPACING_MEDIUM); + gtk_container_add (GTK_CONTAINER (expander), group_grid); + + row = 1; + label = make_label_widget(_("_Symbol:")); + gtk_grid_attach (GTK_GRID (group_grid), label, 1, row, 1, 1); + widget = make_string_maxlength(label, 3); + data.ST_symbol = widget; + gtk_grid_attach (GTK_GRID (group_grid), widget, 2, row, 1, 1); + + row++; + widget = gtk_check_button_new_with_mnemonic (_("Is pre_fix")); + data.CM_symisprefix = widget; + gtk_grid_attach (GTK_GRID (group_grid), widget, 2, row, 1, 1); + + row++; + label = make_label_widget(_("_Decimal char:")); + gtk_grid_attach (GTK_GRID (group_grid), label, 1, row, 1, 1); + widget = make_string_maxlength(label, 1); + data.ST_decimalchar = widget; + gtk_grid_attach (GTK_GRID (group_grid), widget, 2, row, 1, 1); + + row++; + label = make_label_widget(_("_Frac digits:")); + gtk_grid_attach (GTK_GRID (group_grid), label, 1, row, 1, 1); + widget = make_numeric(label, 0.0, 6.0); + data.NB_fracdigits = widget; + gtk_grid_attach (GTK_GRID (group_grid), widget, 2, row, 1, 1); + + row++; + label = make_label_widget(_("_Grouping char:")); + gtk_grid_attach (GTK_GRID (group_grid), label, 1, row, 1, 1); + widget = make_string_maxlength(label, 1); + data.ST_groupingchar = widget; + gtk_grid_attach (GTK_GRID (group_grid), widget, 2, row, 1, 1); + + + //gtk_window_resize(GTK_WINDOW(dialog), 400/PHI, 400); + + ui_cur_edit_dialog_set(dialog, cur); + + gtk_widget_show_all(content_area); + + //signals + g_signal_connect (data.ST_symbol , "changed", G_CALLBACK (ui_cur_edit_dialog_update_sample), NULL); + g_signal_connect (data.CM_symisprefix, "toggled", G_CALLBACK (ui_cur_edit_dialog_update_sample), NULL); + g_signal_connect (data.ST_decimalchar , "changed", G_CALLBACK (ui_cur_edit_dialog_update_sample), NULL); + g_signal_connect (data.ST_groupingchar, "changed", G_CALLBACK (ui_cur_edit_dialog_update_sample), NULL); + g_signal_connect (data.NB_fracdigits, "value-changed", G_CALLBACK (ui_cur_edit_dialog_update_sample), NULL); + + // wait for the user + gint result = gtk_dialog_run (GTK_DIALOG (dialog)); + if(result == GTK_RESPONSE_ACCEPT) + { + ui_cur_edit_dialog_get(dialog, cur); + } + + // cleanup and destroy + gtk_widget_destroy (dialog); + +} + + +/* = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = */ + +enum { + LST_CURSEL_NAME, + LST_CURSEL_ISO, + LST_CURSEL_FULLNAME, + LST_CURSEL_DATA, + NUM_LST_CURSEL +}; + + +static void ui_cur_select_rowactivated (GtkTreeView *treeview, GtkTreePath *path, GtkTreeViewColumn *col, gpointer userdata) +{ +struct ui_cur_select_dialog_data *data = userdata; + + gtk_dialog_response(GTK_DIALOG(data->window), GTK_RESPONSE_ACCEPT); +} + + +static GtkTreeModel *ui_cur_select_model_create (void) +{ +guint i = 0; +GtkListStore *store; +GtkTreeIter iter; +Currency4217 *cur; +gchar buffer[255]; + + /* create list store */ + store = gtk_list_store_new (NUM_LST_CURSEL, + G_TYPE_STRING, + G_TYPE_STRING, + G_TYPE_STRING, + G_TYPE_POINTER, + NULL + ); + + for (i = 0; i< n_iso4217cur; i++) + { + cur = &iso4217cur[i]; + + g_snprintf(buffer, 255-1, "%s - %s", cur->curr_iso_code, cur->name); + + gtk_list_store_append (store, &iter); + gtk_list_store_set (store, &iter, + LST_CURSEL_NAME, cur->name, + LST_CURSEL_ISO, cur->curr_iso_code, + LST_CURSEL_FULLNAME, buffer, + LST_CURSEL_DATA, cur, + -1); + + + } + + return GTK_TREE_MODEL (store); +} + + +static Currency4217 *ui_cur_select_dialog_get_langue(struct ui_cur_select_dialog_data *data) +{ +GtkTreeSelection *treeselection; +gboolean selected; +GtkTreeModel *model; +GtkTreeIter iter; +Currency4217 *curfmt = NULL; + + DB( g_printf("\n(ui_cur_select_dialog_get_langue)\n") ); + + treeselection = gtk_tree_view_get_selection (GTK_TREE_VIEW(data->LV_cur)); + selected = gtk_tree_selection_get_selected(treeselection, &model, &iter); + if(selected) + { + gtk_tree_model_get(model, &iter, LST_CURSEL_DATA, &curfmt, -1); + + DB( g_printf(" - iso is '%s'\n", curfmt->curr_iso_code) ); + } + + return curfmt; +} + + +static void +ui_cur_select_search_changed_cb (GtkWidget *widget, gpointer user_data) +{ +struct ui_cur_select_dialog_data *data = user_data; + + DB( g_print(" search changed\n") ); + + gtk_tree_model_filter_refilter(GTK_TREE_MODEL_FILTER(data->modelfilter)); + +} + + +static gboolean +ui_cur_select_model_func_visible (GtkTreeModel *model, + GtkTreeIter *iter, + gpointer data) +{ + // Visible if row is non-empty and first column is “HI” + gchar *str; + gboolean visible = TRUE; + GtkEntry *entry = data; + + if(!GTK_IS_ENTRY(entry)) + return TRUE; + + gchar *needle = g_ascii_strdown(gtk_entry_get_text(entry), -1); + + gtk_tree_model_get (model, iter, LST_CURSEL_FULLNAME, &str, -1); + + gchar *haystack = g_ascii_strdown(str, -1); + + if (str && g_strrstr (haystack, needle) == NULL) + { + visible = FALSE; + } + + DB( g_print("filter: '%s' '%s' %d\n", str, needle, visible) ); + + g_free(haystack); + g_free(needle); + g_free (str); + + return visible; +} + + +Currency4217 * ui_cur_select_dialog_new(GtkWindow *parent, gint select_mode) +{ +struct ui_cur_select_dialog_data data; +GtkWidget *dialog, *content_area, *content_grid, *group_grid; +GtkWidget *scrollwin, *treeview, *widget; +gint crow, row; +Currency4217 *curfmt = NULL; + + dialog = gtk_dialog_new_with_buttons ( + (select_mode == CUR_SELECT_MODE_BASE) ? _("Select base currency") : _("Select currency"), + GTK_WINDOW (parent), + 0, + _("_Cancel"), + GTK_RESPONSE_REJECT, + _("_OK"), + GTK_RESPONSE_ACCEPT, + NULL); + + data.window = dialog; + + //store our dialog private data + g_object_set_data(G_OBJECT(dialog), "inst_data", (gpointer)&data); + DB( g_printf("(ui_cur_select_dialog_new) dialog=%x, inst_data=%x\n", (guint)dialog, (guint)&data) ); + + + content_area = gtk_dialog_get_content_area(GTK_DIALOG (dialog)); // return a vbox + + content_grid = gtk_grid_new(); + gtk_grid_set_row_spacing (GTK_GRID (content_grid), SPACING_LARGE); + gtk_orientable_set_orientation(GTK_ORIENTABLE(content_grid), GTK_ORIENTATION_VERTICAL); + gtk_container_set_border_width (GTK_CONTAINER(content_grid), SPACING_MEDIUM); + gtk_box_pack_start (GTK_BOX (content_area), content_grid, TRUE, TRUE, 0); + + crow = 0; + // group :: Search + group_grid = gtk_grid_new (); + gtk_grid_set_row_spacing (GTK_GRID (group_grid), SPACING_SMALL); + gtk_grid_set_column_spacing (GTK_GRID (group_grid), SPACING_MEDIUM); + gtk_grid_attach (GTK_GRID (content_grid), group_grid, 0, crow++, 1, 1); + + row = 1; + widget = gtk_search_entry_new(); + data.ST_search = widget; + gtk_widget_set_hexpand (widget, TRUE); + gtk_grid_attach (GTK_GRID (group_grid), widget, 1, row, 1, 1); + + + row++; + scrollwin = gtk_scrolled_window_new(NULL,NULL); + gtk_grid_attach (GTK_GRID (group_grid), scrollwin, 1, row, 1, 1); + + gtk_widget_set_vexpand (scrollwin, TRUE); + gtk_scrolled_window_set_shadow_type (GTK_SCROLLED_WINDOW (scrollwin), GTK_SHADOW_ETCHED_IN); + gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(scrollwin), GTK_POLICY_NEVER, GTK_POLICY_AUTOMATIC); + + //test treefilter + data.model = ui_cur_select_model_create(); + data.modelfilter = gtk_tree_model_filter_new(GTK_TREE_MODEL(data.model), NULL); + gtk_tree_model_filter_set_visible_func(GTK_TREE_MODEL_FILTER(data.modelfilter), ui_cur_select_model_func_visible, data.ST_search, NULL); + data.sortmodel = gtk_tree_model_sort_new_with_model(data.modelfilter); + + + // + + treeview = gtk_tree_view_new_with_model (GTK_TREE_MODEL(data.sortmodel)); + data.LV_cur = treeview; + //gtk_tree_view_set_search_column (GTK_TREE_VIEW (treeview), LST_CURSEL_NAME); + gtk_tree_sortable_set_sort_column_id(GTK_TREE_SORTABLE(data.sortmodel), LST_CURSEL_NAME, GTK_SORT_ASCENDING); + //g_object_unref (model); + gtk_container_add(GTK_CONTAINER(scrollwin), treeview); + + // populate list + GtkCellRenderer *renderer; + GtkTreeViewColumn *column; + + renderer = gtk_cell_renderer_text_new (); + column = gtk_tree_view_column_new_with_attributes (_("Name"), renderer, "text", LST_CURSEL_NAME, NULL); + gtk_tree_view_column_set_sort_column_id (column, LST_CURSEL_NAME); + gtk_tree_view_append_column (GTK_TREE_VIEW (treeview), column); + + renderer = gtk_cell_renderer_text_new (); + column = gtk_tree_view_column_new_with_attributes (_("ISO Code"), renderer, "text", LST_CURSEL_ISO, NULL); + gtk_tree_view_column_set_sort_column_id (column, LST_CURSEL_ISO); + gtk_tree_view_append_column (GTK_TREE_VIEW (treeview), column); + + gtk_window_resize(GTK_WINDOW(dialog), 400/PHI, 400); + + + gtk_widget_show_all(content_area); + + // signals + g_signal_connect (data.ST_search, "search-changed", G_CALLBACK (ui_cur_select_search_changed_cb), &data); + g_signal_connect (GTK_TREE_VIEW(data.LV_cur), "row-activated", G_CALLBACK (ui_cur_select_rowactivated), &data); + + + // wait for the user + gint result = gtk_dialog_run (GTK_DIALOG (dialog)); + if(result == GTK_RESPONSE_ACCEPT) + { + curfmt = ui_cur_select_dialog_get_langue(&data); + } + + + // cleanup and destroy + gtk_widget_destroy (dialog); + + return curfmt; +} + + +/* = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = */ + + +gint ui_cur_manage_dialog_update_currencies(GtkWindow *parent) +{ +GError *error = NULL; +gboolean retcode = FALSE; + + DB( g_printf("\n(ui_cur_manage) update currencies\n") ); + + // do nothing if just the base currency + if(da_cur_length() <= 1) + return TRUE; + + retcode = currency_sync_online(&error); + + DB( g_print("retcode: %d\n", retcode) ); + + if(!retcode) + { + gchar *msg = _("Unknow error"); + + if( error ) + msg = error->message; + + g_warning("update online: '%s'", msg); + + ui_dialog_msg_infoerror(GTK_WINDOW(parent), GTK_MESSAGE_ERROR, + _("Update online error"), + msg, + NULL + ); + + if( error ) + g_error_free (error); + } + + return retcode; +} + + +static void +ui_cur_manage_dialog_sync(GtkWidget *widget, gpointer user_data) +{ +struct ui_cur_manage_dialog_data *data; +gboolean retcode; + + DB( g_printf("\n(ui_cur_manage) sync online\n") ); + + data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW)), "inst_data"); + + retcode = ui_cur_manage_dialog_update_currencies(GTK_WINDOW(data->window)); + + if(retcode == TRUE) + { + gtk_tree_view_columns_autosize (GTK_TREE_VIEW(data->LV_cur)); + //todo: (or not) msg with changes + + } +} + + +/** + * ui_cur_manage_dialog_add: + * + */ +static void +ui_cur_manage_dialog_add(GtkWidget *widget, gpointer user_data) +{ +struct ui_cur_manage_dialog_data *data; +Currency4217 *curfmt; + + DB( g_printf("\n(ui_cur_manage) add\n") ); + + data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW)), "inst_data"); + + curfmt = ui_cur_select_dialog_new(GTK_WINDOW(data->window), CUR_SELECT_MODE_NORMAL); + if( curfmt != NULL ) + { + Currency *item; + + DB( g_printf("- user selected: '%s' '%s'\n", curfmt->curr_iso_code, curfmt->name) ); + item = da_cur_get_by_iso_code(curfmt->curr_iso_code); + if( item == NULL ) + { + item = currency_add_from_user(curfmt); + ui_cur_listview_add(GTK_TREE_VIEW(data->LV_cur), item); + gtk_tree_sortable_sort_column_changed(GTK_TREE_SORTABLE(gtk_tree_view_get_model(GTK_TREE_VIEW(data->LV_cur)))); + + ui_cur_manage_dialog_update (widget, user_data); + GLOBALS->changes_count++; + } + else + { + DB( g_printf("- already exists\n") ); + } + } +} + + + +static void +ui_cur_manage_dialog_modify(GtkWidget *widget, gpointer user_data) +{ +struct ui_cur_manage_dialog_data *data; +GtkTreeSelection *selection; +GtkTreeModel *model; +GtkTreeIter iter; + + DB( g_printf("\n(ui_cur_manage) modify\n") ); + + + data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW)), "inst_data"); + + selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(data->LV_cur)); + if (gtk_tree_selection_get_selected(selection, &model, &iter)) + { + Currency *item; + + gtk_tree_model_get(model, &iter, LST_DEFCUR_DATAS, &item, -1); + + if( item!= NULL ) + { + ui_cur_edit_dialog_new(GTK_WINDOW(data->window), item); + GLOBALS->changes_count++; + } + + } +} + + +/* +** remove the selected curee to our treeview and temp GList +*/ +static void ui_cur_manage_dialog_remove(GtkWidget *widget, gpointer user_data) +{ +struct ui_cur_manage_dialog_data *data; +guint32 key; +gboolean do_remove, result; + + DB( g_printf("\n(ui_cur_manage) remove\n") ); + + data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW)), "inst_data"); + + do_remove = TRUE; + key = ui_cur_listview_get_selected_key(GTK_TREE_VIEW(data->LV_cur)); + if( key > 0 ) + { + Currency *cur; + gchar *title; + gchar *secondtext; + + if( currency_is_used(key) == TRUE ) + { + do_remove = FALSE; + } + else + { + cur = da_cur_get(key); + + title = g_strdup_printf ( + _("Are you sure you want to permanently delete '%s'?"), cur->name); + + secondtext = _("If you delete a currency, it will be permanently lost."); + + result = ui_dialog_msg_confirm_alert( + GTK_WINDOW(data->window), + title, + secondtext, + _("_Delete") + ); + + g_free(title); + + do_remove = (result == GTK_RESPONSE_OK) ? TRUE :FALSE; + } + + if( do_remove ) + { + da_cur_remove(key); + ui_cur_listview_remove_selected(GTK_TREE_VIEW(data->LV_cur)); + ui_cur_manage_dialog_update (widget, user_data); + data->change++; + } + } + +} + +/* +** button callback: set base currency +*/ +static void ui_cur_manage_dialog_setbase(GtkWidget *widget, gpointer user_data) +{ +struct ui_cur_manage_dialog_data *data; +guint32 key; +gboolean do_change; + + DB( g_printf("\n(ui_cur_manage) setbase\n") ); + + + data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW)), "inst_data"); + + key = ui_cur_listview_get_selected_key(GTK_TREE_VIEW(data->LV_cur)); + if( key > 0 ) + { + do_change = ui_dialog_msg_question( + GTK_WINDOW(data->window), + _("Change the base currency"), + _("If you proceed, rates of other currencies\n" + "will be set to 0, don't forget to update it"), + NULL + ); + if(do_change == GTK_RESPONSE_YES) + { + hbfile_change_basecurrency(key); + gtk_tree_view_columns_autosize(GTK_TREE_VIEW(data->LV_cur)); + } + } + +} + + +/* +** +*/ +static void ui_cur_manage_dialog_update(GtkWidget *treeview, gpointer user_data) +{ +struct ui_cur_manage_dialog_data *data; +GtkTreeSelection *selection; +GtkTreeModel *model; +GtkTreeIter iter; +Currency *item; +gboolean sensitive; + + DB( g_printf("\n(ui_cur_manage_dialog) update\n") ); + + data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(GTK_WIDGET(treeview), GTK_TYPE_WINDOW)), "inst_data"); + + sensitive = da_cur_length() <= 1 ? FALSE : TRUE; + gtk_widget_set_sensitive (data->BB_update, sensitive); + + + selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(data->LV_cur)); + + //if true there is a selected node + if (gtk_tree_selection_get_selected(selection, &model, &iter)) + { + gtk_tree_model_get(model, &iter, LST_DEFCUR_DATAS, &item, -1); + + gtk_widget_set_sensitive(data->BT_edit, TRUE); + + sensitive = !(currency_is_used(item->key)); + //gtk_widget_set_sensitive(data->BT_mov, sensitive); + //gtk_widget_set_sensitive(data->BT_mod, sensitive); + gtk_widget_set_sensitive(data->BT_rem, sensitive); + + //disable set as base on actual base currency + sensitive = (item->key != GLOBALS->kcur) ? TRUE : FALSE; + gtk_widget_set_sensitive(data->BT_base, sensitive); + } + else + { + gtk_widget_set_sensitive(data->BT_edit, FALSE); + gtk_widget_set_sensitive(data->BT_rem , FALSE); + gtk_widget_set_sensitive(data->BT_base, FALSE); + } +} + + +/* +** +*/ +static void ui_cur_manage_dialog_selection(GtkTreeSelection *treeselection, gpointer user_data) +{ + ui_cur_manage_dialog_update(GTK_WIDGET(gtk_tree_selection_get_tree_view (treeselection)), NULL); +} + +static void ui_cur_manage_dialog_onRowActivated (GtkTreeView *treeview, + GtkTreePath *path, + GtkTreeViewColumn *col, + gpointer userdata) +{ + + //model = gtk_tree_view_get_model(treeview); + //gtk_tree_model_get_iter_first(model, &iter); + //if(gtk_tree_selection_iter_is_selected(gtk_tree_view_get_selection(GTK_TREE_VIEW(treeview)), &iter) == FALSE) + //{ + ui_cur_manage_dialog_modify(GTK_WIDGET(treeview), NULL); + //} +} + + + +/* +** +*/ +static void ui_cur_manage_dialog_setup(struct ui_cur_manage_dialog_data *data) +{ + + DB( g_printf("\n(ui_cur_manage_setup)\n") ); + + + ui_cur_listview_populate(data->LV_cur); + + //ui_cur_combobox_populate(data->CY_curr, GLOBALS->h_cur); + //ui_cur_combobox_set_active(GTK_COMBO_BOX(data->CY_curr), GLOBALS->kcur); + + + +} + + +/* +** +*/ +GtkWidget *ui_cur_manage_dialog (void) +{ +struct ui_cur_manage_dialog_data data; +GtkWidget *dialog, *content_area, *content_grid, *group_grid, *bbox; +GtkWidget *widget, *scrollwin, *treeview; +gint crow, row, w, h; + + DB( g_printf("\n(ui_cur_manage_dialog)\n") ); + + dialog = gtk_dialog_new_with_buttons (_("Currencies"), + GTK_WINDOW(GLOBALS->mainwindow), + 0, + _("_Close"), + GTK_RESPONSE_ACCEPT, + NULL); + + data.window = dialog; + data.change = 0; + + //set the dialog icon + gtk_window_set_icon_name(GTK_WINDOW (dialog), ICONNAME_HB_CURRENCY); + + //set a nice dialog size + gtk_window_get_size(GTK_WINDOW(GLOBALS->mainwindow), &w, &h); + gtk_window_set_default_size (GTK_WINDOW(dialog), -1, h/PHI); + + + //store our window private data + g_object_set_data(G_OBJECT(dialog), "inst_data", (gpointer)&data); + DB( g_printf("(ui_cur_manage_dialog) dialog=%p, inst_data=%p\n", dialog, &data) ); + + g_signal_connect (dialog, "destroy", + G_CALLBACK (gtk_widget_destroyed), &dialog); + + content_area = gtk_dialog_get_content_area(GTK_DIALOG (dialog)); // return a vbox + + content_grid = gtk_grid_new(); + gtk_grid_set_row_spacing (GTK_GRID (content_grid), SPACING_LARGE); + gtk_orientable_set_orientation(GTK_ORIENTABLE(content_grid), GTK_ORIENTATION_VERTICAL); + gtk_container_set_border_width (GTK_CONTAINER(content_grid), SPACING_MEDIUM); + gtk_box_pack_start (GTK_BOX (content_area), content_grid, TRUE, TRUE, 0); + + crow = 0; + // group :: -------- + group_grid = gtk_grid_new (); + gtk_grid_set_row_spacing (GTK_GRID (group_grid), SPACING_SMALL); + gtk_grid_set_column_spacing (GTK_GRID (group_grid), SPACING_MEDIUM); + gtk_grid_attach (GTK_GRID (content_grid), group_grid, 0, crow++, 1, 1); + + row = 1; + bbox = gtk_box_new(GTK_ORIENTATION_HORIZONTAL, SPACING_MEDIUM); + data.BB_update = bbox; + gtk_grid_attach (GTK_GRID(group_grid), bbox, 0, row, 1, 1); + + widget = gtk_button_new_from_icon_name (ICONNAME_REFRESH, GTK_ICON_SIZE_BUTTON); + gtk_container_add (GTK_CONTAINER (bbox), widget); + + g_signal_connect (G_OBJECT (widget), "clicked", G_CALLBACK (ui_cur_manage_dialog_sync), NULL); + + widget = make_label_widget (_("Update online")); + gtk_container_add (GTK_CONTAINER (bbox), widget); + + row++; + scrollwin = gtk_scrolled_window_new(NULL,NULL); + gtk_scrolled_window_set_shadow_type (GTK_SCROLLED_WINDOW (scrollwin), GTK_SHADOW_ETCHED_IN); + gtk_scrolled_window_set_policy(GTK_SCROLLED_WINDOW(scrollwin), GTK_POLICY_NEVER, GTK_POLICY_AUTOMATIC); + gtk_scrolled_window_set_min_content_height(GTK_SCROLLED_WINDOW(scrollwin), HB_MINHEIGHT_LIST); + treeview = ui_cur_listview_new(FALSE); + data.LV_cur = treeview; + gtk_container_add(GTK_CONTAINER(scrollwin), treeview); + gtk_widget_set_vexpand (scrollwin, TRUE); + gtk_widget_set_hexpand (scrollwin, TRUE); + gtk_grid_attach (GTK_GRID(group_grid), scrollwin, 0, row, 2, 1); + + row++; + bbox = gtk_button_box_new (GTK_ORIENTATION_HORIZONTAL); + gtk_button_box_set_layout (GTK_BUTTON_BOX (bbox), GTK_BUTTONBOX_START); + gtk_box_set_spacing (GTK_BOX (bbox), SPACING_SMALL); + gtk_grid_attach (GTK_GRID (group_grid), bbox, 0, row, 2, 1); + + widget = gtk_button_new_with_mnemonic(_("_Add")); + data.BT_add = widget; + gtk_container_add (GTK_CONTAINER (bbox), widget); + + widget = gtk_button_new_with_mnemonic(_("_Edit")); + data.BT_edit = widget; + gtk_container_add (GTK_CONTAINER (bbox), widget); + + widget = gtk_button_new_with_mnemonic(_("_Delete")); + data.BT_rem = widget; + gtk_container_add (GTK_CONTAINER (bbox), widget); + + widget = gtk_button_new_with_mnemonic(_("Set as base")); + data.BT_base = widget; + gtk_container_add (GTK_CONTAINER (bbox), widget); + + + //connect all our signals + //g_signal_connect (G_OBJECT (data.ST_name), "activate", G_CALLBACK (ui_cur_manage_dialog_add), NULL); + + g_signal_connect (gtk_tree_view_get_selection(GTK_TREE_VIEW(data.LV_cur)), "changed", G_CALLBACK (ui_cur_manage_dialog_selection), NULL); + g_signal_connect (GTK_TREE_VIEW(data.LV_cur), "row-activated", G_CALLBACK (ui_cur_manage_dialog_onRowActivated), NULL); + + g_signal_connect (G_OBJECT (data.BT_add), "clicked", G_CALLBACK (ui_cur_manage_dialog_add), NULL); + g_signal_connect (G_OBJECT (data.BT_rem), "clicked", G_CALLBACK (ui_cur_manage_dialog_remove), NULL); + g_signal_connect (G_OBJECT (data.BT_edit), "clicked", G_CALLBACK (ui_cur_manage_dialog_modify), NULL); + //g_signal_connect (G_OBJECT (data.BT_mov), "clicked", G_CALLBACK (ui_cur_manage_dialog_move), NULL); + g_signal_connect (G_OBJECT (data.BT_base), "clicked", G_CALLBACK (ui_cur_manage_dialog_setbase), NULL); + + //setup, init and show window + ui_cur_manage_dialog_setup(&data); + + ui_cur_manage_dialog_update(data.LV_cur, NULL); + + //gtk_window_resize(GTK_WINDOW(dialog), 256, 414); + + gtk_widget_show_all (dialog); + + //wait for the user + gint result = gtk_dialog_run (GTK_DIALOG (dialog)); + + switch (result) + { + case GTK_RESPONSE_ACCEPT: + //do_application_specific_something (); + break; + default: + //do_nothing_since_dialog_was_cancelled (); + break; + } + + + // cleanup and destroy + GLOBALS->changes_count += data.change; + gtk_widget_destroy (dialog); + + return NULL; +} + + +