summaryrefslogtreecommitdiff
path: root/gtk/gtktreemodelmapping.c
diff options
context:
space:
mode:
Diffstat (limited to 'gtk/gtktreemodelmapping.c')
-rw-r--r--gtk/gtktreemodelmapping.c571
1 files changed, 571 insertions, 0 deletions
diff --git a/gtk/gtktreemodelmapping.c b/gtk/gtktreemodelmapping.c
new file mode 100644
index 0000000000..886295340f
--- /dev/null
+++ b/gtk/gtktreemodelmapping.c
@@ -0,0 +1,571 @@
+/* gtktreemodelmapping.c
+ * Copyright (C) 2000 Red Hat, Inc., Alexander Larsson <alexl@redhat.com>
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * 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 "gtktreemodelmapping.h"
+#include "gtksignal.h"
+
+enum {
+ CHANGED,
+ INSERTED,
+ CHILD_TOGGLED,
+ DELETED,
+ LAST_SIGNAL
+};
+
+static guint tree_model_mapping_signals[LAST_SIGNAL] = { 0 };
+
+static void gtk_tree_model_mapping_init (GtkTreeModelMapping *tree_model_mapping);
+static void gtk_tree_model_mapping_class_init (GtkTreeModelMappingClass *tree_model_mapping_class);
+static void gtk_tree_model_mapping_tree_model_init (GtkTreeModelIface *iface);
+static void gtk_tree_model_mapping_finalize (GObject *object);
+/* signals */
+static void gtk_tree_model_mapping_changed (GtkTreeModel *model,
+ GtkTreePath *path,
+ GtkTreeIter *iter,
+ gpointer data);
+static void gtk_tree_model_mapping_inserted (GtkTreeModel *model,
+ GtkTreePath *path,
+ GtkTreeIter *iter,
+ gpointer data);
+static void gtk_tree_model_mapping_child_toggled (GtkTreeModel *model,
+ GtkTreePath *path,
+ GtkTreeIter *iter,
+ gpointer data);
+static void gtk_tree_model_mapping_deleted (GtkTreeModel *model,
+ GtkTreePath *path,
+ gpointer data);
+static void gtk_tree_model_mapping_reordered (GtkTreeModel *model,
+ GtkTreePath *path,
+ gint *new_order);
+/* vtable */
+static GtkTreeModelFlags gtk_tree_model_mapping_get_flags (GtkTreeModel *tree_model);
+static gint gtk_tree_model_mapping_get_n_columns (GtkTreeModel *tree_model);
+static GType gtk_tree_model_mapping_get_column_type (GtkTreeModel *tree_model,
+ gint index);
+static gboolean gtk_tree_model_mapping_get_iter (GtkTreeModel *tree_model,
+ GtkTreeIter *iter,
+ GtkTreePath *path);
+static GtkTreePath *gtk_tree_model_mapping_get_path (GtkTreeModel *tree_model,
+ GtkTreeIter *iter);
+static void gtk_tree_model_mapping_get_value (GtkTreeModel *tree_model,
+ GtkTreeIter *iter,
+ gint column,
+ GValue *value);
+static gboolean gtk_tree_model_mapping_iter_next (GtkTreeModel *tree_model,
+ GtkTreeIter *iter);
+static gboolean gtk_tree_model_mapping_iter_children (GtkTreeModel *tree_model,
+ GtkTreeIter *iter,
+ GtkTreeIter *parent);
+static gboolean gtk_tree_model_mapping_iter_has_child (GtkTreeModel *tree_model,
+ GtkTreeIter *iter);
+static gint gtk_tree_model_mapping_iter_n_children (GtkTreeModel *tree_model,
+ GtkTreeIter *iter);
+static gboolean gtk_tree_model_mapping_iter_nth_child (GtkTreeModel *tree_model,
+ GtkTreeIter *iter,
+ GtkTreeIter *parent,
+ gint n);
+static gboolean gtk_tree_model_mapping_iter_parent (GtkTreeModel *tree_model,
+ GtkTreeIter *iter,
+ GtkTreeIter *child);
+static void gtk_tree_model_mapping_ref_iter (GtkTreeModel *tree_model,
+ GtkTreeIter *iter);
+static void gtk_tree_model_mapping_unref_iter (GtkTreeModel *tree_model,
+ GtkTreeIter *iter);
+
+
+GtkType
+gtk_tree_model_mapping_get_type (void)
+{
+ static GtkType tree_model_mapping_type = 0;
+
+ if (!tree_model_mapping_type)
+ {
+ static const GTypeInfo tree_model_mapping_info =
+ {
+ sizeof (GtkTreeModelMappingClass),
+ NULL, /* base_init */
+ NULL, /* base_finalize */
+ (GClassInitFunc) gtk_tree_model_mapping_class_init,
+ NULL, /* class_finalize */
+ NULL, /* class_data */
+ sizeof (GtkTreeModelMapping),
+ 0, /* n_preallocs */
+ (GInstanceInitFunc) gtk_tree_model_mapping_init
+ };
+
+ static const GInterfaceInfo tree_model_info =
+ {
+ (GInterfaceInitFunc) gtk_tree_model_mapping_tree_model_init,
+ NULL,
+ NULL
+ };
+
+ tree_model_mapping_type = g_type_register_static (GTK_TYPE_OBJECT, "GtkTreeModelMapping", &tree_model_mapping_info, 0);
+ g_type_add_interface_static (tree_model_mapping_type,
+ GTK_TYPE_TREE_MODEL,
+ &tree_model_info);
+ }
+
+ return tree_model_mapping_type;
+}
+
+static void
+gtk_tree_model_mapping_class_init (GtkTreeModelMappingClass *tree_model_mapping_class)
+{
+ GObjectClass *object_class;
+
+ object_class = (GObjectClass *) tree_model_mapping_class;
+
+ object_class->finalize = gtk_tree_model_mapping_finalize;
+
+ tree_model_mapping_signals[CHANGED] =
+ gtk_signal_new ("changed",
+ GTK_RUN_FIRST,
+ GTK_CLASS_TYPE (object_class),
+ GTK_SIGNAL_OFFSET (GtkTreeModelMappingClass, changed),
+ gtk_marshal_VOID__POINTER_POINTER,
+ GTK_TYPE_NONE, 2,
+ GTK_TYPE_POINTER,
+ GTK_TYPE_POINTER);
+ tree_model_mapping_signals[INSERTED] =
+ gtk_signal_new ("inserted",
+ GTK_RUN_FIRST,
+ GTK_CLASS_TYPE (object_class),
+ GTK_SIGNAL_OFFSET (GtkTreeModelMappingClass, inserted),
+ gtk_marshal_VOID__POINTER_POINTER,
+ GTK_TYPE_NONE, 2,
+ GTK_TYPE_POINTER,
+ GTK_TYPE_POINTER);
+ tree_model_mapping_signals[CHILD_TOGGLED] =
+ gtk_signal_new ("child_toggled",
+ GTK_RUN_FIRST,
+ GTK_CLASS_TYPE (object_class),
+ GTK_SIGNAL_OFFSET (GtkTreeModelMappingClass, child_toggled),
+ gtk_marshal_VOID__POINTER_POINTER,
+ GTK_TYPE_NONE, 2,
+ GTK_TYPE_POINTER,
+ GTK_TYPE_POINTER);
+ tree_model_mapping_signals[DELETED] =
+ gtk_signal_new ("deleted",
+ GTK_RUN_FIRST,
+ GTK_CLASS_TYPE (object_class),
+ GTK_SIGNAL_OFFSET (GtkTreeModelMappingClass, deleted),
+ gtk_marshal_VOID__POINTER,
+ GTK_TYPE_NONE, 1,
+ GTK_TYPE_POINTER);
+}
+
+static void
+gtk_tree_model_mapping_tree_model_init (GtkTreeModelIface *iface)
+{
+ iface->get_flags = gtk_tree_model_mapping_get_flags;
+ iface->get_n_columns = gtk_tree_model_mapping_get_n_columns;
+ iface->get_column_type = gtk_tree_model_mapping_get_column_type;
+ iface->get_iter = gtk_tree_model_mapping_get_iter;
+ iface->get_path = gtk_tree_model_mapping_get_path;
+ iface->get_value = gtk_tree_model_mapping_get_value;
+ iface->iter_next = gtk_tree_model_mapping_iter_next;
+ iface->iter_children = gtk_tree_model_mapping_iter_children;
+ iface->iter_has_child = gtk_tree_model_mapping_iter_has_child;
+ iface->iter_n_children = gtk_tree_model_mapping_iter_n_children;
+ iface->iter_nth_child = gtk_tree_model_mapping_iter_nth_child;
+ iface->iter_parent = gtk_tree_model_mapping_iter_parent;
+ iface->ref_iter = gtk_tree_model_mapping_ref_iter;
+ iface->unref_iter = gtk_tree_model_mapping_unref_iter;
+}
+
+static void
+gtk_tree_model_mapping_init (GtkTreeModelMapping *tree_model_mapping)
+{
+}
+
+GtkTreeModel *
+gtk_tree_model_mapping_new (void)
+{
+ return GTK_TREE_MODEL (gtk_type_new (gtk_tree_model_mapping_get_type ()));
+}
+
+GtkTreeModel *
+gtk_tree_model_mapping_new_with_model (GtkTreeModel *child_model)
+{
+ GtkTreeModel *retval;
+
+ retval = gtk_tree_model_mapping_new ();
+ gtk_tree_model_mapping_set_model (GTK_TREE_MODEL_MAPPING (retval), child_model);
+ return retval;
+}
+
+void
+gtk_tree_model_mapping_set_n_columns (GtkTreeModelMapping *tree_model_mapping,
+ gint n_columns)
+{
+ g_return_if_fail (tree_model_mapping != NULL);
+ g_return_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model_mapping));
+
+ tree_model_mapping->n_columns = n_columns;
+ tree_model_mapping->column_maps = g_realloc (tree_model_mapping->column_maps, sizeof (GtkTreeModelMapping)*n_columns);
+}
+
+void
+gtk_tree_model_mapping_set_column_mapping (GtkTreeModelMapping *tree_model_mapping,
+ gint column,
+ gint src_column,
+ GType col_type,
+ GValueMapFunc map_func,
+ gpointer user_data)
+{
+ GtkTreeModelMappingMap *map;
+
+ g_return_if_fail (tree_model_mapping != NULL);
+ g_return_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model_mapping));
+ g_return_if_fail (column < tree_model_mapping->n_columns);
+
+ map = &tree_model_mapping->column_maps[column];
+ map->src_column = src_column;
+ map->col_type = col_type;
+ map->map_func = map_func;
+ map->user_data = user_data;
+}
+
+/**
+ * gtk_tree_model_mapping_set_model:
+ * @tree_model_mapping: The #GtkTreeModelMapping.
+ * @child_model: A #GtkTreeModel, or NULL.
+ *
+ * Sets the model of @tree_model_mapping to be @model. If @model is NULL, then the
+ * old model is unset.
+ **/
+void
+gtk_tree_model_mapping_set_model (GtkTreeModelMapping *tree_model_mapping,
+ GtkTreeModel *child_model)
+{
+ g_return_if_fail (tree_model_mapping != NULL);
+ g_return_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model_mapping));
+
+ if (child_model)
+ g_object_ref (G_OBJECT (child_model));
+
+ if (tree_model_mapping->child_model)
+ {
+ gtk_signal_disconnect_by_func (GTK_OBJECT (tree_model_mapping->child_model),
+ gtk_tree_model_mapping_changed,
+ tree_model_mapping);
+ gtk_signal_disconnect_by_func (GTK_OBJECT (tree_model_mapping->child_model),
+ gtk_tree_model_mapping_inserted,
+ tree_model_mapping);
+ gtk_signal_disconnect_by_func (GTK_OBJECT (tree_model_mapping->child_model),
+ gtk_tree_model_mapping_child_toggled,
+ tree_model_mapping);
+ gtk_signal_disconnect_by_func (GTK_OBJECT (tree_model_mapping->child_model),
+ gtk_tree_model_mapping_deleted,
+ tree_model_mapping);
+
+ g_object_unref (G_OBJECT (tree_model_mapping->child_model));
+ }
+
+ tree_model_mapping->child_model = child_model;
+
+ if (child_model)
+ {
+ gtk_signal_connect (GTK_OBJECT (child_model),
+ "changed",
+ gtk_tree_model_mapping_changed,
+ tree_model_mapping);
+ gtk_signal_connect (GTK_OBJECT (child_model),
+ "inserted",
+ gtk_tree_model_mapping_inserted,
+ tree_model_mapping);
+ gtk_signal_connect (GTK_OBJECT (child_model),
+ "child_toggled",
+ gtk_tree_model_mapping_child_toggled,
+ tree_model_mapping);
+ gtk_signal_connect (GTK_OBJECT (child_model),
+ "deleted",
+ gtk_tree_model_mapping_deleted,
+ tree_model_mapping);
+ }
+}
+
+/**
+ * gtk_tree_model_mapping_get_model:
+ * @tree_model: a #GtkTreeModelMapping
+ *
+ * Returns the model the #GtkTreeModelMapping is mappinging.
+ *
+ * Return value: the "child model" being mappinged
+ **/
+GtkTreeModel*
+gtk_tree_model_mapping_get_model (GtkTreeModelMapping *tree_model)
+{
+ g_return_val_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model), NULL);
+
+ return tree_model->child_model;
+}
+
+static void
+gtk_tree_model_mapping_finalize (GObject *object)
+{
+ GtkTreeModelMapping *tree_model_mapping = (GtkTreeModelMapping *) object;
+
+ g_free (tree_model_mapping->column_maps);
+ tree_model_mapping->column_maps = NULL;
+
+ if (tree_model_mapping->child_model)
+ {
+ g_object_unref (G_OBJECT (tree_model_mapping->child_model));
+ tree_model_mapping->child_model = NULL;
+ }
+}
+
+static void
+gtk_tree_model_mapping_changed (GtkTreeModel *model,
+ GtkTreePath *path,
+ GtkTreeIter *iter,
+ gpointer data)
+{
+ gtk_signal_emit_by_name (GTK_OBJECT (data), "changed", path, iter);
+}
+
+static void
+gtk_tree_model_mapping_inserted (GtkTreeModel *model,
+ GtkTreePath *path,
+ GtkTreeIter *iter,
+ gpointer data)
+{
+ gtk_signal_emit_by_name (GTK_OBJECT (data), "inserted", path, iter);
+}
+
+static void
+gtk_tree_model_mapping_child_toggled (GtkTreeModel *model,
+ GtkTreePath *path,
+ GtkTreeIter *iter,
+ gpointer data)
+{
+ gtk_signal_emit_by_name (GTK_OBJECT (data), "child_toggled", path, iter);
+}
+
+static void
+gtk_tree_model_mapping_deleted (GtkTreeModel *model,
+ GtkTreePath *path,
+ gpointer data)
+{
+ gtk_signal_emit_by_name (GTK_OBJECT (data), "deleted", path);
+}
+
+
+static GtkTreeModelFlags
+gtk_tree_model_mapping_get_flags (GtkTreeModel *tree_model)
+{
+ GtkTreeModel *child_model;
+
+ g_return_val_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model), 0);
+ g_return_val_if_fail (GTK_TREE_MODEL_MAPPING (tree_model)->child_model != NULL, 0);
+
+ child_model = GTK_TREE_MODEL_MAPPING (tree_model)->child_model;
+
+ return gtk_tree_model_get_flags (child_model);
+}
+
+static gint
+gtk_tree_model_mapping_get_n_columns (GtkTreeModel *tree_model)
+{
+ GtkTreeModelMapping *tree_model_mapping;
+
+ g_return_val_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model), 0);
+
+ tree_model_mapping = GTK_TREE_MODEL_MAPPING (tree_model);
+
+ return tree_model_mapping->n_columns;
+}
+
+static GType
+gtk_tree_model_mapping_get_column_type (GtkTreeModel *tree_model,
+ gint index)
+{
+ GtkTreeModelMapping *tree_model_mapping;
+
+ g_return_val_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model), 0);
+
+ tree_model_mapping = GTK_TREE_MODEL_MAPPING (tree_model);
+
+ return tree_model_mapping->column_maps[index].col_type;
+}
+
+static gboolean
+gtk_tree_model_mapping_get_iter (GtkTreeModel *tree_model,
+ GtkTreeIter *iter,
+ GtkTreePath *path)
+{
+ GtkTreeModel *child_model;
+
+ g_return_val_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model), 0);
+ g_return_val_if_fail (GTK_TREE_MODEL_MAPPING (tree_model)->child_model != NULL, 0);
+
+ child_model = GTK_TREE_MODEL_MAPPING (tree_model)->child_model;
+
+ return gtk_tree_model_get_iter (child_model, iter, path);
+}
+
+static GtkTreePath *
+gtk_tree_model_mapping_get_path (GtkTreeModel *tree_model,
+ GtkTreeIter *iter)
+{
+ GtkTreeModel *child_model;
+
+ g_return_val_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model), 0);
+ g_return_val_if_fail (GTK_TREE_MODEL_MAPPING (tree_model)->child_model != NULL, 0);
+
+ child_model = GTK_TREE_MODEL_MAPPING (tree_model)->child_model;
+
+ return gtk_tree_model_get_path (child_model, iter);
+}
+
+static void
+gtk_tree_model_mapping_get_value (GtkTreeModel *tree_model,
+ GtkTreeIter *iter,
+ gint column,
+ GValue *value)
+{
+ GValue src_val = { 0, };
+ GtkTreeModel *child_model;
+ GtkTreeModelMapping *tree_model_mapping;
+ GtkTreeModelMappingMap *map;
+
+ g_return_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model));
+ g_return_if_fail (GTK_TREE_MODEL_MAPPING (tree_model)->child_model != NULL);
+
+ tree_model_mapping = GTK_TREE_MODEL_MAPPING (tree_model);
+ child_model = tree_model_mapping->child_model;
+
+ map = &tree_model_mapping->column_maps[column];
+
+ gtk_tree_model_get_value (child_model, iter, map->src_column, &src_val);
+ (* map->map_func) (&src_val, value, map->user_data);
+ g_value_unset (&src_val);
+}
+
+static gboolean
+gtk_tree_model_mapping_iter_next (GtkTreeModel *tree_model,
+ GtkTreeIter *iter)
+{
+ GtkTreeModel *child_model;
+
+ g_return_val_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model), 0);
+ g_return_val_if_fail (GTK_TREE_MODEL_MAPPING (tree_model)->child_model != NULL, 0);
+
+ child_model = GTK_TREE_MODEL_MAPPING (tree_model)->child_model;
+
+ return gtk_tree_model_iter_next (child_model, iter);
+}
+
+static gboolean
+gtk_tree_model_mapping_iter_children (GtkTreeModel *tree_model,
+ GtkTreeIter *iter,
+ GtkTreeIter *parent)
+{
+ GtkTreeModel *child_model;
+
+ g_return_val_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model), 0);
+ g_return_val_if_fail (GTK_TREE_MODEL_MAPPING (tree_model)->child_model != NULL, 0);
+
+ child_model = GTK_TREE_MODEL_MAPPING (tree_model)->child_model;
+ return gtk_tree_model_iter_children (child_model, iter, parent);
+}
+
+static gboolean
+gtk_tree_model_mapping_iter_has_child (GtkTreeModel *tree_model,
+ GtkTreeIter *iter)
+
+{
+ GtkTreeModel *child_model;
+
+ g_return_val_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model), 0);
+ g_return_val_if_fail (GTK_TREE_MODEL_MAPPING (tree_model)->child_model != NULL, 0);
+
+ child_model = GTK_TREE_MODEL_MAPPING (tree_model)->child_model;
+ return gtk_tree_model_iter_has_child (child_model, iter);
+}
+
+static gint
+gtk_tree_model_mapping_iter_n_children (GtkTreeModel *tree_model,
+ GtkTreeIter *iter)
+{
+ GtkTreeModel *child_model;
+
+ g_return_val_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model), 0);
+ g_return_val_if_fail (GTK_TREE_MODEL_MAPPING (tree_model)->child_model != NULL, 0);
+
+ child_model = GTK_TREE_MODEL_MAPPING (tree_model)->child_model;
+ return gtk_tree_model_iter_n_children (child_model, iter);
+}
+
+static gboolean
+gtk_tree_model_mapping_iter_nth_child (GtkTreeModel *tree_model,
+ GtkTreeIter *iter,
+ GtkTreeIter *parent,
+ gint n)
+{
+ GtkTreeModel *child_model;
+
+ g_return_val_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model), 0);
+ g_return_val_if_fail (GTK_TREE_MODEL_MAPPING (tree_model)->child_model != NULL, 0);
+
+ child_model = GTK_TREE_MODEL_MAPPING (tree_model)->child_model;
+ return gtk_tree_model_iter_nth_child (child_model, iter, parent, n);
+}
+
+static gboolean
+gtk_tree_model_mapping_iter_parent (GtkTreeModel *tree_model,
+ GtkTreeIter *iter,
+ GtkTreeIter *child)
+{
+ GtkTreeModel *child_model;
+
+ g_return_val_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model), 0);
+ g_return_val_if_fail (GTK_TREE_MODEL_MAPPING (tree_model)->child_model != NULL, 0);
+
+ child_model = GTK_TREE_MODEL_MAPPING (tree_model)->child_model;
+ return gtk_tree_model_iter_parent (child_model, iter, child);
+}
+
+static void
+gtk_tree_model_mapping_ref_iter (GtkTreeModel *tree_model,
+ GtkTreeIter *iter)
+{
+ GtkTreeModel *child_model;
+
+ g_return_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model));
+ g_return_if_fail (GTK_TREE_MODEL_MAPPING (tree_model)->child_model != NULL);
+
+ child_model = GTK_TREE_MODEL_MAPPING (tree_model)->child_model;
+ gtk_tree_model_ref_iter (child_model, iter);
+}
+
+static void
+gtk_tree_model_mapping_unref_iter (GtkTreeModel *tree_model,
+ GtkTreeIter *iter)
+{
+ GtkTreeModel *child_model;
+
+ g_return_if_fail (GTK_IS_TREE_MODEL_MAPPING (tree_model));
+ g_return_if_fail (GTK_TREE_MODEL_MAPPING (tree_model)->child_model != NULL);
+
+ child_model = GTK_TREE_MODEL_MAPPING (tree_model)->child_model;
+ gtk_tree_model_unref_iter (child_model, iter);
+}