added table view events (GTK)

Fri, 16 May 2014 16:19:46 +0200

author
Olaf Wintermann <olaf.wintermann@gmail.com>
date
Fri, 16 May 2014 16:19:46 +0200
changeset 42
29b2821d1262
parent 41
394f3b06dba1
child 43
157a21a914ac

added table view events (GTK)

application/main.c file | annotate | diff | comparison | revisions
make/configure_gtk2.sh file | annotate | diff | comparison | revisions
make/configure_gtk2legacy.sh file | annotate | diff | comparison | revisions
ui/gtk/button.c file | annotate | diff | comparison | revisions
ui/gtk/menu.c file | annotate | diff | comparison | revisions
ui/gtk/model.c file | annotate | diff | comparison | revisions
ui/gtk/toolbar.c file | annotate | diff | comparison | revisions
ui/gtk/toolkit.h file | annotate | diff | comparison | revisions
ui/gtk/tree.c file | annotate | diff | comparison | revisions
ui/gtk/tree.h file | annotate | diff | comparison | revisions
ui/ui/tree.h file | annotate | diff | comparison | revisions
--- a/application/main.c	Thu May 15 22:13:25 2014 +0200
+++ b/application/main.c	Fri May 16 16:19:46 2014 +0200
@@ -51,6 +51,20 @@
     return NULL;
 }
 
+void action_activate(UiEvent *event, void *data) {
+    UiListSelection *selection = event->eventdata;
+    printf("activate: %d\n", event->intval);
+}
+
+void action_select(UiEvent *event, void *data) {
+    UiListSelection *selection = event->eventdata;
+    printf("selection[%d]: ", selection->count);
+    for(int i=0;i<selection->count;i++) {
+        printf("%d ", selection->rows[i]);
+    }
+    printf("\n");
+}
+
 int main(int argc, char** argv) { 
     ui_init("app1", argc, argv);
     ui_locales_dir("/opt/app1/locales");
@@ -67,6 +81,8 @@
     
     UiModelInfo *model = ui_model_info(window->ctx, UI_STRING, "Name", UI_STRING, "Email", -1);
     model->getvalue = (ui_model_getvalue_f)person_getvalue;
+    model->activate = action_activate;
+    model->selection = action_select;
     UiList *list = ui_list_new();
     Person *p1 = ui_malloc(window->ctx, sizeof(Person));
     Person *p2 = ui_malloc(window->ctx, sizeof(Person));
--- a/make/configure_gtk2.sh	Thu May 15 22:13:25 2014 +0200
+++ b/make/configure_gtk2.sh	Fri May 16 16:19:46 2014 +0200
@@ -28,7 +28,7 @@
 
 TK_CFLAGS="-DUI_GTK2 `pkg-config --cflags gtk+-2.0 libxml-2.0`"
 
-TK_LDFLAGS=`pkg-config --libs gtk+-2.0 libxml-2.0` -lpthread
+TK_LDFLAGS="`pkg-config --libs gtk+-2.0 libxml-2.0` -lpthread"
 
 cat >> config.mk << __EOF__
 
--- a/make/configure_gtk2legacy.sh	Thu May 15 22:13:25 2014 +0200
+++ b/make/configure_gtk2legacy.sh	Fri May 16 16:19:46 2014 +0200
@@ -29,7 +29,7 @@
 TK_CFLAGS="-DUI_GTK2 -DUI_GTK2LEGACY "
 TK_CFLAGS="$TK_CFLAGS `pkg-config --cflags gtk+-2.0 libxml-2.0`"
 
-TK_LDFLAGS=`pkg-config --libs gtk+-2.0 libxml-2.0` -lpthread
+TK_LDFLAGS="`pkg-config --libs gtk+-2.0 libxml-2.0` -lpthread"
 
 cat >> config.mk << __EOF__
 
--- a/ui/gtk/button.c	Thu May 15 22:13:25 2014 +0200
+++ b/ui/gtk/button.c	Fri May 16 16:19:46 2014 +0200
@@ -43,7 +43,7 @@
                 obj->ctx->mempool,
                 sizeof(UiEventData));
         event->obj = obj;
-        event->user_data = data;
+        event->userdata = data;
         event->callback = f;
         event->value = 0;
 
@@ -73,7 +73,7 @@
     e.document = event->obj->document;
     e.eventdata = NULL;
     e.intval = event->value;
