aboutsummaryrefslogtreecommitdiffstats
path: root/widgets/table/e-tree-table-adapter.c
diff options
context:
space:
mode:
Diffstat (limited to 'widgets/table/e-tree-table-adapter.c')
-rw-r--r--widgets/table/e-tree-table-adapter.c1148
1 files changed, 0 insertions, 1148 deletions
diff --git a/widgets/table/e-tree-table-adapter.c b/widgets/table/e-tree-table-adapter.c
deleted file mode 100644
index d828fbb4a8..0000000000
--- a/widgets/table/e-tree-table-adapter.c
+++ /dev/null
@@ -1,1148 +0,0 @@
-/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
-/*
- * e-tree-table-adapter.c
- * Copyright 2000, 2001, Ximian, Inc.
- *
- * Authors:
- * Chris Lahey <clahey@ximian.com>
- * Chris Toshok <toshok@ximian.com>
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License, version 2, as published by the Free Software Foundation.
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License along with this library; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
- * 02111-1307, USA.
- */
-
-#include <config.h>
-#include <stdlib.h>
-#include <string.h>
-#include <gtk/gtksignal.h>
-#include <gnome-xml/tree.h>
-#include <gnome-xml/parser.h>
-#include "gal/util/e-util.h"
-#include "gal/util/e-xml-utils.h"
-#include "e-tree-table-adapter.h"
-
-#define PARENT_TYPE E_TABLE_MODEL_TYPE
-#define d(x)
-
-#define INCREMENT_AMOUNT 100
-
-static ETableModelClass *parent_class;
-
-
-struct ETreeTableAdapterPriv {
- ETreeModel *source;
- int n_map;
- int n_vals_allocated;
- ETreePath *map_table;
- GHashTable *attributes;
-
- guint root_visible : 1;
-
- int last_access;
-
- int tree_model_pre_change_id;
- int tree_model_no_change_id;
- int tree_model_node_changed_id;
- int tree_model_node_data_changed_id;
- int tree_model_node_col_changed_id;
- int tree_model_node_inserted_id;
- int tree_model_node_removed_id;
- int tree_model_node_request_collapse_id;
-};
-
-typedef struct ETreeTableAdapterNode {
- guint expanded : 1;
- guint expandable : 1;
- guint expandable_set : 1;
-
- /* parent/child/sibling pointers */
- guint32 num_visible_children;
-} ETreeTableAdapterNode;
-
-static ETreeTableAdapterNode *
-find_node(ETreeTableAdapter *adapter, ETreePath path)
-{
- ETreeTableAdapterNode *node;
-
- if (path == NULL)
- return NULL;
-
- if (e_tree_model_has_save_id(adapter->priv->source)) {
- char *save_id;
- save_id = e_tree_model_get_save_id(adapter->priv->source, path);
- node = g_hash_table_lookup(adapter->priv->attributes, save_id);
- g_free(save_id);
- } else {
- node = g_hash_table_lookup(adapter->priv->attributes, path);
- }
- if (node && !node->expandable_set) {
- node->expandable = e_tree_model_node_is_expandable(adapter->priv->source, path);
- node->expandable_set = 1;
- }
-
- return node;
-}
-
-static ETreeTableAdapterNode *
-find_or_create_node(ETreeTableAdapter *etta, ETreePath path)
-{
- ETreeTableAdapterNode *node;
-
- node = find_node(etta, path);
-
- if (!node) {
- node = g_new(ETreeTableAdapterNode, 1);
- if (e_tree_model_node_is_root(etta->priv->source, path))
- node->expanded = TRUE;
- else
- node->expanded = e_tree_model_get_expanded_default(etta->priv->source);
- node->expandable = e_tree_model_node_is_expandable(etta->priv->source, path);
- node->expandable_set = 1;
- node->num_visible_children = 0;
-
- if (e_tree_model_has_save_id(etta->priv->source)) {
- char *save_id;
- save_id = e_tree_model_get_save_id(etta->priv->source, path);
- g_hash_table_insert(etta->priv->attributes, save_id, node);
- } else {
- g_hash_table_insert(etta->priv->attributes, path, node);
- }
- }
-
- return node;
-}
-
-static void
-add_expanded_node(ETreeTableAdapter *etta, char *save_id, gboolean expanded)
-{
- ETreeTableAdapterNode *node;
-
- node = g_hash_table_lookup(etta->priv->attributes, save_id);
-
- if (node) {
- node->expandable_set = 0;
- node->expanded = expanded;
- return;
- }
-
- node = g_new(ETreeTableAdapterNode, 1);
-
- node->expanded = expanded;
- node->expandable = 0;
- node->expandable_set = 0;
- node->num_visible_children = 0;
-
- g_hash_table_insert(etta->priv->attributes, save_id, node);
-}
-
-static void
-etta_expand_to(ETreeTableAdapter *etta, int size)
-{
- if (size > etta->priv->n_vals_allocated) {
- etta->priv->n_vals_allocated = MAX(etta->priv->n_vals_allocated + INCREMENT_AMOUNT, size);
- etta->priv->map_table = g_renew (ETreePath, etta->priv->map_table, etta->priv->n_vals_allocated);
- }
-
-}
-
-static void
-etta_update_parent_child_counts(ETreeTableAdapter *etta, ETreePath path, int change)
-{
- for (path = e_tree_model_node_get_parent(etta->priv->source, path);
- path;
- path = e_tree_model_node_get_parent(etta->priv->source, path)) {
- ETreeTableAdapterNode *node = find_or_create_node(etta, path);
- node->num_visible_children += change;
- }
- etta->priv->n_map += change;
-}
-
-static int
-find_next_node_maybe_deleted(ETreeTableAdapter *adapter, int row)
-{
- ETreePath path = adapter->priv->map_table[row];
- if (path) {
- ETreeTableAdapterNode *current = find_node (adapter, path);
-
- row += (current ? current->num_visible_children : 0) + 1;
- if (row >= adapter->priv->n_map)
- return -1;
- return row;
- } else
- return -1;
-}
-
-static int
-find_first_child_node_maybe_deleted(ETreeTableAdapter *adapter, int row)
-{
- if (row != -1) {
- ETreePath path = adapter->priv->map_table[row];
- if (e_tree_table_adapter_node_is_expanded (adapter, path)) {
- row ++;
- if (row >= adapter->priv->n_map)
- return -1;
- return row;
- } else
- return -1;
- } else
- return 0;
-}
-
-static int
-find_next_node(ETreeTableAdapter *adapter, int row)
-{
- ETreePath path = adapter->priv->map_table[row];
- if (path) {
- ETreePath next_sibling = e_tree_model_node_get_next(adapter->priv->source, path);
- ETreeTableAdapterNode *current = find_node (adapter, path);
- if (next_sibling) {
- row += (current ? current->num_visible_children : 0) + 1;
- if (row >= adapter->priv->n_map)
- return -1;
- return row;
- } else
- return -1;
- } else
- return -1;
-}
-
-static int
-find_first_child_node(ETreeTableAdapter *adapter, int row)
-{
- if (row != -1) {
- ETreePath path = adapter->priv->map_table[row];
- ETreePath first_child = e_tree_model_node_get_first_child(adapter->priv->source, path);
- if (first_child && e_tree_table_adapter_node_is_expanded (adapter, path)) {
- row ++;
- if (row >= adapter->priv->n_map)
- return -1;
- return row;
- } else
- return -1;
- } else
- return 0;
-}
-
-static int
-find_child_row_num_maybe_deleted(ETreeTableAdapter *etta, int row, ETreePath path)
-{
- row = find_first_child_node_maybe_deleted(etta, row);
-
- while (row != -1 && path != etta->priv->map_table[row]) {
- row = find_next_node_maybe_deleted(etta, row);
- }
-
- return row;
-}
-
-static int
-find_row_num(ETreeTableAdapter *etta, ETreePath path)
-{
- int depth;
- ETreePath *sequence;
- int i;
- int row;
-
- if (etta->priv->map_table == NULL)
- return -1;
- if (etta->priv->n_map == 0)
- return -1;
-
- if (path == NULL)
- return -1;
-
- if (etta->priv->last_access != -1) {
- int end = MIN(etta->priv->n_map, etta->priv->last_access + 10);
- int start = MAX(0, etta->priv->last_access - 10);
- int initial = MAX (MIN (etta->priv->last_access, end), start);
- for (i = initial; i < end; i++) {
- if(etta->priv->map_table[i] == path) {
- d(g_print("Found last access %d at row %d. (find_row_num)\n", etta->priv->last_access, i));
- return i;
- }
- }
- for (i = initial - 1; i >= start; i--) {
- if(etta->priv->map_table[i] == path) {
- d(g_print("Found last access %d at row %d. (find_row_num)\n", etta->priv->last_access, i));
- return i;
- }
- }
- }
-
-
- depth = e_tree_model_node_depth(etta->priv->source, path);
-
- sequence = g_new(ETreePath, depth + 1);
-
- sequence[0] = path;
-
- for (i = 0; i < depth; i++) {
- sequence[i + 1] = e_tree_model_node_get_parent(etta->priv->source, sequence[i]);
-
- if (!e_tree_table_adapter_node_is_expanded (etta, sequence[i + 1])) {
- g_free(sequence);
- return -1;
- }
- }
-
- row = 0;
-
- for (i = depth; i >= 0; i --) {
- while (row != -1 && sequence[i] != etta->priv->map_table[row]) {
- row = find_next_node(etta, row);
- }
- if (row == -1)
- break;
- if (i == 0)
- break;
- row = find_first_child_node(etta, row);
- }
- g_free (sequence);
-
- d(g_print("Didn't find last access %d. Setting to %d. (find_row_num)\n", etta->priv->last_access, row));
- etta->priv->last_access = row;
- return row;
-}
-
-static int
-array_size_from_path(ETreeTableAdapter *etta, ETreePath path)
-{
- int size = 1;
-
- if (e_tree_table_adapter_node_is_expanded (etta, path)) {
- ETreePath children;
-
- for (children = e_tree_model_node_get_first_child(etta->priv->source, path);
- children;
- children = e_tree_model_node_get_next(etta->priv->source, children)) {
- size += array_size_from_path(etta, children);
- }
- }
-
- return size;
-}
-
-static int
-fill_array_from_path(ETreeTableAdapter *etta, ETreePath *array, ETreePath path)
-{
- ETreeTableAdapterNode *node = NULL;
- int index = 0;
-
- array[index] = path;
-
- index ++;
-
- node = find_node(etta, path);
-
- if (e_tree_table_adapter_node_is_expanded (etta, path)) {
- ETreePath children;
-
- if (!node)
- node = find_or_create_node(etta, path);
-
- for (children = e_tree_model_node_get_first_child(etta->priv->source, path);
- children;
- children = e_tree_model_node_get_next(etta->priv->source, children)) {
- index += fill_array_from_path(etta, array + index, children);
- }
- }
-
- if (node)
- node->num_visible_children = index - 1;
-
- return index;
-}
-
-static void
-free_string (gpointer key, gpointer value, gpointer data)
-{
- g_free(key);
-}
-
-static void
-etta_destroy (GtkObject *object)
-{
- ETreeTableAdapter *etta = E_TREE_TABLE_ADAPTER (object);
-
- if (etta->priv->source && e_tree_model_has_save_id(etta->priv->source)) {
- g_hash_table_foreach(etta->priv->attributes, free_string, NULL);
- }
- g_hash_table_destroy (etta->priv->attributes);
-
- if (etta->priv->source) {
- gtk_signal_disconnect (GTK_OBJECT (etta->priv->source),
- etta->priv->tree_model_pre_change_id);
- gtk_signal_disconnect (GTK_OBJECT (etta->priv->source),
- etta->priv->tree_model_no_change_id);
- gtk_signal_disconnect (GTK_OBJECT (etta->priv->source),
- etta->priv->tree_model_node_changed_id);
- gtk_signal_disconnect (GTK_OBJECT (etta->priv->source),
- etta->priv->tree_model_node_data_changed_id);
- gtk_signal_disconnect (GTK_OBJECT (etta->priv->source),
- etta->priv->tree_model_node_col_changed_id);
- gtk_signal_disconnect (GTK_OBJECT (etta->priv->source),
- etta->priv->tree_model_node_inserted_id);
- gtk_signal_disconnect (GTK_OBJECT (etta->priv->source),
- etta->priv->tree_model_node_removed_id);
- gtk_signal_disconnect (GTK_OBJECT (etta->priv->source),
- etta->priv->tree_model_node_request_collapse_id);
-
- gtk_object_unref (GTK_OBJECT (etta->priv->source));
- etta->priv->source = NULL;
-
- etta->priv->tree_model_pre_change_id = 0;
- etta->priv->tree_model_no_change_id = 0;
- etta->priv->tree_model_node_changed_id = 0;
- etta->priv->tree_model_node_data_changed_id = 0;
- etta->priv->tree_model_node_col_changed_id = 0;
- etta->priv->tree_model_node_inserted_id = 0;
- etta->priv->tree_model_node_removed_id = 0;
- etta->priv->tree_model_node_request_collapse_id = 0;
- }
-
- g_free (etta->priv->map_table);
-
- g_free (etta->priv);
-
- GTK_OBJECT_CLASS (parent_class)->destroy (object);
-}
-
-static int
-etta_column_count (ETableModel *etm)
-{
- ETreeTableAdapter *etta = (ETreeTableAdapter *)etm;
-
- return e_tree_model_column_count (etta->priv->source);
-}
-
-static gboolean
-etta_has_save_id (ETableModel *etm)
-{
- ETreeTableAdapter *etta = (ETreeTableAdapter *)etm;
-
- return e_tree_model_has_save_id (etta->priv->source);
-}
-
-static gchar *
-etta_get_save_id (ETableModel *etm, int row)
-{
- ETreeTableAdapter *etta = (ETreeTableAdapter *)etm;
-
- if (etta->priv->root_visible)
- return e_tree_model_get_save_id (etta->priv->source, etta->priv->map_table [row]);
- else
- return e_tree_model_get_save_id (etta->priv->source, etta->priv->map_table [row + 1]);
-}
-
-static gboolean
-etta_has_change_pending (ETableModel *etm)
-{
- ETreeTableAdapter *etta = (ETreeTableAdapter *)etm;
-
- return e_tree_model_has_change_pending (etta->priv->source);
-}
-
-
-static int
-etta_row_count (ETableModel *etm)
-{
- ETreeTableAdapter *etta = (ETreeTableAdapter *)etm;
-
- if (etta->priv->root_visible)
- return etta->priv->n_map;
- else {
- if (etta->priv->n_map > 0)
- return etta->priv->n_map - 1;
- else
- return 0;
- }
-}
-
-static void *
-etta_value_at (ETableModel *etm, int col, int row)
-{
- ETreeTableAdapter *etta = (ETreeTableAdapter *)etm;
-
-#if 0
- etta->priv->last_access = row;
- d(g_print("g) Setting last_access to %d\n", row));
-#endif
-
- switch (col) {
- case -1:
- if (etta->priv->root_visible)
- return etta->priv->map_table [row];
- else
- return etta->priv->map_table [row + 1];
- case -2:
- return etta->priv->source;
- case -3:
- return etta;
- default:
- if (etta->priv->root_visible)
- return e_tree_model_value_at (etta->priv->source, etta->priv->map_table [row], col);
- else
- return e_tree_model_value_at (etta->priv->source, etta->priv->map_table [row + 1], col);
- }
-}
-
-static void
-etta_set_value_at (ETableModel *etm, int col, int row, const void *val)
-{
- ETreeTableAdapter *etta = (ETreeTableAdapter *)etm;
-
- etta->priv->last_access = row;
- d(g_print("h) Setting last_access to %d\n", row));
- if (etta->priv->root_visible)
- e_tree_model_set_value_at (etta->priv->source, etta->priv->map_table [row], col, val);
- else
- e_tree_model_set_value_at (etta->priv->source, etta->priv->map_table [row + 1], col, val);
-}
-
-static gboolean
-etta_is_cell_editable (ETableModel *etm, int col, int row)
-{
- ETreeTableAdapter *etta = (ETreeTableAdapter *)etm;
-
- if (etta->priv->root_visible)
- return e_tree_model_node_is_editable (etta->priv->source, etta->priv->map_table [row], col);
- else
- return e_tree_model_node_is_editable (etta->priv->source, etta->priv->map_table [row + 1], col);
-}
-
-static void
-etta_append_row (ETableModel *etm, ETableModel *source, int row)
-{
-#if 0
- ETreeTableAdapter *etta = (ETreeTableAdapter *)etm;
- e_table_model_append_row (etta->priv->source, source, row);
-#endif
-}
-
-static void *
-etta_duplicate_value (ETableModel *etm, int col, const void *value)
-{
- ETreeTableAdapter *etta = (ETreeTableAdapter *)etm;
-
- return e_tree_model_duplicate_value (etta->priv->source, col, value);
-}
-
-static void
-etta_free_value (ETableModel *etm, int col, void *value)
-{
- ETreeTableAdapter *etta = (ETreeTableAdapter *)etm;
-
- e_tree_model_free_value (etta->priv->source, col, value);
-}
-
-static void *
-etta_initialize_value (ETableModel *etm, int col)
-{
- ETreeTableAdapter *etta = (ETreeTableAdapter *)etm;
-
- return e_tree_model_initialize_value (etta->priv->source, col);
-}
-
-static gboolean
-etta_value_is_empty (ETableModel *etm, int col, const void *value)
-{
- ETreeTableAdapter *etta = (ETreeTableAdapter *)etm;
-
- return e_tree_model_value_is_empty (etta->priv->source, col, value);
-}
-
-static char *
-etta_value_to_string (ETableModel *etm, int col, const void *value)
-{
- ETreeTableAdapter *etta = (ETreeTableAdapter *)etm;
-
- return e_tree_model_value_to_string (etta->priv->source, col, value);
-}
-
-static void
-etta_class_init (ETreeTableAdapterClass *klass)
-{
- ETableModelClass *table_class = (ETableModelClass *) klass;
- GtkObjectClass *object_class = (GtkObjectClass *) klass;
-
- parent_class = gtk_type_class (PARENT_TYPE);
-
- object_class->destroy = etta_destroy;
-
- table_class->column_count = etta_column_count;
- table_class->row_count = etta_row_count;
- table_class->append_row = etta_append_row;
-
- table_class->value_at = etta_value_at;
- table_class->set_value_at = etta_set_value_at;
- table_class->is_cell_editable = etta_is_cell_editable;
-
- table_class->has_save_id = etta_has_save_id;
- table_class->get_save_id = etta_get_save_id;
-
- table_class->has_change_pending = etta_has_change_pending;
- table_class->duplicate_value = etta_duplicate_value;
- table_class->free_value = etta_free_value;
- table_class->initialize_value = etta_initialize_value;
- table_class->value_is_empty = etta_value_is_empty;
- table_class->value_to_string = etta_value_to_string;
-}
-
-static void
-etta_init (ETreeTableAdapter *etta)
-{
- etta->priv = g_new(ETreeTableAdapterPriv, 1);
-
- etta->priv->source = NULL;
-
- etta->priv->n_map = 0;
- etta->priv->n_vals_allocated = 0;
- etta->priv->map_table = NULL;
- etta->priv->attributes = NULL;
-
- etta->priv->root_visible = TRUE;
-
- etta->priv->last_access = 0;
-
- etta->priv->tree_model_pre_change_id = 0;
- etta->priv->tree_model_no_change_id = 0;
- etta->priv->tree_model_node_changed_id = 0;
- etta->priv->tree_model_node_data_changed_id = 0;
- etta->priv->tree_model_node_col_changed_id = 0;
- etta->priv->tree_model_node_inserted_id = 0;
- etta->priv->tree_model_node_removed_id = 0;
- etta->priv->tree_model_node_request_collapse_id = 0;
-}
-
-E_MAKE_TYPE(e_tree_table_adapter, "ETreeTableAdapter", ETreeTableAdapter, etta_class_init, etta_init, PARENT_TYPE)
-
-static void
-etta_proxy_pre_change (ETreeModel *etm, ETreeTableAdapter *etta)
-{
- e_table_model_pre_change(E_TABLE_MODEL(etta));
-}
-
-static void
-etta_proxy_no_change (ETreeModel *etm, ETreeTableAdapter *etta)
-{
- e_table_model_no_change(E_TABLE_MODEL(etta));
-}
-
-static void
-etta_proxy_node_changed (ETreeModel *etm, ETreePath path, ETreeTableAdapter *etta)
-{
- if (e_tree_model_node_is_root(etm, path)) {
- int size;
-
- size = array_size_from_path(etta, path);
- etta_expand_to(etta, size);
- etta->priv->n_map = size;
- fill_array_from_path(etta, etta->priv->map_table, path);
- } else {
- int row = find_row_num(etta, path);
- int size;
- int old_size;
- ETreeTableAdapterNode *node;
-
- if (row == -1)
- return;
-
- size = array_size_from_path(etta, path);
-
- node = find_node(etta, path);
- if (node)
- old_size = node->num_visible_children + 1;
- else
- old_size = 1;
-
- etta_expand_to(etta, etta->priv->n_map + size - old_size);
-
- memmove(etta->priv->map_table + row + size,
- etta->priv->map_table + row + old_size,
- (etta->priv->n_map - row - old_size) * sizeof (ETreePath));
- fill_array_from_path(etta, etta->priv->map_table + row, path);
- etta_update_parent_child_counts(etta, path, size - old_size);
- }
-
- e_table_model_changed(E_TABLE_MODEL(etta));
-}
-
-static void
-etta_proxy_node_data_changed (ETreeModel *etm, ETreePath path, ETreeTableAdapter *etta)
-{
- int row = find_row_num(etta, path);
- if (row != -1) {
- if (etta->priv->root_visible)
- e_table_model_row_changed(E_TABLE_MODEL(etta), row);
- else if (row != 0)
- e_table_model_row_changed(E_TABLE_MODEL(etta), row - 1);
- else
- e_table_model_no_change(E_TABLE_MODEL(etta));
- } else
- e_table_model_no_change(E_TABLE_MODEL(etta));
-}
-
-static void
-etta_proxy_node_col_changed (ETreeModel *etm, ETreePath path, int col, ETreeTableAdapter *etta)
-{
- int row = find_row_num(etta, path);
- if (row != -1) {
- if (etta->priv->root_visible)
- e_table_model_cell_changed(E_TABLE_MODEL(etta), col, row);
- else if (row != 0)
- e_table_model_cell_changed(E_TABLE_MODEL(etta), col, row - 1);
- else
- e_table_model_no_change(E_TABLE_MODEL(etta));
- } else
- e_table_model_no_change(E_TABLE_MODEL(etta));
-}
-
-static void
-etta_proxy_node_inserted (ETreeModel *etm, ETreePath parent, ETreePath child, ETreeTableAdapter *etta)
-{
- int row;
-
- if (e_tree_model_node_is_root(etm, child)) {
- row = 0;
- } else {
- ETreePath children;
- int parent_row;
- ETreeTableAdapterNode *parent_node;
-
- parent_row = find_row_num(etta, parent);
- if (parent_row == -1) {
- e_table_model_no_change(E_TABLE_MODEL(etta));
- return;
- }
-
- parent_node = find_or_create_node(etta, parent);
- if (parent_node->expandable != e_tree_model_node_is_expandable(etta->priv->source, parent)) {
- e_table_model_pre_change(E_TABLE_MODEL(etta));
- parent_node->expandable = e_tree_model_node_is_expandable(etta->priv->source, parent);
- parent_node->expandable_set = 1;
- if (etta->priv->root_visible)
- e_table_model_row_changed(E_TABLE_MODEL(etta), parent_row);
- else if (parent_row != 0)
- e_table_model_row_changed(E_TABLE_MODEL(etta), parent_row - 1);
- else
- e_table_model_no_change(E_TABLE_MODEL(etta));
- }
-
- if (!e_tree_table_adapter_node_is_expanded (etta, parent)) {
- e_table_model_no_change(E_TABLE_MODEL(etta));
- return;
- }
-
- row = find_first_child_node(etta, parent_row);
- children = e_tree_model_node_get_first_child(etta->priv->source, parent);
-
- while (row != -1 &&
- row <= parent_row + parent_node->num_visible_children &&
- children != NULL &&
- children == etta->priv->map_table[row]) {
- children = e_tree_model_node_get_next(etta->priv->source, children);
- row = find_next_node(etta, row);
- }
- }
-
- if (row != -1) {
- int size;
-
- size = array_size_from_path(etta, child);
-
- etta_expand_to(etta, etta->priv->n_map + size);
-
- memmove(etta->priv->map_table + row + size,
- etta->priv->map_table + row,
- (etta->priv->n_map - row) * sizeof (ETreePath));
-
- fill_array_from_path(etta, etta->priv->map_table + row, child);
- etta_update_parent_child_counts(etta, child, size);
-
- if (etta->priv->root_visible)
- e_table_model_rows_inserted(E_TABLE_MODEL(etta), row, size);
- else if (row != 0)
- e_table_model_rows_inserted(E_TABLE_MODEL(etta), row - 1, size);
- else
- e_table_model_rows_inserted(E_TABLE_MODEL(etta), 0, size - 1);
- } else
- e_table_model_no_change(E_TABLE_MODEL(etta));
-}
-
-static void
-etta_proxy_node_removed (ETreeModel *etm, ETreePath parent, ETreePath child, int old_position, ETreeTableAdapter *etta)
-{
- int parent_row = find_row_num(etta, parent);
- int row = find_child_row_num_maybe_deleted(etta, parent_row, child);
- ETreeTableAdapterNode *parent_node = find_node(etta, parent);
- if (parent_row != -1 && parent_node) {
- if (parent_node->expandable != e_tree_model_node_is_expandable(etta->priv->source, parent)) {
- e_table_model_pre_change(E_TABLE_MODEL(etta));
- parent_node->expandable = e_tree_model_node_is_expandable(etta->priv->source, parent);
- if (etta->priv->root_visible)
- e_table_model_row_changed(E_TABLE_MODEL(etta), parent_row);
- else if (parent_row != 0)
- e_table_model_row_changed(E_TABLE_MODEL(etta), parent_row - 1);
- else
- e_table_model_no_change(E_TABLE_MODEL(etta));
- }
- }
-
- if (row != -1) {
- ETreeTableAdapterNode *node = find_node(etta, child);
- int to_remove = (node ? node->num_visible_children : 0) + 1;
-
- memmove(etta->priv->map_table + row,
- etta->priv->map_table + row + to_remove,
- (etta->priv->n_map - row - to_remove) * sizeof (ETreePath));
-
- if (parent_node)
- parent_node->num_visible_children -= to_remove;
- if (parent)
- etta_update_parent_child_counts(etta, parent, - to_remove);
-
- if (etta->priv->root_visible)
- e_table_model_rows_deleted(E_TABLE_MODEL(etta), row, to_remove);
- else if (row != 0)
- e_table_model_rows_deleted(E_TABLE_MODEL(etta), row - 1, to_remove);
- else
- e_table_model_rows_deleted(E_TABLE_MODEL(etta), 0, to_remove - 1);
- } else
- e_table_model_no_change(E_TABLE_MODEL(etta));
-}
-
-static void
-etta_proxy_node_request_collapse (ETreeModel *etm, ETreePath node, ETreeTableAdapter *etta)
-{
- e_tree_table_adapter_node_set_expanded(etta, node, FALSE);
-}
-
-ETableModel *
-e_tree_table_adapter_construct (ETreeTableAdapter *etta, ETreeModel *source)
-{
- ETreePath root;
-
- etta->priv->source = source;
- gtk_object_ref (GTK_OBJECT (source));
-
- if (e_tree_model_has_save_id(source))
- etta->priv->attributes = g_hash_table_new(g_str_hash, g_str_equal);
- else
- etta->priv->attributes = g_hash_table_new(NULL, NULL);
-
- root = e_tree_model_get_root (source);
-
- if (root) {
- etta->priv->n_map = array_size_from_path(etta, root);
- etta->priv->n_vals_allocated = etta->priv->n_map;
- etta->priv->map_table = g_new(ETreePath, etta->priv->n_map);
- fill_array_from_path(etta, etta->priv->map_table, root);
- }
-
- etta->priv->tree_model_pre_change_id = gtk_signal_connect (GTK_OBJECT (source), "pre_change",
- GTK_SIGNAL_FUNC (etta_proxy_pre_change), etta);
- etta->priv->tree_model_no_change_id = gtk_signal_connect (GTK_OBJECT (source), "no_change",
- GTK_SIGNAL_FUNC (etta_proxy_no_change), etta);
- etta->priv->tree_model_node_changed_id = gtk_signal_connect (GTK_OBJECT (source), "node_changed",
- GTK_SIGNAL_FUNC (etta_proxy_node_changed), etta);
- etta->priv->tree_model_node_data_changed_id = gtk_signal_connect (GTK_OBJECT (source), "node_data_changed",
- GTK_SIGNAL_FUNC (etta_proxy_node_data_changed), etta);
- etta->priv->tree_model_node_col_changed_id = gtk_signal_connect (GTK_OBJECT (source), "node_col_changed",
- GTK_SIGNAL_FUNC (etta_proxy_node_col_changed), etta);
- etta->priv->tree_model_node_inserted_id = gtk_signal_connect (GTK_OBJECT (source), "node_inserted",
- GTK_SIGNAL_FUNC (etta_proxy_node_inserted), etta);
- etta->priv->tree_model_node_removed_id = gtk_signal_connect (GTK_OBJECT (source), "node_removed",
- GTK_SIGNAL_FUNC (etta_proxy_node_removed), etta);
- etta->priv->tree_model_node_request_collapse_id = gtk_signal_connect (GTK_OBJECT (source), "node_request_collapse",
- GTK_SIGNAL_FUNC (etta_proxy_node_request_collapse), etta);
-
- return E_TABLE_MODEL (etta);
-}
-
-ETableModel *
-e_tree_table_adapter_new (ETreeModel *source)
-{
- ETreeTableAdapter *etta = gtk_type_new (E_TREE_TABLE_ADAPTER_TYPE);
-
- e_tree_table_adapter_construct (etta, source);
-
- return (ETableModel *) etta;
-}
-
-typedef struct {
- xmlNode *root;
- ETreeModel *tree;
-} TreeAndRoot;
-
-static void
-save_expanded_state_func (gpointer keyp, gpointer value, gpointer data)
-{
- gchar *key = keyp;
- ETreeTableAdapterNode *node = value;
- TreeAndRoot *tar = data;
- xmlNode *root = tar->root;
- ETreeModel *etm = tar->tree;
- xmlNode *xmlnode;
-
- if (node->expanded != e_tree_model_get_expanded_default(etm)) {
- xmlnode = xmlNewChild (root, NULL, "node", NULL);
- e_xml_set_string_prop_by_name(xmlnode, "id", key);
- }
-}
-
-void
-e_tree_table_adapter_save_expanded_state (ETreeTableAdapter *etta, const char *filename)
-{
- xmlDoc *doc;
- xmlNode *root;
- ETreeTableAdapterPriv *priv;
- TreeAndRoot tar;
-
- g_return_if_fail(etta != NULL);
-
- priv = etta->priv;
-
- doc = xmlNewDoc ((xmlChar*) "1.0");
- root = xmlNewDocNode (doc, NULL,
- (xmlChar *) "expanded_state",
- NULL);
- xmlDocSetRootElement (doc, root);
-
- e_xml_set_integer_prop_by_name (root, "vers", 2);
- e_xml_set_bool_prop_by_name (root, "default", e_tree_model_get_expanded_default (priv->source));
-
- tar.root = root;
- tar.tree = etta->priv->source;
-
- g_hash_table_foreach (priv->attributes,
- save_expanded_state_func,
- &tar);
-
- xmlSaveFile (filename, doc);
-
- xmlFreeDoc (doc);
-}
-
-void
-e_tree_table_adapter_load_expanded_state (ETreeTableAdapter *etta, const char *filename)
-{
- ETreeTableAdapterPriv *priv;
- xmlDoc *doc;
- xmlNode *root;
- xmlNode *child;
- int vers;
- gboolean model_default, saved_default;
-
- g_return_if_fail(etta != NULL);
-
- priv = etta->priv;
-
- doc = xmlParseFile (filename);
- if (!doc)
- return;
-
- root = xmlDocGetRootElement (doc);
- if (root == NULL || strcmp (root->name, "expanded_state")) {
- xmlFreeDoc (doc);
- return;
- }
-
- vers = e_xml_get_integer_prop_by_name_with_default (root, "vers", 0);
- if (vers > 2) {
- xmlFreeDoc (doc);
- return;
- }
- model_default = e_tree_model_get_expanded_default (priv->source);
- saved_default = e_xml_get_bool_prop_by_name_with_default (root, "default", !model_default);
- if (saved_default != model_default) {
- xmlFreeDoc (doc);
- return;
- }
-
- for (child = root->xmlChildrenNode; child; child = child->next) {
- char *id;
-
- if (strcmp (child->name, "node")) {
- d(g_warning ("unknown node '%s' in %s", child->name, filename));
- continue;
- }
-
- id = e_xml_get_string_prop_by_name_with_default (child, "id", "");
-
- if (!strcmp(id, "")) {
- g_free(id);
- return;
- }
-
- add_expanded_node(etta, id, !model_default);
- }
-
- xmlFreeDoc (doc);
-}
-
-void e_tree_table_adapter_root_node_set_visible (ETreeTableAdapter *etta, gboolean visible)
-{
- if (etta->priv->root_visible == visible)
- return;
-
- e_table_model_pre_change (E_TABLE_MODEL(etta));
-
- etta->priv->root_visible = visible;
- if (!visible) {
- ETreePath root = e_tree_model_get_root(etta->priv->source);
- if (root)
- e_tree_table_adapter_node_set_expanded(etta, root, TRUE);
- }
- e_table_model_changed(E_TABLE_MODEL(etta));
-}
-
-void e_tree_table_adapter_node_set_expanded (ETreeTableAdapter *etta, ETreePath path, gboolean expanded)
-{
- ETreeTableAdapterNode *node;
- int row;
-
- if (!expanded && e_tree_model_node_is_root (etta->priv->source, path) && !etta->priv->root_visible)
- return;
-
- node = find_or_create_node(etta, path);
-
- if (expanded == node->expanded)
- return;
-
- node->expanded = expanded;
-
- row = find_row_num(etta, path);
- if (row != -1) {
- e_table_model_pre_change (E_TABLE_MODEL(etta));
-
- if (etta->priv->root_visible) {
- e_table_model_pre_change (E_TABLE_MODEL(etta));
- e_table_model_row_changed(E_TABLE_MODEL(etta), row);
- } else if (row != 0) {
- e_table_model_pre_change (E_TABLE_MODEL(etta));
- e_table_model_row_changed(E_TABLE_MODEL(etta), row - 1);
- }
-
- if (expanded) {
- int num_children = array_size_from_path(etta, path) - 1;
- etta_expand_to(etta, etta->priv->n_map + num_children);
- memmove(etta->priv->map_table + row + 1 + num_children,
- etta->priv->map_table + row + 1,
- (etta->priv->n_map - row - 1) * sizeof (ETreePath));
- fill_array_from_path(etta, etta->priv->map_table + row, path);
- etta_update_parent_child_counts(etta, path, num_children);
- if (num_children != 0) {
- if (etta->priv->root_visible)
- e_table_model_rows_inserted(E_TABLE_MODEL(etta), row + 1, num_children);
- else
- e_table_model_rows_inserted(E_TABLE_MODEL(etta), row, num_children);
- } else
- e_table_model_no_change(E_TABLE_MODEL(etta));
- } else {
- int num_children = node->num_visible_children;
- g_assert (etta->priv->n_map >= row + 1 + num_children);
- memmove(etta->priv->map_table + row + 1,
- etta->priv->map_table + row + 1 + num_children,
- (etta->priv->n_map - row - 1 - num_children) * sizeof (ETreePath));
- node->num_visible_children = 0;
- etta_update_parent_child_counts(etta, path, - num_children);
- if (num_children != 0) {
- if (etta->priv->root_visible)
- e_table_model_rows_deleted(E_TABLE_MODEL(etta), row + 1, num_children);
- else
- e_table_model_rows_deleted(E_TABLE_MODEL(etta), row, num_children);
- } else
- e_table_model_no_change(E_TABLE_MODEL(etta));
- }
- }
-}
-
-void e_tree_table_adapter_node_set_expanded_recurse (ETreeTableAdapter *etta, ETreePath path, gboolean expanded)
-{
- ETreePath children;
-
- e_tree_table_adapter_node_set_expanded(etta, path, expanded);
-
- for (children = e_tree_model_node_get_first_child(etta->priv->source, path);
- children;
- children = e_tree_model_node_get_next(etta->priv->source, children)) {
- e_tree_table_adapter_node_set_expanded_recurse(etta, children, expanded);
- }
-}
-
-ETreePath e_tree_table_adapter_node_at_row (ETreeTableAdapter *etta, int row)
-{
- if (row < 0)
- return NULL;
- if (etta->priv->root_visible) {
- if (row < etta->priv->n_map)
- return etta->priv->map_table[row];
- } else {
- if (row + 1 < etta->priv->n_map)
- return etta->priv->map_table[row + 1];
- }
- return NULL;
-}
-
-int e_tree_table_adapter_row_of_node (ETreeTableAdapter *etta, ETreePath path)
-{
- if (etta->priv->root_visible)
- return find_row_num(etta, path);
- else {
- int row_num = find_row_num (etta, path);
- if (row_num != -1)
- return row_num - 1;
- else
- return row_num;
- }
-}
-
-gboolean e_tree_table_adapter_root_node_is_visible(ETreeTableAdapter *etta)
-{
- return etta->priv->root_visible;
-}
-
-void e_tree_table_adapter_show_node (ETreeTableAdapter *etta, ETreePath path)
-{
- ETreePath parent;
-
- parent = e_tree_model_node_get_parent(etta->priv->source, path);
-
- while (parent) {
- e_tree_table_adapter_node_set_expanded(etta, parent, TRUE);
- parent = e_tree_model_node_get_parent(etta->priv->source, parent);
- }
-}
-
-gboolean e_tree_table_adapter_node_is_expanded (ETreeTableAdapter *etta, ETreePath path)
-{
- ETreeTableAdapterNode *node;
-
- if (!e_tree_model_node_is_expandable (etta->priv->source, path))
- return FALSE;
-
- if (e_tree_model_node_is_root(etta->priv->source, path) &&
- !etta->priv->root_visible)
- return TRUE;
-
- node = find_node (etta, path);
- if (node)
- return node->expanded;
- else {
- if (e_tree_model_node_is_root(etta->priv->source, path))
- return TRUE;
- else
- return e_tree_model_get_expanded_default(etta->priv->source);
- }
-}