From 4bff733352f608744e86328deb443d68ce666f7d Mon Sep 17 00:00:00 2001 From: Jon Bergli Heier Date: Wed, 30 Dec 2009 04:30:25 +0100 Subject: Basic adding and assigning of tags implemented. Committing this before it gets out of hand. Only adding new tags is working atm. Created a text input dialog. Added a tag dialog. Other minor changes. --- window_tag.c | 204 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 204 insertions(+) create mode 100644 window_tag.c (limited to 'window_tag.c') diff --git a/window_tag.c b/window_tag.c new file mode 100644 index 0000000..2209572 --- /dev/null +++ b/window_tag.c @@ -0,0 +1,204 @@ +#include "window_tag.h" +#include "tags_ui.h" +#include "db.h" +#include "text_input_dialog.h" + +void on_tagview_cell_toggled(GtkCellRendererToggle *cell_renderer, gchar *path_string, gpointer user_data) { + GtkTreeIter iter; + GtkTreeModel *model; + struct tagdialog_data_t *data; + GValue value = {0}; + gboolean active, inconsistent; + + data = user_data; + + model = gtk_tree_view_get_model(GTK_TREE_VIEW(data->tagview)); + + gtk_tree_model_get_iter_from_string(model, &iter, path_string); + gtk_tree_model_get_value(model, &iter, 0, &value); + active = g_value_get_boolean(&value); + g_value_unset(&value); + + gtk_tree_model_get_value(model, &iter, 1, &value); + inconsistent = g_value_get_boolean(&value); + g_value_unset(&value); + + if(inconsistent) { + gtk_list_store_set(GTK_LIST_STORE(model), &iter, 1, FALSE, -1); + } else { + gtk_list_store_set(GTK_LIST_STORE(model), &iter, 0, !active, -1); + } +} + +/* TODO: Find a better way to do this. */ +inline static gboolean is_tag_inconsistent(struct tag_t *tag, GArray *walltags, gboolean *exists) { + gboolean res; + gint n_y, n_n; + GArray *walltag_single; + gboolean found; + struct tag_t *wall_tag; + + n_y = n_n = 0; + + for(int i = 0; i < walltags->len; i++) { + walltag_single = g_array_index(walltags, GArray*, i); + found = FALSE; + for(int j = 0; j < walltag_single->len; j++) { + wall_tag = &g_array_index(walltag_single, struct tag_t, j); + if(wall_tag->id == tag->id) { + n_y++; + found = TRUE; + break; + } + } + if(!found) + n_n++; + } + if(n_y == 0) + *exists = FALSE; + else + *exists = TRUE; + return (n_n == 0 || n_y == 0 ? FALSE : TRUE); +} + +static void tagview_create_model(GtkTreeView *tagview, gpointer user_data) { + GtkListStore *model; + GArray *array, *walltags, *walltag_single, *wallarray; + GtkTreeIter iter; + struct tag_t *tag; + gboolean inconsistent, exists; + struct tagdialog_data_t *data; + + data = user_data; + wallarray = data->wallarray; + + walltags = g_array_new(FALSE, FALSE, sizeof(GArray*)); + for(int i = 0; i < wallarray->len; i++) { + if(db_get_wall_tags(g_array_index(wallarray, guint64, i), &walltag_single)) { + g_array_append_val(walltags, walltag_single); + } else { + g_error("db_get_wall_tags failed\n"); + return; + } + } + + model = gtk_list_store_new(4, G_TYPE_BOOLEAN, G_TYPE_BOOLEAN, G_TYPE_STRING, G_TYPE_UINT64); + + if(db_get_tags_all(&array)) { + for(int i = 0; i < array->len; i++) { + tag = &g_array_index(array, struct tag_t, i); + gtk_list_store_append(model, &iter); + inconsistent = is_tag_inconsistent(tag, walltags, &exists); + gtk_list_store_set(model, &iter, 0, exists, 1, inconsistent, 2, g_strdup(tag->name), 3, tag->id, -1); + g_free(tag->name); + } + g_array_free(array, TRUE); + } else { + g_warning("Could not fetch tags\n"); + } + + for(int i = 0; i < walltags->len; i++) { + walltag_single = g_array_index(walltags, GArray*, i); + g_array_free(walltag_single, TRUE); + } + g_array_free(walltags, TRUE); + + gtk_tree_view_set_model(tagview, GTK_TREE_MODEL(model)); +} + +static void tagview_init(GtkTreeView *tagview, gpointer user_data) { + GtkTreeViewColumn *col1, *col2; + GtkCellRenderer *renderer; + + col1 = gtk_tree_view_column_new(); + gtk_tree_view_column_set_title(col1, "Select"); + gtk_tree_view_append_column(tagview, col1); + + col2 = gtk_tree_view_column_new(); + gtk_tree_view_column_set_title(col2, "Name"); + gtk_tree_view_append_column(tagview, col2); + + renderer = gtk_cell_renderer_toggle_new(); + gtk_tree_view_column_pack_start(col1, renderer, FALSE); + gtk_tree_view_column_add_attribute(col1, renderer, "active", 0); + gtk_tree_view_column_add_attribute(col1, renderer, "inconsistent", 1); + g_signal_connect(renderer, "toggled", G_CALLBACK(on_tagview_cell_toggled), user_data); + + renderer = gtk_cell_renderer_text_new(); + gtk_tree_view_column_pack_end(col2, renderer, TRUE); + gtk_tree_view_column_add_attribute(col2, renderer, "text", 2); + + tagview_create_model(tagview, user_data); +} + +void on_tags_addbtn_clicked(GtkButton *button, gpointer user_data) { + struct tagdialog_data_t *data; + GtkDialog *dialog; + gchar *s; + + data = user_data; + dialog = text_input_dialog_new(data->dialog, "Enter the name of the new tag:"); + if(gtk_dialog_run(dialog) == GTK_RESPONSE_OK) { + s = text_input_dialog_get_text(GTK_WIDGET(dialog)); + if(db_add_tag(s)) + tagview_create_model(GTK_TREE_VIEW(data->tagview), user_data); + else + g_warning("Failed to add tag \"%s\"\n", s); + g_free(s); + } + gtk_widget_destroy(GTK_WIDGET(dialog)); +} + +void on_tags_rembtn_clicked(GtkButton *button, gpointer user_data) { +} + +void on_tags_selallbtn_clicked(GtkButton *button, gpointer user_data) { +} + +void on_tags_selnonebtn_clicked(GtkButton *button, gpointer user_data) { +} + +void on_tagsdialog_destroy(GtkObject *object, gpointer user_data) { + g_free(user_data); +} + +struct tagdialog_data_t *window_tagview_new(GtkWidget *parent, GArray* array) { + GtkBuilder *builder; + GtkDialog *dialog; + GtkTreeView *tagview; + GtkWidget *content; + GtkButton *selnonebtn; + GtkImage *image; + GError *error = NULL; + struct tagdialog_data_t *data; + + builder = gtk_builder_new(); + if(!gtk_builder_add_from_string(builder, tags_ui_string, -1, &error)) { + g_warning("%s", error->message); + g_error_free(error); + return NULL; + } + + dialog = GTK_DIALOG(gtk_builder_get_object(builder, "tagsdialog")); + gtk_window_set_transient_for(GTK_WINDOW(dialog), GTK_WINDOW(parent)); + gtk_window_set_default_size(GTK_WINDOW(dialog), 300, 300); + + tagview = GTK_TREE_VIEW(gtk_builder_get_object(builder, "tagview")); + + selnonebtn = GTK_BUTTON(gtk_builder_get_object(builder, "selnonebtn")); + gtk_button_set_label(selnonebtn, "Select None"); + + image = GTK_IMAGE(gtk_image_new_from_stock(GTK_STOCK_NEW, GTK_ICON_SIZE_BUTTON)); + gtk_button_set_image(selnonebtn, GTK_WIDGET(image)); + + data = g_malloc(sizeof(struct tagdialog_data_t)); + data->dialog = GTK_WIDGET(dialog); + data->tagview = GTK_WIDGET(tagview); + data->wallarray = array; + + tagview_init(tagview, data); + + gtk_builder_connect_signals(builder, data); + + return data; +} -- cgit v1.2.3