-    event->callback(&e, event->user_data);
+    event->callback(&e, event->userdata);
 }
 
 void ui_button_toggled(GtkToggleToolButton *widget, UiEventData *event) {
@@ -83,5 +83,5 @@
     e.document = event->obj->document;
     e.eventdata = NULL;
     e.intval = gtk_toggle_tool_button_get_active(widget);
-    event->callback(&e, event->user_data);
+    event->callback(&e, event->userdata);
 }
--- a/ui/gtk/menu.c	Thu May 15 22:13:25 2014 +0200
+++ b/ui/gtk/menu.c	Fri May 16 16:19:46 2014 +0200
@@ -245,7 +245,7 @@
     if(i->callback != NULL) {
         UiEventData *event = malloc(sizeof(UiEventData));
         event->obj = obj;
-        event->user_data = i->userdata;
+        event->userdata = i->userdata;
         event->callback = i->callback;
         event->value = 0;
 
@@ -281,7 +281,7 @@
     if(i->callback != NULL) {
         UiEventData *event = malloc(sizeof(UiEventData));
         event->obj = obj;
-        event->user_data = i->userdata;
+        event->userdata = i->userdata;
         event->callback = i->callback;
         event->value = 0;
 
@@ -323,7 +323,7 @@
     if(ci->callback) {
         UiEventData *event = malloc(sizeof(UiEventData));
         event->obj = obj;
-        event->user_data = ci->userdata;
+        event->userdata = ci->userdata;
         event->callback = ci->callback;
         event->value = 0;
 
@@ -413,7 +413,7 @@
             // TODO: use mempool
             UiEventData *event = malloc(sizeof(UiEventData));
             event->obj = list->object;
-            event->user_data = list->userdata;
+            event->userdata = list->userdata;
             event->callback = list->callback;
             event->value = i - 1;
 
@@ -443,7 +443,7 @@
     evt.document = event->obj->document;
     evt.eventdata = NULL;
     evt.intval = event->value;
-    event->callback(&evt, event->user_data);    
+    event->callback(&evt, event->userdata);    
 }
 
 void ui_menu_event_toggled(GtkCheckMenuItem *ci, UiEventData *event) {
@@ -453,7 +453,7 @@
     evt.document = event->obj->document;
     evt.eventdata = NULL;
     evt.intval = gtk_check_menu_item_get_active(ci);
-    event->callback(&evt, event->user_data);    
+    event->callback(&evt, event->userdata);    
 }
 
 int ui_checkitem_get(UiInteger *i) {
--- a/ui/gtk/model.c	Thu May 15 22:13:25 2014 +0200
+++ b/ui/gtk/model.c	Fri May 16 16:19:46 2014 +0200
@@ -237,7 +237,6 @@
     //list->current = iter->user_data3;
     if(model->info->getvalue) {
         void *data = model->info->getvalue(iter->user_data3, column);
-        printf("data[%d]: %s\n", column, data);
         ui_model_set_value(model->info->types[column], data, value);
     } else {
         value->g_type = G_TYPE_INVALID;
--- a/ui/gtk/toolbar.c	Thu May 15 22:13:25 2014 +0200
+++ b/ui/gtk/toolbar.c	Fri May 16 16:19:46 2014 +0200
@@ -201,7 +201,7 @@
                 obj->ctx->mempool,
                 sizeof(UiEventData));
         event->obj = obj;
-        event->user_data = item->userdata;
+        event->userdata = item->userdata;
         event->callback = item->callback;
         
         g_signal_connect(
@@ -230,7 +230,7 @@
                 obj->ctx->mempool,
                 sizeof(UiEventData));
         event->obj = obj;
-        event->user_data = item->userdata;
+        event->userdata = item->userdata;
         event->callback = item->callback;
         
         g_signal_connect(
@@ -264,7 +264,7 @@
                 obj->ctx->mempool,
                 sizeof(UiEventData));
         event->obj = obj;
-        event->user_data = item->userdata;
+        event->userdata = item->userdata;
         event->callback = item->callback;
         
         g_signal_connect(
@@ -290,7 +290,7 @@
                 obj->ctx->mempool,
                 sizeof(UiEventData));
         event->obj = obj;
-        event->user_data = item->userdata;
+        event->userdata = item->userdata;
         event->callback = item->callback;
         
         g_signal_connect(
--- a/ui/gtk/toolkit.h	Thu May 15 22:13:25 2014 +0200
+++ b/ui/gtk/toolkit.h	Fri May 16 16:19:46 2014 +0200
@@ -40,7 +40,7 @@
 typedef struct UiEventData {
     UiObject    *obj;
     ui_callback callback;
-    void        *user_data;
+    void        *userdata;
     int         value;
 } UiEventData;
 
--- a/ui/gtk/tree.c	Thu May 15 22:13:25 2014 +0200
+++ b/ui/gtk/tree.c	Fri May 16 16:19:46 2014 +0200
@@ -78,18 +78,16 @@
     
     // add callback
     if(f) {
-        UiEventData *event = ucx_mempool_malloc(
-                obj->ctx->mempool,
-                sizeof(UiEventData));
+        UiTreeEventData *event = ui_malloc(obj->ctx, sizeof(UiEventData));
         event->obj = obj;
-        event->user_data = udata;
-        event->callback = f;
-        event->value = 0;
+        event->userdata = udata;
+        event->activate = f;
+        event->selection = NULL;
 
         g_signal_connect(
                 view,
                 "row-activated",
-                G_CALLBACK(ui_listview_selected),
+                G_CALLBACK(ui_listview_activate_event),
                 event);
     }
     
@@ -142,7 +140,7 @@
     
     //gtk_tree_view_set_headers_visible(GTK_TREE_VIEW(view), FALSE);
 #ifdef UI_GTK3
-    gtk_tree_view_set_activate_on_single_click(GTK_TREE_VIEW(view), TRUE);
+    //gtk_tree_view_set_activate_on_single_click(GTK_TREE_VIEW(view), TRUE);
 #else
     
 #endif
@@ -162,21 +160,31 @@
             tableview);
     
     // add callback
-    if(modelinfo->callback) {
-        UiEventData *event = ucx_mempool_malloc(
-                obj->ctx->mempool,
-                sizeof(UiEventData));
-        event->obj = obj;
-        event->user_data = modelinfo->userdata;
-        event->callback = modelinfo->callback;
-        event->value = 0;
-
+    UiTreeEventData *event = ui_malloc(obj->ctx, sizeof(UiTreeEventData));
+    event->obj = obj;
+    event->activate = modelinfo->activate;
+    event->selection = modelinfo->selection;
+    event->userdata = modelinfo->userdata;
+    if(modelinfo->activate) {
         g_signal_connect(
                 view,
                 "row-activated",
-                G_CALLBACK(ui_listview_selected),
+                G_CALLBACK(ui_listview_activate_event),
                 event);
     }
+    if(modelinfo->selection) {
+        GtkTreeSelection *selection = gtk_tree_view_get_selection(
+                GTK_TREE_VIEW(view));
+        g_signal_connect(
+                selection,
+                "changed",
+                G_CALLBACK(ui_listview_selection_event),
+                event);
+    }
+    // TODO: destroy callback
+    
+    GtkTreeSelection *selection = gtk_tree_view_get_selection (GTK_TREE_VIEW(view));
+    gtk_tree_selection_set_mode(selection, GTK_SELECTION_MULTIPLE);
     
     // add widget to the current container
     GtkWidget *scroll_area = gtk_scrolled_window_new(NULL, NULL);
@@ -212,36 +220,76 @@
 
 
 void ui_listview_update(UiEvent *event, UiTableView *view) {
-    UiList *list = view->list->list;
     UiListModel *model = ui_list_model_new(view->list, view->modelinfo);
     gtk_tree_view_set_model(GTK_TREE_VIEW(view->widget), GTK_TREE_MODEL(model));   
     
     // TODO: free old model
 }
 
-void ui_listview_selected(
+void ui_listview_activate_event(
         GtkTreeView *treeview,
         GtkTreePath *path,
         GtkTreeViewColumn *column,
-        UiEventData *event)
+        UiTreeEventData *event)
 {
-    int *indices = gtk_tree_path_get_indices(path);
-    int depth = gtk_tree_path_get_depth(path);
-    if(depth == 0) {
-        fprintf(stderr, "UiError: ui_treeview_selected: depth == 0\n");
-        return;
-    }
-    GtkTreeModel *model = gtk_tree_view_get_model(treeview);
-    GtkTreeIter iter;
-    gtk_tree_model_get_iter (model, &iter, path);
-    void *value = NULL;
-    gtk_tree_model_get(model, &iter, 0, &value, -1);
+    UiListSelection *selection = ui_listview_selection(
+            gtk_tree_view_get_selection(treeview),
+            event);
+    
+    UiEvent e;
+    e.obj = event->obj;
+    e.window = event->obj->window;
+    e.document = event->obj->document;
+    e.eventdata = selection;
+    e.intval = selection->count > 0 ? selection->rows[0] : -1;
+    event->activate(&e, event->userdata);
+    
+    free(selection);
+}
+
+void ui_listview_selection_event(
+        GtkTreeSelection *treeselection,
+        UiTreeEventData *event)
+{
+    UiListSelection *selection = ui_listview_selection(treeselection, event);
     
     UiEvent e;
     e.obj = event->obj;
     e.window = event->obj->window;
     e.document = event->obj->document;
-    e.eventdata = value;
-    e.intval = indices[depth-1];
-    event->callback(&e, event->user_data);
+    e.eventdata = selection;
+    e.intval = selection->count > 0 ? selection->rows[0] : -1;
+    event->selection(&e, event->userdata);
+    
+    free(selection);
 }
+
+UiListSelection* ui_listview_selection(
+        GtkTreeSelection *selection,
+        UiTreeEventData *event)
+{
+    GList *rows = gtk_tree_selection_get_selected_rows(selection, NULL);
+    
+    UiListSelection *ls = malloc(sizeof(UiListSelection));
+    ls->count = g_list_length(rows);
+    ls->rows = calloc(ls->count, sizeof(int));
+    GList *r = rows;
+    int i = 0;
+    while(r) {
+        GtkTreePath *path = r->data;
+        ls->rows[i] = ui_tree_path_list_index(path);
+        r = r->next;
+        i++;
+    }
+    return ls;
+}
+
+int ui_tree_path_list_index(GtkTreePath *path) {
+    int depth = gtk_tree_path_get_depth(path);
+    if(depth == 0) {
+        fprintf(stderr, "UiError: treeview selection: depth == 0\n");
+        return -1;
+    }
+    int *indices = gtk_tree_path_get_indices(path);
+    return indices[depth - 1];
+}
--- a/ui/gtk/tree.h	Thu May 15 22:13:25 2014 +0200
+++ b/ui/gtk/tree.h	Fri May 16 16:19:46 2014 +0200
@@ -41,19 +41,33 @@
     GtkWidget           *widget;
     UiListPtr           *list;
     UiModelInfo         *modelinfo;
-    //ui_model_getvalue_f getvalue;
 } UiTableView;
+
+typedef struct UiTreeEventData {
+    UiObject    *obj;
+    ui_callback activate;
+    ui_callback selection;
+    void        *userdata;
+} UiTreeEventData;
     
 void* ui_strmodel_getvalue(void *elm, int column);
 
 UIWIDGET ui_listview_var(UiObject *obj, UiListPtr *list, ui_model_getvalue_f getvalue, ui_callback f, void *udata);
+UIWIDGET ui_table_var(UiObject *obj, UiListPtr *list, UiModelInfo *modelinfo);
 
 void ui_listview_update(UiEvent *event, UiTableView *view);
-void ui_listview_selected(
+void ui_listview_activate_event(
         GtkTreeView *tree_view,
         GtkTreePath *path,
         GtkTreeViewColumn *column,
-        UiEventData *event);
+        UiTreeEventData *event);
+void ui_listview_selection_event(
+        GtkTreeSelection *treeselection,
+        UiTreeEventData *event);
+UiListSelection* ui_listview_selection(
+        GtkTreeSelection *selection,
+        UiTreeEventData *event);
+int ui_tree_path_list_index(GtkTreePath *path);
 
 #ifdef	__cplusplus
 }
--- a/ui/ui/tree.h	Thu May 15 22:13:25 2014 +0200
+++ b/ui/ui/tree.h	Fri May 16 16:19:46 2014 +0200
@@ -35,7 +35,8 @@
 extern "C" {
 #endif
 
-typedef struct UiModelInfo UiModelInfo;
+typedef struct UiModelInfo     UiModelInfo;
+typedef struct UiListSelection UiListSelection;
 
 typedef enum UiModelType UiModelType;
 
@@ -73,14 +74,31 @@
     /*
      * selection callback
      */
-    ui_callback callback;
+    ui_callback activate;
+    
+    /*
+     * cursor callback
+     */
+    ui_callback selection;
     
     /*
-     * userdata for callback
+     * userdata for both callback
      */
     void *userdata;
 };
 
+struct UiListSelection {
+    /*
+     * number of selected items
+     */
+    int count;
+    
+    /*
+     * indices of selected rows
+     */
+    int *rows;
+};
+
 UiModelInfo* ui_model_info(UiContext *ctx, ...);
 void ui_model_info_free(UiContext *ctx, UiModelInfo *mi);
 

mercurial