summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--gtk/Makefile.am4
-rw-r--r--gtk/gtkcellarea.c695
-rw-r--r--gtk/gtkcellarea.h218
-rw-r--r--gtk/gtkcellareabox.c315
-rw-r--r--gtk/gtkcellareabox.h71
5 files changed, 1303 insertions, 0 deletions
diff --git a/gtk/Makefile.am b/gtk/Makefile.am
index 0774710ff2..eae08f0100 100644
--- a/gtk/Makefile.am
+++ b/gtk/Makefile.am
@@ -168,6 +168,8 @@ gtk_public_h_sources = \
gtkbuildable.h \
gtkbutton.h \
gtkcalendar.h \
+ gtkcellarea.h \
+ gtkcellareabox.h \
gtkcelleditable.h \
gtkcelllayout.h \
gtkcellrenderer.h \
@@ -430,6 +432,8 @@ gtk_base_c_sources = \
gtkbuilderparser.c \
gtkbutton.c \
gtkcalendar.c \
+ gtkcellarea.c \
+ gtkcellareabox.c \
gtkcelleditable.c \
gtkcelllayout.c \
gtkcellrenderer.c \
diff --git a/gtk/gtkcellarea.c b/gtk/gtkcellarea.c
new file mode 100644
index 0000000000..e4611e364e
--- /dev/null
+++ b/gtk/gtkcellarea.c
@@ -0,0 +1,695 @@
+/* gtkcellarea.c
+ *
+ * Copyright (C) 2010 Openismus GmbH
+ *
+ * Authors:
+ * Tristan Van Berkom <tristanvb@openismus.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 "gtkcelllayout.h"
+#include "gtkcellarea.h"
+
+/* GObjectClass */
+static void gtk_cell_area_dispose (GObject *object);
+static void gtk_cell_area_finalize (GObject *object);
+
+/* GtkCellAreaClass */
+static void gtk_cell_area_real_get_preferred_height_for_width (GtkCellArea *area,
+ GtkWidget *widget,
+ gint width,
+ gint *minimum_height,
+ gint *natural_height);
+static void gtk_cell_area_real_get_preferred_width_for_height (GtkCellArea *area,
+ GtkWidget *widget,
+ gint height,
+ gint *minimum_width,
+ gint *natural_width);
+
+/* GtkCellLayoutIface */
+static void gtk_cell_area_cell_layout_init (GtkCellLayoutIface *iface);
+static void gtk_cell_area_pack_default (GtkCellLayout *cell_layout,
+ GtkCellRenderer *renderer,
+ gboolean expand);
+static void gtk_cell_area_clear (GtkCellLayout *cell_layout);
+static void gtk_cell_area_add_attribute (GtkCellLayout *cell_layout,
+ GtkCellRenderer *renderer,
+ const gchar *attribute,
+ gint id);
+static void gtk_cell_area_set_cell_data_func (GtkCellLayout *cell_layout,
+ GtkCellRenderer *cell,
+ GtkCellLayoutDataFunc func,
+ gpointer func_data,
+ GDestroyNotify destroy);
+static void gtk_cell_area_clear_attributes (GtkCellLayout *cell_layout,
+ GtkCellRenderer *renderer);
+static void gtk_cell_area_reorder (GtkCellLayout *cell_layout,
+ GtkCellRenderer *cell,
+ gint position);
+static GList *gtk_cell_area_get_cells (GtkCellLayout *cell_layout);
+
+/* GtkCellLayoutDataFunc handling */
+typedef struct {
+ GtkCellLayoutDataFunc func;
+ gpointer data;
+ GDestroyNotify destroy;
+} CustomCellData;
+
+static CustomCellData *custom_cell_data_new (GtkCellLayoutDataFunc func,
+ gpointer data,
+ GDestroyNotify destroy);
+static void custom_cell_data_free (CustomCellData *custom);
+
+/* Struct to pass data while looping over
+ * cell renderer attributes
+ */
+typedef struct {
+ GtkCellArea *area;
+ GtkTreeModel *model;
+ GtkTreeIter *iter;
+} AttributeData;
+
+struct _GtkCellAreaPrivate
+{
+ GHashTable *custom_cell_data;
+};
+
+G_DEFINE_ABSTRACT_TYPE_WITH_CODE (GtkCellArea, gtk_cell_area, G_TYPE_INITIALLY_UNOWNED,
+ G_IMPLEMENT_INTERFACE (GTK_TYPE_CELL_LAYOUT,
+ gtk_cell_area_cell_layout_init));
+
+static void
+gtk_cell_area_init (GtkCellArea *area)
+{
+ GtkCellAreaPrivate *priv;
+
+ area->priv = G_TYPE_INSTANCE_GET_PRIVATE (area,
+ GTK_TYPE_CELL_AREA,
+ GtkCellAreaPrivate);
+ priv = area->priv;
+
+ priv->custom_cell_data = g_hash_table_new_full (g_direct_hash,
+ g_direct_equal,
+ NULL,
+ (GDestroyNotify)custom_cell_data_free);
+}
+
+static void
+gtk_cell_area_class_init (GtkCellAreaClass *class)
+{
+ GObjectClass *object_class = G_OBJECT_CLASS (class);
+
+ /* GObjectClass */
+ object_class->dispose = gtk_cell_area_dispose;
+ object_class->finalize = gtk_cell_area_finalize;
+
+ /* general */
+ class->add = NULL;
+ class->remove = NULL;
+ class->forall = NULL;
+ class->event = NULL;
+ class->render = NULL;
+
+ /* attributes */
+ class->attribute_connect = NULL;
+ class->attribute_disconnect = NULL;
+ class->attribute_forall = NULL;
+
+ /* geometry */
+ class->get_request_mode = NULL;
+ class->get_preferred_width = NULL;
+ class->get_preferred_height = NULL;
+ class->get_preferred_height_for_width = gtk_cell_area_real_get_preferred_height_for_width;
+ class->get_preferred_width_for_height = gtk_cell_area_real_get_preferred_width_for_height;
+
+ g_type_class_add_private (object_class, sizeof (GtkCellAreaPrivate));
+}
+
+
+/*************************************************************
+ * GObjectClass *
+ *************************************************************/
+static void
+gtk_cell_area_finalize (GObject *object)
+{
+ GtkCellArea *area = GTK_CELL_AREA (object);
+ GtkCellAreaPrivate *priv = area->priv;
+
+ /* All cell renderers should already be removed at this point,
+ * just kill our hash table here.
+ */
+ g_hash_table_destroy (priv->custom_cell_data);
+
+ G_OBJECT_CLASS (gtk_cell_area_parent_class)->finalize (object);
+}
+
+
+static void
+gtk_cell_area_dispose (GObject *object)
+{
+ /* This removes every cell renderer that may be added to the GtkCellArea,
+ * subclasses should be breaking references to the GtkCellRenderers
+ * at this point.
+ */
+ gtk_cell_layout_clear (GTK_CELL_LAYOUT (object));
+
+ G_OBJECT_CLASS (gtk_cell_area_parent_class)->dispose (object);
+}
+
+
+/*************************************************************
+ * GtkCellAreaClass *
+ *************************************************************/
+static void
+gtk_cell_area_real_get_preferred_height_for_width (GtkCellArea *area,
+ GtkWidget *widget,
+ gint width,
+ gint *minimum_height,
+ gint *natural_height)
+{
+ /* If the area doesnt do height-for-width, fallback on base preferred height */
+ GTK_CELL_AREA_GET_CLASS (area)->get_preferred_width (area, widget, minimum_height, natural_height);
+}
+
+static void
+gtk_cell_area_real_get_preferred_width_for_height (GtkCellArea *area,
+ GtkWidget *widget,
+ gint height,
+ gint *minimum_width,
+ gint *natural_width)
+{
+ /* If the area doesnt do width-for-height, fallback on base preferred width */
+ GTK_CELL_AREA_GET_CLASS (area)->get_preferred_width (area, widget, minimum_width, natural_width);
+}
+
+/*************************************************************
+ * GtkCellLayoutIface *
+ *************************************************************/
+static CustomCellData *
+custom_cell_data_new (GtkCellLayoutDataFunc func,
+ gpointer data,
+ GDestroyNotify destroy)
+{
+ CustomCellData *custom = g_slice_new (CustomCellData);
+
+ custom->func = func;
+ custom->data = data;
+ custom->destroy = destroy;
+
+ return custom;
+}
+
+static void
+custom_cell_data_free (CustomCellData *custom)
+{
+ if (custom->destroy)
+ custom->destroy (custom->data);
+
+ g_slice_free (CustomCellData, custom);
+}
+
+static void
+gtk_cell_area_cell_layout_init (GtkCellLayoutIface *iface)
+{
+ iface->pack_start = gtk_cell_area_pack_default;
+ iface->pack_end = gtk_cell_area_pack_default;
+ iface->clear = gtk_cell_area_clear;
+ iface->add_attribute = gtk_cell_area_add_attribute;
+ iface->set_cell_data_func = gtk_cell_area_set_cell_data_func;
+ iface->clear_attributes = gtk_cell_area_clear_attributes;
+ iface->reorder = gtk_cell_area_reorder;
+ iface->get_cells = gtk_cell_area_get_cells;
+}
+
+static void
+gtk_cell_area_pack_default (GtkCellLayout *cell_layout,
+ GtkCellRenderer *renderer,
+ gboolean expand)
+{
+ gtk_cell_area_add (GTK_CELL_AREA (cell_layout), renderer);
+}
+
+static void
+gtk_cell_area_clear (GtkCellLayout *cell_layout)
+{
+ GtkCellArea *area = GTK_CELL_AREA (cell_layout);
+ GList *l, *cells =
+ gtk_cell_layout_get_cells (cell_layout);
+
+ for (l = cells; l; l = l->next)
+ {
+ GtkCellRenderer *renderer = l->data;
+ gtk_cell_area_remove (area, renderer);
+ }
+
+ g_list_free (cells);
+}
+
+static void
+gtk_cell_area_add_attribute (GtkCellLayout *cell_layout,
+ GtkCellRenderer *renderer,
+ const gchar *attribute,
+ gint id)
+{
+ gtk_cell_area_attribute_connect (GTK_CELL_AREA (cell_layout),
+ renderer, attribute, id);
+}
+
+typedef struct {
+ const gchar *attribute;
+ gchar id;
+} CellAttribute;
+
+static void
+accum_attributes (GtkCellArea *area,
+ GtkCellRenderer *renderer,
+ const gchar *attribute,
+ gint id,
+ GList **accum)
+{
+ CellAttribute *attrib = g_slice_new (CellAttribute);
+
+ attrib->attribute = attribute;
+ attrib->id = id;
+
+ *accum = g_list_prepend (*accum, attrib);
+}
+
+static void
+gtk_cell_area_set_cell_data_func (GtkCellLayout *cell_layout,
+ GtkCellRenderer *cell,
+ GtkCellLayoutDataFunc func,
+ gpointer func_data,
+ GDestroyNotify destroy)
+{
+ GtkCellArea *area = GTK_CELL_AREA (cell_layout);
+ GtkCellAreaPrivate *priv = area->priv;
+ CustomCellData *custom;
+
+ if (func)
+ {
+ custom = custom_cell_data_new (func, func_data, destroy);
+ g_hash_table_insert (priv->custom_cell_data, cell, custom);
+ }
+ else
+ g_hash_table_remove (priv->custom_cell_data, cell);
+}
+
+
+static void
+gtk_cell_area_clear_attributes (GtkCellLayout *cell_layout,
+ GtkCellRenderer *renderer)
+{
+ GtkCellArea *area = GTK_CELL_AREA (cell_layout);
+ GList *l, *attributes = NULL;
+
+ /* Get a list of attributes so we dont modify the list inline */
+ gtk_cell_area_attribute_forall (area, renderer,
+ (GtkCellAttributeCallback)accum_attributes,
+ &attributes);
+
+ for (l = attributes; l; l = l->next)
+ {
+ CellAttribute *attrib = l->data;
+
+ gtk_cell_area_attribute_disconnect (area, renderer,
+ attrib->attribute, attrib->id);
+
+ g_slice_free (CellAttribute, attrib);
+ }
+
+ g_list_free (attributes);
+}
+
+static void
+gtk_cell_area_reorder (GtkCellLayout *cell_layout,
+ GtkCellRenderer *cell,
+ gint position)
+{
+ g_warning ("GtkCellLayout::reorder not implemented for `%s'",
+ g_type_name (G_TYPE_FROM_INSTANCE (cell_layout)));
+}
+
+static void
+accum_cells (GtkCellRenderer *renderer,
+ GList **accum)
+{
+ *accum = g_list_prepend (*accum, renderer);
+}
+
+static GList *
+gtk_cell_area_get_cells (GtkCellLayout *cell_layout)
+{
+ GList *cells = NULL;
+
+ gtk_cell_area_forall (GTK_CELL_AREA (cell_layout),
+ (GtkCellCallback)accum_cells,
+ &cells);
+
+ return g_list_reverse (cells);
+}
+
+
+/*************************************************************
+ * API *
+ *************************************************************/
+
+/* Basic methods */
+void
+gtk_cell_area_add (GtkCellArea *area,
+ GtkCellRenderer *renderer)
+{
+ GtkCellAreaClass *class;
+
+ g_return_if_fail (GTK_IS_CELL_AREA (area));
+ g_return_if_fail (GTK_IS_CELL_RENDERER (renderer));
+
+ class = GTK_CELL_AREA_GET_CLASS (area);
+
+ if (class->add)
+ class->add (area, renderer);
+ else
+ g_warning ("GtkCellAreaClass::add not implemented for `%s'",
+ g_type_name (G_TYPE_FROM_INSTANCE (area)));
+}
+
+void
+gtk_cell_area_remove (GtkCellArea *area,
+ GtkCellRenderer *renderer)
+{
+ GtkCellAreaClass *class;
+
+ g_return_if_fail (GTK_IS_CELL_AREA (area));
+ g_return_if_fail (GTK_IS_CELL_RENDERER (renderer));
+
+ class = GTK_CELL_AREA_GET_CLASS (area);
+
+ /* Remove any custom cell data func we have for this renderer */
+ gtk_cell_layout_set_cell_data_func (GTK_CELL_LAYOUT (area),
+ renderer, NULL, NULL, NULL);
+
+ if (class->remove)
+ class->remove (area, renderer);
+ else
+ g_warning ("GtkCellAreaClass::remove not implemented for `%s'",
+ g_type_name (G_TYPE_FROM_INSTANCE (area)));
+}
+
+void
+gtk_cell_area_forall (GtkCellArea *area,
+ GtkCellCallback callback,
+ gpointer callback_data)
+{
+ GtkCellAreaClass *class;
+
+ g_return_if_fail (GTK_IS_CELL_AREA (area));
+ g_return_if_fail (callback != NULL);
+
+ class = GTK_CELL_AREA_GET_CLASS (area);
+
+ if (class->forall)
+ class->forall (area, callback, callback_data);
+ else
+ g_warning ("GtkCellAreaClass::forall not implemented for `%s'",
+ g_type_name (G_TYPE_FROM_INSTANCE (area)));
+}
+
+gint
+gtk_cell_area_event (GtkCellArea *area,
+ GtkWidget *widget,
+ GdkEvent *event,
+ const GdkRectangle *cell_area)
+{
+ GtkCellAreaClass *class;
+
+ g_return_val_if_fail (GTK_IS_CELL_AREA (area), 0);
+ g_return_val_if_fail (GTK_IS_WIDGET (widget), 0);
+ g_return_val_if_fail (event != NULL, 0);
+ g_return_val_if_fail (cell_area != NULL, 0);
+
+ class = GTK_CELL_AREA_GET_CLASS (area);
+
+ if (class->event)
+ return class->event (area, widget, event, cell_area);
+
+ g_warning ("GtkCellAreaClass::event not implemented for `%s'",
+ g_type_name (G_TYPE_FROM_INSTANCE (area)));
+ return 0;
+}
+
+void
+gtk_cell_area_render (GtkCellArea *area,
+ cairo_t *cr,
+ GtkWidget *widget,
+ const GdkRectangle *cell_area)
+{
+ GtkCellAreaClass *class;
+
+ g_return_if_fail (GTK_IS_CELL_AREA (area));
+ g_return_if_fail (cr != NULL);
+ g_return_if_fail (GTK_IS_WIDGET (widget));
+ g_return_if_fail (cell_area != NULL);
+
+ class = GTK_CELL_AREA_GET_CLASS (area);
+
+ if (class->render)
+ class->render (area, cr, widget, cell_area);
+ else
+ g_warning ("GtkCellAreaClass::render not implemented for `%s'",
+ g_type_name (G_TYPE_FROM_INSTANCE (area)));
+}
+
+/* Attributes */
+void
+gtk_cell_area_attribute_connect (GtkCellArea *area,
+ GtkCellRenderer *renderer,
+ const gchar *attribute,
+ gint id)
+{
+ GtkCellAreaClass *class;
+
+ g_return_if_fail (GTK_IS_CELL_AREA (area));
+ g_return_if_fail (GTK_IS_CELL_RENDERER (renderer));
+ g_return_if_fail (attribute != NULL);
+
+ class = GTK_CELL_AREA_GET_CLASS (area);
+
+ if (class->attribute_connect)
+ class->attribute_connect (area, renderer, attribute, id);
+ else
+ g_warning ("GtkCellAreaClass::attribute_connect not implemented for `%s'",
+ g_type_name (G_TYPE_FROM_INSTANCE (area)));
+}
+
+void
+gtk_cell_area_attribute_disconnect (GtkCellArea *area,
+ GtkCellRenderer *renderer,
+ const gchar *attribute,
+ gint id)
+{
+ GtkCellAreaClass *class;
+
+ g_return_if_fail (GTK_IS_CELL_AREA (area));
+ g_return_if_fail (GTK_IS_CELL_RENDERER (renderer));
+ g_return_if_fail (attribute != NULL);
+
+ class = GTK_CELL_AREA_GET_CLASS (area);
+
+ if (class->attribute_disconnect)
+ class->attribute_disconnect (area, renderer, attribute, id);
+ else
+ g_warning ("GtkCellAreaClass::attribute_disconnect not implemented for `%s'",
+ g_type_name (G_TYPE_FROM_INSTANCE (area)));
+}
+
+void
+gtk_cell_area_attribute_forall (GtkCellArea *area,
+ GtkCellRenderer *renderer,
+ GtkCellAttributeCallback callback,
+ gpointer user_data)
+{
+ GtkCellAreaClass *class;
+
+ g_return_if_fail (GTK_IS_CELL_AREA (area));
+ g_return_if_fail (GTK_IS_CELL_RENDERER (renderer));
+ g_return_if_fail (callback != NULL);
+
+ class = GTK_CELL_AREA_GET_CLASS (area);
+
+ if (class->attribute_forall)
+ class->attribute_forall (area, renderer, callback, user_data);
+ else
+ g_warning ("GtkCellAreaClass::attribute_forall not implemented for `%s'",
+ g_type_name (G_TYPE_FROM_INSTANCE (area)));
+}
+
+
+/* Geometry */
+GtkSizeRequestMode
+gtk_cell_area_get_request_mode (GtkCellArea *area)
+{
+ GtkCellAreaClass *class;
+
+ g_return_val_if_fail (GTK_IS_CELL_AREA (area),
+ GTK_SIZE_REQUEST_HEIGHT_FOR_WIDTH);
+
+ class = GTK_CELL_AREA_GET_CLASS (area);
+
+ if (class->get_request_mode)
+ return class->get_request_mode (area);
+
+ g_warning ("GtkCellAreaClass::get_request_mode not implemented for `%s'",
+ g_type_name (G_TYPE_FROM_INSTANCE (area)));
+
+ return GTK_SIZE_REQUEST_HEIGHT_FOR_WIDTH;
+}
+
+void
+gtk_cell_area_get_preferred_width (GtkCellArea *area,
+ GtkWidget *widget,
+ gint *minimum_size,
+ gint *natural_size)
+{
+ GtkCellAreaClass *class;
+
+ g_return_if_fail (GTK_IS_CELL_AREA (area));
+ g_return_if_fail (GTK_IS_WIDGET (widget));
+
+ class = GTK_CELL_AREA_GET_CLASS (area);
+
+ if (class->get_preferred_width)
+ class->get_preferred_width (area, widget, minimum_size, natural_size);
+ else
+ g_warning ("GtkCellAreaClass::get_preferred_width not implemented for `%s'",
+ g_type_name (G_TYPE_FROM_INSTANCE (area)));
+}
+
+void
+gtk_cell_area_get_preferred_height_for_width (GtkCellArea *area,
+ GtkWidget *widget,
+ gint width,
+ gint *minimum_height,
+ gint *natural_height)
+{
+ GtkCellAreaClass *class;
+
+ g_return_if_fail (GTK_IS_CELL_AREA (area));
+ g_return_if_fail (GTK_IS_WIDGET (widget));
+
+ class = GTK_CELL_AREA_GET_CLASS (area);
+ class->get_preferred_height_for_width (area, widget, width, minimum_height, natural_height);
+}
+
+void
+gtk_cell_area_get_preferred_height (GtkCellArea *area,
+ GtkWidget *widget,
+ gint *minimum_size,
+ gint *natural_size)
+{
+ GtkCellAreaClass *class;
+
+ g_return_if_fail (GTK_IS_CELL_AREA (area));
+ g_return_if_fail (GTK_IS_WIDGET (widget));
+
+ class = GTK_CELL_AREA_GET_CLASS (area);
+
+ if (class->get_preferred_height)
+ class->get_preferred_height (area, widget, minimum_size, natural_size);
+ else
+ g_warning ("GtkCellAreaClass::get_preferred_height not implemented for `%s'",
+ g_type_name (G_TYPE_FROM_INSTANCE (area)));
+}
+
+void
+gtk_cell_area_get_preferred_width_for_height (GtkCellArea *area,
+ GtkWidget *widget,
+ gint height,
+ gint *minimum_width,
+ gint *natural_width)
+{
+ GtkCellAreaClass *class;
+
+ g_return_if_fail (GTK_IS_CELL_AREA (area));
+ g_return_if_fail (GTK_IS_WIDGET (widget));
+
+ class = GTK_CELL_AREA_GET_CLASS (area);
+ class->get_preferred_width_for_height (area, widget, height, minimum_width, natural_width);
+}
+
+
+static void
+apply_attributes (GtkCellRenderer *renderer,
+ const gchar *attribute,
+ gint id,
+ AttributeData *data)
+{
+ GValue value = { 0, };
+
+ /* For each attribute of each renderer we apply the value
+ * from the model to the renderer here
+ */
+ gtk_tree_model_get_value (data->model, data->iter, id, &value);
+ g_object_set_property (G_OBJECT (renderer), attribute, &value);
+ g_value_unset (&value);
+}
+
+static void
+apply_render_attributes (GtkCellRenderer *renderer,
+ AttributeData *data)
+{
+ gtk_cell_area_attribute_forall (data->area, renderer,
+ (GtkCellAttributeCallback)apply_attributes,
+ data);
+}
+
+static void
+apply_custom_cell_data (GtkCellRenderer *renderer,
+ CustomCellData *custom,
+ AttributeData *data)
+{
+ g_assert (custom->func);
+
+ /* For each renderer that has a GtkCellLayoutDataFunc set,
+ * go ahead and envoke it to apply the data from the model
+ */
+ custom->func (GTK_CELL_LAYOUT (data->area), renderer,
+ data->model, data->iter, custom->data);
+}
+
+void
+gtk_cell_area_apply_attributes (GtkCellArea *area,
+ GtkTreeModel *tree_model,
+ GtkTreeIter *iter)
+{
+ GtkCellAreaPrivate *priv;
+ AttributeData data;
+
+ g_return_if_fail (GTK_IS_CELL_AREA (area));
+ g_return_if_fail (GTK_IS_TREE_MODEL (tree_model));
+ g_return_if_fail (iter != NULL);
+
+ priv = area->priv;
+
+ /* For every cell renderer, for every attribute, apply the attribute */
+ data.area = area;
+ data.model = tree_model;
+ data.iter = iter;
+ gtk_cell_area_forall (area, (GtkCellCallback)apply_render_attributes, &data);
+
+ /* Now go over any custom cell data functions */
+ g_hash_table_foreach (priv->custom_cell_data, (GHFunc)apply_custom_cell_data, &data);
+}
diff --git a/gtk/gtkcellarea.h b/gtk/gtkcellarea.h
new file mode 100644
index 0000000000..073f76a2d1
--- /dev/null
+++ b/gtk/gtkcellarea.h
@@ -0,0 +1,218 @@
+/* gtkcellarea.h
+ *
+ * Copyright (C) 2010 Openismus GmbH
+ *
+ * Authors:
+ * Tristan Van Berkom <tristanvb@openismus.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.
+ */
+
+#if !defined (__GTK_H_INSIDE__) && !defined (GTK_COMPILATION)
+#error "Only <gtk/gtk.h> can be included directly."
+#endif
+
+#ifndef __GTK_CELL_AREA_H__
+#define __GTK_CELL_AREA_H__
+
+#include <gtk/gtkcellrenderer.h>
+#include <gtk/gtkwidget.h>
+#include <gtk/gtktreemodel.h>
+
+G_BEGIN_DECLS
+
+#define GTK_TYPE_CELL_AREA (gtk_cell_area_get_type ())
+#define GTK_CELL_AREA(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GTK_TYPE_CELL_AREA, GtkCellArea))
+#define GTK_CELL_AREA_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GTK_TYPE_CELL_AREA, GtkCellAreaClass))
+#define GTK_IS_CELL_AREA(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GTK_TYPE_CELL_AREA))
+#define GTK_IS_CELL_AREA_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GTK_TYPE_CELL_AREA))
+#define GTK_CELL_AREA_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GTK_TYPE_CELL_AREA, GtkCellAreaClass))
+
+typedef struct _GtkCellArea GtkCellArea;
+typedef struct _GtkCellAreaClass GtkCellAreaClass;
+typedef struct _GtkCellAreaPrivate GtkCellAreaPrivate;
+
+
+/**
+ * GtkCellCallback:
+ * @renderer: the cell renderer to operate on
+ * @data: user-supplied data
+ *
+ * The type of the callback functions used for iterating over
+ * the cell renderers of a #GtkCellArea, see gtk_cell_area_forall().
+ */
+typedef void (*GtkCellCallback) (GtkCellRenderer *renderer,
+ gpointer data);
+
+
+/**
+ * GtkCellAttributeCallback:
+ * @renderer: the #GtkCellRenderer that has an attribute
+ * @attribute: the property attributed to @id
+ * @id: the identifier of this attributed value
+ * @data: user-supplied data
+ *
+ * The type of the callback functions used for iterating over the
+ * attributes of the cell renderers in a #GtkCellArea,
+ * see gtk_cell_area_attribute_forall().
+ */
+typedef void (*GtkCellAttributeCallback) (GtkCellRenderer *renderer,
+ const gchar *attribute,
+ gint id,
+ gpointer data);
+
+
+struct _GtkCellArea
+{
+ GInitiallyUnowned parent_instance;
+
+ GtkCellAreaPrivate *priv;
+};
+
+struct _GtkCellAreaClass
+{
+ GInitiallyUnownedClass parent_class;
+
+ /* vtable - not signals */
+
+ /* Basic methods */
+ void (* add) (GtkCellArea *area,
+ GtkCellRenderer *renderer);
+ void (* remove) (GtkCellArea *area,
+ GtkCellRenderer *renderer);
+ void (* forall) (GtkCellArea *area,
+ GtkCellCallback callback,
+ gpointer callback_data);
+ gint (* event) (GtkCellArea *area,
+ GtkWidget *widget,
+ GdkEvent *event,
+ const GdkRectangle *cell_area);
+ void (* render) (GtkCellArea *area,
+ cairo_t *cr,
+ GtkWidget *widget,
+ const GdkRectangle *cell_area);
+
+ /* Attributes */
+ void (* attribute_connect) (GtkCellArea *area,
+ GtkCellRenderer *renderer,
+ const gchar *attribute,
+ gint id);
+ void (* attribute_disconnect) (GtkCellArea *area,
+ GtkCellRenderer *renderer,
+ const gchar *attribute,
+ gint id);
+ void (* attribute_forall) (GtkCellArea *area,
+ GtkCellRenderer *renderer,
+ GtkCellAttributeCallback callback,
+ gpointer user_data);
+
+ /* Geometry */
+ GtkSizeRequestMode (* get_request_mode) (GtkCellArea *area);
+ void (* get_preferred_width) (GtkCellArea *area,
+ GtkWidget *widget,
+ gint *minimum_size,
+ gint *natural_size);
+ void (* get_preferred_height_for_width) (GtkCellArea *area,
+ GtkWidget *widget,
+ gint width,
+ gint *minimum_height,
+ gint *natural_height);
+ void (* get_preferred_height) (GtkCellArea *area,
+ GtkWidget *widget,
+ gint *minimum_size,
+ gint *natural_size);
+ void (* get_preferred_width_for_height) (GtkCellArea *area,
+ GtkWidget *widget,
+ gint height,
+ gint *minimum_width,
+ gint *natural_width);
+
+
+ /* Padding for future expansion */
+ void (*_gtk_reserved1) (void);
+ void (*_gtk_reserved2) (void);
+ void (*_gtk_reserved3) (void);
+ void (*_gtk_reserved4) (void);
+ void (*_gtk_reserved5) (void);
+ void (*_gtk_reserved6) (void);
+ void (*_gtk_reserved7) (void);
+ void (*_gtk_reserved8) (void);
+};
+
+GType gtk_cell_area_get_type (void) G_GNUC_CONST;
+
+/* Basic methods */
+void gtk_cell_area_add (GtkCellArea *area,
+ GtkCellRenderer *renderer);
+void gtk_cell_area_remove (GtkCellArea *area,
+ GtkCellRenderer *renderer);
+void gtk_cell_area_forall (GtkCellArea *area,
+ GtkCellCallback callback,
+ gpointer callback_data);
+gint gtk_cell_area_event (GtkCellArea *area,
+ GtkWidget *widget,
+ GdkEvent *event,
+ const GdkRectangle *cell_area);
+void gtk_cell_area_render (GtkCellArea *area,
+ cairo_t *cr,
+ GtkWidget *widget,
+ const GdkRectangle *cell_area);
+
+/* Attributes */
+void gtk_cell_area_attribute_connect (GtkCellArea *area,
+ GtkCellRenderer *renderer,
+ const gchar *attribute,
+ gint id);
+void gtk_cell_area_attribute_disconnect (GtkCellArea *area,
+ GtkCellRenderer *renderer,
+ const gchar *attribute,
+ gint id);
+void gtk_cell_area_attribute_forall (GtkCellArea *area,
+ GtkCellRenderer *renderer,
+ GtkCellAttributeCallback callback,
+ gpointer user_data);
+
+/* Geometry */
+GtkSizeRequestMode gtk_cell_area_get_request_mode (GtkCellArea *area);
+void gtk_cell_area_get_preferred_width (GtkCellArea *area,
+ GtkWidget *widget,
+ gint *minimum_size,
+ gint *natural_size);
+void gtk_cell_area_get_preferred_height_for_width (GtkCellArea *area,
+ GtkWidget *widget,
+ gint width,
+ gint *minimum_height,
+ gint *natural_height);
+void gtk_cell_area_get_preferred_height (GtkCellArea *area,
+ GtkWidget *widget,
+ gint *minimum_size,
+ gint *natural_size);
+void gtk_cell_area_get_preferred_width_for_height (GtkCellArea *area,
+ GtkWidget *widget,
+ gint height,
+ gint *minimum_width,
+ gint *natural_width);
+
+
+/* Following apis are not class virtual methods */
+void gtk_cell_area_apply_attributes (GtkCellArea *area,
+ GtkTreeModel *tree_model,
+ GtkTreeIter *iter);
+
+
+G_END_DECLS
+
+#endif /* __GTK_CELL_AREA_H__ */
diff --git a/gtk/gtkcellareabox.c b/gtk/gtkcellareabox.c
new file mode 100644
index 0000000000..52db6e9ad1
--- /dev/null
+++ b/gtk/gtkcellareabox.c
@@ -0,0 +1,315 @@
+/* gtkcellarea.c
+ *
+ * Copyright (C) 2010 Openismus GmbH
+ *
+ * Authors:
+ * Tristan Van Berkom <tristanvb@openismus.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 "gtkorientable.h"
+#include "gtkcellareabox.h"
+
+/* GObjectClass */
+static void gtk_cell_area_box_finalize (GObject *object);
+static void gtk_cell_area_box_dispose (GObject *object);
+static void gtk_cell_area_box_set_property (GObject *object,
+ guint prop_id,
+ const GValue *value,
+ GParamSpec *pspec);
+static void gtk_cell_area_box_get_property (GObject *object,
+ guint prop_id,
+ GValue *value,
+ GParamSpec *pspec);
+
+/* GtkCellAreaClass */
+static void gtk_cell_area_box_add (GtkCellArea *area,
+ GtkCellRenderer *renderer);
+static void gtk_cell_area_box_remove (GtkCellArea *area,
+ GtkCellRenderer *renderer);
+static void gtk_cell_area_box_forall (GtkCellArea *area,
+ GtkCellCallback callback,
+ gpointer callback_data);
+static gint gtk_cell_area_box_event (GtkCellArea *area,
+ GtkWidget *widget,
+ GdkEvent *event,
+ const GdkRectangle *cell_area);
+static void gtk_cell_area_box_render (GtkCellArea *area,
+ cairo_t *cr,
+ GtkWidget *widget,
+ const GdkRectangle *cell_area);
+
+static void gtk_cell_area_box_attribute_connect (GtkCellArea *area,
+ GtkCellRenderer *renderer,
+ const gchar *attribute,
+ gint id);
+static void gtk_cell_area_box_attribute_disconnect (GtkCellArea *area,
+ GtkCellRenderer *renderer,
+ const gchar *attribute,
+ gint id);
+static void gtk_cell_area_box_attribute_forall (GtkCellArea *area,
+ GtkCellRenderer *renderer,
+ GtkCellAttributeCallback callback,
+ gpointer user_data);
+
+static GtkSizeRequestMode gtk_cell_area_box_get_request_mode (GtkCellArea *area);
+static void gtk_cell_area_box_get_preferred_width (GtkCellArea *area,
+ GtkWidget *widget,
+ gint *minimum_width,
+ gint *natural_width);
+static void gtk_cell_area_box_get_preferred_height (GtkCellArea *area,
+ GtkWidget *widget,
+ gint *minimum_height,
+ gint *natural_height);
+static void gtk_cell_area_box_get_preferred_height_for_width (GtkCellArea *area,
+ GtkWidget *widget,
+ gint width,
+ gint *minimum_height,
+ gint *natural_height);
+static void gtk_cell_area_box_get_preferred_width_for_height (GtkCellArea *area,
+ GtkWidget *widget,
+ gint height,
+ gint *minimum_width,
+ gint *natural_width);
+
+
+struct _GtkCellAreaBoxPrivate
+{
+ GtkOrientation orientation;
+
+
+};
+
+enum {
+ PROP_0,
+ PROP_ORIENTATION
+};
+
+
+G_DEFINE_TYPE_WITH_CODE (GtkCellAreaBox, gtk_cell_area_box, GTK_TYPE_CELL_AREA,
+ G_IMPLEMENT_INTERFACE (GTK_TYPE_ORIENTABLE, NULL));
+
+
+static void
+gtk_cell_area_box_init (GtkCellAreaBox *box)
+{
+ GtkCellAreaBoxPrivate *priv;
+
+ box->priv = G_TYPE_INSTANCE_GET_PRIVATE (box,
+ GTK_TYPE_CELL_AREA_BOX,
+ GtkCellAreaBoxPrivate);
+ priv = box->priv;
+
+ priv->orientation = GTK_ORIENTATION_HORIZONTAL;
+}
+
+static void
+gtk_cell_area_box_class_init (GtkCellAreaBoxClass *class)
+{
+ GObjectClass *object_class = G_OBJECT_CLASS (class);
+ GtkCellAreaClass *area_class = GTK_CELL_AREA_CLASS (class);
+
+ /* GObjectClass */
+ object_class->finalize = gtk_cell_area_box_finalize;
+ object_class->dispose = gtk_cell_area_box_dispose;
+ object_class->set_property = gtk_cell_area_box_set_property;
+ object_class->get_property = gtk_cell_area_box_get_property;
+
+ /* GtkCellAreaClass */
+ area_class->add = gtk_cell_area_box_add;
+ area_class->remove = gtk_cell_area_box_remove;
+ area_class->forall = gtk_cell_area_box_forall;
+ area_class->event = gtk_cell_area_box_event;
+ area_class->render = gtk_cell_area_box_render;
+
+ area_class->attribute_connect = gtk_cell_area_box_attribute_connect;
+ area_class->attribute_disconnect = gtk_cell_area_box_attribute_disconnect;
+ area_class->attribute_forall = gtk_cell_area_box_attribute_forall;
+
+ area_class->get_request_mode = gtk_cell_area_box_get_request_mode;
+ area_class->get_preferred_width = gtk_cell_area_box_get_preferred_width;
+ area_class->get_preferred_height = gtk_cell_area_box_get_preferred_height;
+ area_class->get_preferred_height_for_width = gtk_cell_area_box_get_preferred_height_for_width;
+ area_class->get_preferred_width_for_height = gtk_cell_area_box_get_preferred_width_for_height;
+
+ g_object_class_override_property (object_class, PROP_ORIENTATION, "orientation");
+
+
+ g_type_class_add_private (object_class, sizeof (GtkCellAreaBoxPrivate));
+}
+
+
+/*************************************************************
+ * GObjectClass *
+ *************************************************************/
+static void
+gtk_cell_area_box_finalize (GObject *object)
+{
+ G_OBJECT_CLASS (gtk_cell_area_box_parent_class)->finalize (object);
+}
+
+static void
+gtk_cell_area_box_dispose (GObject *object)
+{
+ G_OBJECT_CLASS (gtk_cell_area_box_parent_class)->dispose (object);
+}
+
+static void
+gtk_cell_area_box_set_property (GObject *object,
+ guint prop_id,
+ const GValue *value,
+ GParamSpec *pspec)
+{
+
+}
+
+static void
+gtk_cell_area_box_get_property (GObject *object,
+ guint prop_id,
+ GValue *value,
+ GParamSpec *pspec)
+{
+
+}
+
+
+/*************************************************************
+ * GtkCellAreaClass *
+ *************************************************************/
+static void
+gtk_cell_area_box_add (GtkCellArea *area,
+ GtkCellRenderer *renderer)
+{
+
+}
+
+static void
+gtk_cell_area_box_remove (GtkCellArea *area,
+ GtkCellRenderer *renderer)
+{
+
+}
+
+static void
+gtk_cell_area_box_forall (GtkCellArea *area,
+ GtkCellCallback callback,
+ gpointer callback_data)
+{
+
+}
+
+static gint
+gtk_cell_area_box_event (GtkCellArea *area,
+ GtkWidget *widget,
+ GdkEvent *event,
+ const GdkRectangle *cell_area)
+{
+
+
+ return 0;
+}
+
+static void
+gtk_cell_area_box_render (GtkCellArea *area,
+ cairo_t *cr,
+ GtkWidget *widget,
+ const GdkRectangle *cell_area)
+{
+
+}
+
+static void
+gtk_cell_area_box_attribute_connect (GtkCellArea *area,
+ GtkCellRenderer *renderer,
+ const gchar *attribute,
+ gint id)
+{
+
+}
+
+static void
+gtk_cell_area_box_attribute_disconnect (GtkCellArea *area,
+ GtkCellRenderer *renderer,
+ const gchar *attribute,
+ gint id)
+{
+
+}
+
+static void
+gtk_cell_area_box_attribute_forall (GtkCellArea *area,
+ GtkCellRenderer *renderer,
+ GtkCellAttributeCallback callback,
+ gpointer user_data)
+{
+
+}
+
+
+static GtkSizeRequestMode
+gtk_cell_area_box_get_request_mode (GtkCellArea *area)
+{
+ GtkCellAreaBox *box = GTK_CELL_AREA_BOX (area);
+ GtkCellAreaBoxPrivate *priv = box->priv;
+
+ return (priv->orientation) == GTK_ORIENTATION_HORIZONTAL ?
+ GTK_SIZE_REQUEST_HEIGHT_FOR_WIDTH :
+ GTK_SIZE_REQUEST_WIDTH_FOR_HEIGHT;
+}
+
+static void
+gtk_cell_area_box_get_preferred_width (GtkCellArea *area,
+ GtkWidget *widget,
+ gint *minimum_width,
+ gint *natural_width)
+{
+
+}
+
+static void
+gtk_cell_area_box_get_preferred_height (GtkCellArea *area,
+ GtkWidget *widget,
+ gint *minimum_height,
+ gint *natural_height)
+{
+
+
+}
+
+static void
+gtk_cell_area_box_get_preferred_height_for_width (GtkCellArea *area,
+ GtkWidget *widget,
+ gint width,
+ gint *minimum_height,
+ gint *natural_height)
+{
+
+}
+
+static void
+gtk_cell_area_box_get_preferred_width_for_height (GtkCellArea *area,
+ GtkWidget *widget,
+ gint height,
+ gint *minimum_width,
+ gint *natural_width)
+{
+
+}
+
+/*************************************************************
+ * API *
+ *************************************************************/
diff --git a/gtk/gtkcellareabox.h b/gtk/gtkcellareabox.h
new file mode 100644
index 0000000000..1e188cecb2
--- /dev/null
+++ b/gtk/gtkcellareabox.h
@@ -0,0 +1,71 @@
+/* gtkcellareabox.h
+ *
+ * Copyright (C) 2010 Openismus GmbH
+ *
+ * Authors:
+ * Tristan Van Berkom <tristanvb@openismus.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.
+ */
+
+#if !defined (__GTK_H_INSIDE__) && !defined (GTK_COMPILATION)
+#error "Only <gtk/gtk.h> can be included directly."
+#endif
+
+#ifndef __GTK_CELL_AREA_BOX_H__
+#define __GTK_CELL_AREA_BOX_H__
+
+#include <gtk/gtkcellarea.h>
+
+G_BEGIN_DECLS
+
+#define GTK_TYPE_CELL_AREA_BOX (gtk_cell_area_box_get_type ())
+#define GTK_CELL_AREA_BOX(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), GTK_TYPE_CELL_AREA_BOX, GtkCellAreaBox))
+#define GTK_CELL_AREA_BOX_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), GTK_TYPE_CELL_AREA_BOX, GtkCellAreaBoxClass))
+#define GTK_IS_CELL_AREA_BOX(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GTK_TYPE_CELL_AREA_BOX))
+#define GTK_IS_CELL_AREA_BOX_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GTK_TYPE_CELL_AREA_BOX))
+#define GTK_CELL_AREA_BOX_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), GTK_TYPE_CELL_AREA_BOX, GtkCellAreaBoxClass))
+
+typedef struct _GtkCellAreaBox GtkCellAreaBox;
+typedef struct _GtkCellAreaBoxClass GtkCellAreaBoxClass;
+typedef struct _GtkCellAreaBoxPrivate GtkCellAreaBoxPrivate;
+
+struct _GtkCellAreaBox
+{
+ GtkCellArea parent_instance;
+
+ GtkCellAreaBoxPrivate *priv;
+};
+
+struct _GtkCellAreaBoxClass
+{
+ GtkCellAreaClass parent_class;
+
+
+ /* Padding for future expansion */
+ void (*_gtk_reserved1) (void);
+ void (*_gtk_reserved2) (void);
+ void (*_gtk_reserved3) (void);
+ void (*_gtk_reserved4) (void);
+};
+
+GType gtk_cell_area_box_get_type (void) G_GNUC_CONST;
+
+
+
+G_END_DECLS
+
+#endif /* __GTK_CELL_AREA_BOX_H__ */