X-Git-Url: https://git.dogcows.com/gitweb?p=chaz%2Fhomebank;a=blobdiff_plain;f=src%2Fui-tag.c;fp=src%2Fui-tag.c;h=d8c9806fa36f0a570d0216b0ca370f49acfbb2fe;hp=0000000000000000000000000000000000000000;hb=a6c6b0df5492c2160ed97e3a376bdb2fe7c5ebc4;hpb=cd13d9691c46c2b2d6d459e9e6a76bed1c21b7a6 diff --git a/src/ui-tag.c b/src/ui-tag.c new file mode 100644 index 0000000..d8c9806 --- /dev/null +++ b/src/ui-tag.c @@ -0,0 +1,702 @@ +/* HomeBank -- Free, easy, personal accounting for everyone. + * Copyright (C) 1995-2019 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 ofdeftransaction_amountchanged + * 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-tag.h" + + +/****************************************************************************/ +/* Debug macros */ +/****************************************************************************/ +#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; + + +/* = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = */ + + +void +ui_tag_combobox_populate(GtkComboBoxText *combobox) +{ +GList *ltag, *list; + + //populate template + hbtk_combo_box_text_append(GTK_COMBO_BOX_TEXT(combobox), 0, "----"); + gtk_combo_box_set_active(GTK_COMBO_BOX(combobox), 0); + + ltag = list = tag_glist_sorted(1); + while (list != NULL) + { + Tag *item = list->data; + + DB( g_print(" populate: %d\n", item->key) ); + + hbtk_combo_box_text_append(GTK_COMBO_BOX_TEXT(combobox), item->key, item->name); + list = g_list_next(list); + } + + g_list_free(ltag); + +} + + +GtkWidget * +ui_tag_combobox_new(GtkWidget *label) +{ +GtkWidget *combobox; + + combobox = hbtk_combo_box_new(label); + return combobox; +} + + +/* = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = */ + + +static void +ui_tag_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_DEFTAG_TOGGLE, &fixed, -1); + + /* do something with the value */ + fixed ^= 1; + + /* set new value */ + gtk_list_store_set (GTK_LIST_STORE (model), &iter, LST_DEFTAG_TOGGLE, fixed, -1); + + /* clean up */ + gtk_tree_path_free (path); +} + +static gint +ui_tag_listview_compare_func (GtkTreeModel *model, GtkTreeIter *a, GtkTreeIter *b, gpointer userdata) +{ +gint retval = 0; +Tag *entry1, *entry2; +//gchar *name1, *name2; + + gtk_tree_model_get(model, a, LST_DEFTAG_DATAS, &entry1, -1); + gtk_tree_model_get(model, b, LST_DEFTAG_DATAS, &entry2, -1); + + retval = hb_string_utf8_compare(entry1->name, entry2->name); + + return retval; +} + + +static void +ui_tag_listview_name_cell_data_function (GtkTreeViewColumn *col, + GtkCellRenderer *renderer, + GtkTreeModel *model, + GtkTreeIter *iter, + gpointer user_data) +{ +Tag *entry; +gchar *name; +#if MYDEBUG +gchar *string; +#endif + + gtk_tree_model_get(model, iter, LST_DEFTAG_DATAS, &entry, -1); + if(entry->name == NULL) + name = _("(none)"); // can never occurs ! + else + name = entry->name; + + #if MYDEBUG + string = g_strdup_printf ("[%d] %s", entry->key, name ); + g_object_set(renderer, "text", string, NULL); + g_free(string); + #else + g_object_set(renderer, "text", name, NULL); + #endif + +} + + + +/* = = = = = = = = = = = = = = = = */ + +/** + * tag_list_add: + * + * Add a single element (useful for dynamics add) + * + * Return value: -- + * + */ +void +ui_tag_listview_add(GtkTreeView *treeview, Tag *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_DEFTAG_TOGGLE, FALSE, + LST_DEFTAG_DATAS, item, + -1); + + gtk_tree_selection_select_iter (gtk_tree_view_get_selection(GTK_TREE_VIEW(treeview)), &iter); + + } +} + +guint32 +ui_tag_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)) + { + Tag *item; + + gtk_tree_model_get(model, &iter, LST_DEFTAG_DATAS, &item, -1); + + if( item!= NULL ) + return item->key; + } + return 0; +} + +void +ui_tag_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); + } +} + + +void ui_tag_listview_populate(GtkWidget *view, gint insert_type) +{ +GtkTreeModel *model; +GtkTreeIter iter; +GList *ltag, *list; + + 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_tag, (GHFunc)ui_tag_listview_populate_ghfunc, model); + ltag = list = g_hash_table_get_values(GLOBALS->h_tag); + while (list != NULL) + { + Tag *item = list->data; + + DB( g_print(" populate: %d\n", item->key) ); + + gtk_list_store_append (GTK_LIST_STORE(model), &iter); + gtk_list_store_set (GTK_LIST_STORE(model), &iter, + LST_DEFTAG_TOGGLE , FALSE, + LST_DEFTAG_DATAS, item, + -1); + + list = g_list_next(list); + } + g_list_free(ltag); + + gtk_tree_view_set_model(GTK_TREE_VIEW(view), model); /* Re-attach model to view */ + g_object_unref(model); +} + + +GtkWidget * +ui_tag_listview_new(gboolean withtoggle) +{ +GtkListStore *store; +GtkWidget *treeview; +GtkCellRenderer *renderer; +GtkTreeViewColumn *column; + + // create list store + store = gtk_list_store_new(NUM_LST_DEFTAG, + G_TYPE_BOOLEAN, + G_TYPE_POINTER + ); + + // treeview + treeview = gtk_tree_view_new_with_model(GTK_TREE_MODEL(store)); + g_object_unref(store); + + gtk_tree_view_set_grid_lines (GTK_TREE_VIEW (treeview), PREFS->grid_lines); + + // column 1: toggle + if( withtoggle == TRUE ) + { + renderer = gtk_cell_renderer_toggle_new (); + column = gtk_tree_view_column_new_with_attributes (_("Visible"), + renderer, + "active", LST_DEFTAG_TOGGLE, + NULL); + gtk_tree_view_append_column (GTK_TREE_VIEW(treeview), column); + + g_signal_connect (renderer, "toggled", + G_CALLBACK (ui_tag_listview_toggled_cb), store); + + } + + // column 2: name + column = gtk_tree_view_column_new(); + + renderer = gtk_cell_renderer_text_new (); + g_object_set(renderer, + "ellipsize", PANGO_ELLIPSIZE_END, + "ellipsize-set", TRUE, + NULL); + + gtk_tree_view_column_pack_start(column, renderer, TRUE); + gtk_tree_view_column_set_cell_data_func(column, renderer, ui_tag_listview_name_cell_data_function, GINT_TO_POINTER(LST_DEFTAG_DATAS), NULL); + + gtk_tree_view_column_set_resizable(column, TRUE); + gtk_tree_view_append_column (GTK_TREE_VIEW(treeview), column); + + // treeviewattribute + gtk_tree_view_set_headers_visible (GTK_TREE_VIEW(treeview), FALSE); + gtk_tree_view_set_reorderable (GTK_TREE_VIEW(treeview), TRUE); + + gtk_tree_sortable_set_default_sort_func(GTK_TREE_SORTABLE(store), ui_tag_listview_compare_func, NULL, NULL); + gtk_tree_sortable_set_sort_column_id(GTK_TREE_SORTABLE(store), GTK_TREE_SORTABLE_DEFAULT_SORT_COLUMN_ID, GTK_SORT_ASCENDING); + + return treeview; +} + + + +/* = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = */ + + +/** + * ui_tag_manage_dialog_add: + * + */ +static void +ui_tag_manage_dialog_add(GtkWidget *widget, gpointer user_data) +{ +struct ui_tag_manage_dialog_data *data; +Tag *item; +gchar *name; + + data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW)), "inst_data"); + DB( g_print("(defayee) add (data=%p)\n", data) ); + + name = (gchar *)gtk_entry_get_text(GTK_ENTRY(data->ST_name)); + + item = da_tag_malloc (); + item->name = g_strdup(name); + + g_strstrip(item->name); + + if( strlen(item->name) > 0 ) + { + if( da_tag_append(item) ) + { + ui_tag_listview_add(GTK_TREE_VIEW(data->LV_tag), item); + data->change++; + } + } + else + da_tag_free (item); + + gtk_entry_set_text(GTK_ENTRY(data->ST_name), ""); +} + + +static void ui_tag_manage_dialog_edit_entry_cb(GtkEditable *editable, gpointer user_data) +{ +GtkDialog *window = user_data; +const gchar *buffer; + + buffer = gtk_entry_get_text(GTK_ENTRY(editable)); + gtk_dialog_set_response_sensitive(GTK_DIALOG(window), GTK_RESPONSE_ACCEPT, strlen(buffer) > 0 ? TRUE : FALSE); +} + + +static void ui_tag_manage_dialog_edit(GtkWidget *dowidget, gpointer user_data) +{ +struct ui_tag_manage_dialog_data *data; +GtkWidget *dialog, *content_area, *content_grid, *group_grid; +GtkWidget *label, *widget; +GtkWidget *ST_name; +gint crow, row; +guint32 key; + + data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(dowidget, GTK_TYPE_WINDOW)), "inst_data"); + DB( g_print("(defayee) modify %p\n", data) ); + + key = ui_tag_listview_get_selected_key(GTK_TREE_VIEW(data->LV_tag)); + if( key > 0 ) + { + Tag *item; + + item = da_tag_get( key ); + + dialog = gtk_dialog_new_with_buttons (_("Edit..."), + GTK_WINDOW (data->window), + 0, + _("_Cancel"), + GTK_RESPONSE_REJECT, + _("_OK"), + GTK_RESPONSE_ACCEPT, + NULL); + + content_area = gtk_dialog_get_content_area(GTK_DIALOG (dialog)); + + 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 :: General + 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(_("General")); + //gtk_grid_attach (GTK_GRID (group_grid), label, 0, 0, 3, 1); + + row = 1; + label = make_label_widget(_("_Name:")); + gtk_grid_attach (GTK_GRID (group_grid), label, 1, row, 1, 1); + widget = gtk_entry_new(); + ST_name = widget; + gtk_widget_set_hexpand(widget, TRUE); + gtk_grid_attach (GTK_GRID (group_grid), widget, 2, row, 1, 1); + + g_signal_connect (G_OBJECT (ST_name), "changed", G_CALLBACK (ui_tag_manage_dialog_edit_entry_cb), dialog); + + gtk_widget_show_all(content_grid); + + + gtk_dialog_set_default_response(GTK_DIALOG( dialog ), GTK_RESPONSE_ACCEPT); + + //wait for the user + gint result = gtk_dialog_run (GTK_DIALOG (dialog)); + + if(result == GTK_RESPONSE_ACCEPT) + { + const gchar *name; + + // 1: manage renaming + name = gtk_entry_get_text(GTK_ENTRY(ST_name)); + // ignore if item is empty + if (name && *name) + { + if( tag_rename(item, name) ) + { + //to redraw the active entry + gtk_tree_view_columns_autosize (GTK_TREE_VIEW(data->LV_tag)); + data->change++; + } + else + { + ui_dialog_msg_infoerror(GTK_WINDOW(dialog), GTK_MESSAGE_ERROR, + _("Error"), + _("Cannot rename this Tag,\n" + "from '%s' to '%s',\n" + "this name already exists."), + item->name, + name + ); + + } + } + + + } + + // cleanup and destroy + gtk_widget_destroy (dialog); + } + +} + + +/* +** delete the selected payee to our treeview and temp GList +*/ +static void ui_tag_manage_dialog_delete(GtkWidget *widget, gpointer user_data) +{ +struct ui_tag_manage_dialog_data *data; +Tag *item; +guint32 key; +gint result; + + + data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(widget, GTK_TYPE_WINDOW)), "inst_data"); + DB( g_print("(ui_tag_manage_dialog) delete (data=%p)\n", data) ); + + key = ui_tag_listview_get_selected_key(GTK_TREE_VIEW(data->LV_tag)); + if( key > 0 ) + { + gchar *title; + gchar *secondtext = NULL; + + item = da_tag_get(key); + + title = g_strdup_printf ( + _("Are you sure you want to permanently delete '%s'?"), item->name); + + if( item->usage_count > 0 ) + { + secondtext = _("This payee is used.\n" + "Any transaction using that payee will be set to (no payee)"); + } + + result = ui_dialog_msg_confirm_alert( + GTK_WINDOW(data->window), + title, + secondtext, + _("_Delete") + ); + + g_free(title); + + if( result == GTK_RESPONSE_OK ) + { + payee_move(key, 0); + ui_tag_listview_remove_selected(GTK_TREE_VIEW(data->LV_tag)); + da_tag_remove(key); + data->change++; + } + + } +} + + +static void ui_tag_manage_dialog_update(GtkWidget *treeview, gpointer user_data) +{ +struct ui_tag_manage_dialog_data *data; +gboolean sensitive; +guint32 key; + + DB( g_print("\n(ui_tag_manage_dialog) cursor changed\n") ); + + data = g_object_get_data(G_OBJECT(gtk_widget_get_ancestor(GTK_WIDGET(treeview), GTK_TYPE_WINDOW)), "inst_data"); + + key = ui_tag_listview_get_selected_key(GTK_TREE_VIEW(data->LV_tag)); + + sensitive = (key > 0) ? TRUE : FALSE; + gtk_widget_set_sensitive(data->BT_edit, sensitive); + gtk_widget_set_sensitive(data->BT_delete, sensitive); + +} + + +/* +** +*/ +static void ui_tag_manage_dialog_selection(GtkTreeSelection *treeselection, gpointer user_data) +{ + ui_tag_manage_dialog_update(GTK_WIDGET(gtk_tree_selection_get_tree_view (treeselection)), NULL); +} + +static void ui_tag_manage_dialog_onRowActivated (GtkTreeView *treeview, + GtkTreePath *path, + GtkTreeViewColumn *col, + gpointer user_data) +{ +GtkTreeModel *model; +GtkTreeIter iter; + + DB( g_print("ui_tag_manage_dialog_onRowActivated()\n") ); + + + 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_tag_manage_dialog_edit(GTK_WIDGET(treeview), NULL); + } +} + + +GtkWidget *ui_tag_manage_dialog (void) +{ +struct ui_tag_manage_dialog_data data; +GtkWidget *dialog, *content, *mainvbox, *box, *bbox, *treeview, *scrollwin, *table, *addreveal; +gint w, h, row; + + dialog = gtk_dialog_new_with_buttons (_("Manage Tags"), + GTK_WINDOW(GLOBALS->mainwindow), + 0, + _("_Close"), GTK_RESPONSE_ACCEPT, + NULL); + + /*dialog = g_object_new (GTK_TYPE_DIALOG, "use-header-bar", TRUE, NULL); + gtk_window_set_title (GTK_WINDOW (dialog), _("Manage Tags")); + gtk_window_set_transient_for (GTK_WINDOW (dialog), GTK_WINDOW(GLOBALS->mainwindow)); + gtk_window_set_modal (GTK_WINDOW (dialog), TRUE); + */ + //gtk_window_set_destroy_with_parent (GTK_WINDOW (dialog), TRUE); + + data.window = dialog; + data.change = 0; + + //gtk_window_set_icon_name(GTK_WINDOW (dialog), ICONNAME_HB_TAG); + + //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 dialog private data + g_object_set_data(G_OBJECT(dialog), "inst_data", (gpointer)&data); + DB( g_print("(ui_tag_manage_dialog) dialog=%p, inst_data=%p\n", dialog, &data) ); + + g_signal_connect (dialog, "destroy", + G_CALLBACK (gtk_widget_destroyed), &dialog); + + //dialog contents + content = gtk_dialog_get_content_area(GTK_DIALOG (dialog)); + mainvbox = gtk_box_new (GTK_ORIENTATION_VERTICAL, SPACING_SMALL); + gtk_box_pack_start (GTK_BOX (content), mainvbox, TRUE, TRUE, 0); + gtk_container_set_border_width (GTK_CONTAINER(mainvbox), SPACING_MEDIUM); + + //our table + table = gtk_grid_new (); + gtk_grid_set_row_spacing (GTK_GRID (table), SPACING_SMALL); + gtk_grid_set_column_spacing (GTK_GRID (table), SPACING_MEDIUM); + gtk_box_pack_start (GTK_BOX (mainvbox), table, TRUE, TRUE, 0); + + row = 0; + bbox = gtk_box_new (GTK_ORIENTATION_HORIZONTAL, SPACING_MEDIUM); + gtk_grid_attach (GTK_GRID (table), bbox, 0, row, 2, 1); + //test headerbar + //content = gtk_dialog_get_header_bar(GTK_DIALOG (dialog)); + + row++; + box = gtk_box_new (GTK_ORIENTATION_VERTICAL, 0); + gtk_grid_attach (GTK_GRID (table), box, 0, row, 2, 1); + + scrollwin = gtk_scrolled_window_new(NULL,NULL); + gtk_container_add(GTK_CONTAINER(box), scrollwin); + 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); + gtk_widget_set_hexpand (scrollwin, TRUE); + gtk_widget_set_vexpand (scrollwin, TRUE); + treeview = ui_tag_listview_new(FALSE); + data.LV_tag = treeview; + gtk_container_add(GTK_CONTAINER(scrollwin), treeview); + + row++; + addreveal = gtk_revealer_new (); + gtk_grid_attach (GTK_GRID (table), addreveal, 0, row, 2, 1); + data.ST_name = gtk_entry_new (); + gtk_entry_set_placeholder_text(GTK_ENTRY(data.ST_name), _("new tag") ); + gtk_widget_set_hexpand (data.ST_name, TRUE); + gtk_container_add(GTK_CONTAINER(addreveal), data.ST_name); + + 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 (table), bbox, 0, row, 2, 1); + + data.BT_add = gtk_toggle_button_new_with_mnemonic(_("_Add")); + gtk_container_add (GTK_CONTAINER (bbox), data.BT_add); + + //todo: useless ? + data.BT_edit = gtk_button_new_with_mnemonic(_("_Edit")); + gtk_container_add (GTK_CONTAINER (bbox), data.BT_edit); + + data.BT_delete = gtk_button_new_with_mnemonic(_("_Delete")); + gtk_container_add (GTK_CONTAINER (bbox), data.BT_delete); + + + //connect all our signals + g_object_bind_property (data.BT_add, "active", addreveal, "reveal-child", G_BINDING_BIDIRECTIONAL); + + g_signal_connect (G_OBJECT (data.ST_name), "activate", G_CALLBACK (ui_tag_manage_dialog_add), NULL); + + g_signal_connect (gtk_tree_view_get_selection(GTK_TREE_VIEW(data.LV_tag)), "changed", G_CALLBACK (ui_tag_manage_dialog_selection), NULL); + g_signal_connect (GTK_TREE_VIEW(data.LV_tag), "row-activated", G_CALLBACK (ui_tag_manage_dialog_onRowActivated), NULL); + + g_signal_connect (G_OBJECT (data.BT_edit), "clicked", G_CALLBACK (ui_tag_manage_dialog_edit), NULL); + g_signal_connect (G_OBJECT (data.BT_delete), "clicked", G_CALLBACK (ui_tag_manage_dialog_delete), NULL); + + //setup, init and show dialog + //tag_fill_usage(); + ui_tag_listview_populate(data.LV_tag, 0); + ui_tag_manage_dialog_update(data.LV_tag, NULL); + + 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 + + gtk_widget_destroy (dialog); + + GLOBALS->changes_count += data.change; + + return NULL; +} +