[libgda] Correctly handle GdaHolder with NULL initial type if forms



commit 177c6c3461211a47de62b8feb7f5342d3ecd0786
Author: Vivien Malerba <malerba gnome-db org>
Date:   Sun Jul 18 18:51:06 2010 +0200

    Correctly handle GdaHolder with NULL initial type if forms
    
    where the GdaHolder's type is only known when some data is assigned
    to it

 libgda-ui/gdaui-basic-form.c |   25 +++++++++++++++++++++++++
 libgda-ui/gdaui-init.c       |    7 ++++---
 libgda/gda-holder.c          |    4 +++-
 libgda/gda-set.c             |   42 ++++++++++++++++++++++++++++++++++++++++++
 libgda/gda-set.h             |    2 +-
 5 files changed, 75 insertions(+), 5 deletions(-)
---
diff --git a/libgda-ui/gdaui-basic-form.c b/libgda-ui/gdaui-basic-form.c
index 7f9a870..eded78e 100644
--- a/libgda-ui/gdaui-basic-form.c
+++ b/libgda-ui/gdaui-basic-form.c
@@ -107,6 +107,8 @@ static void get_rid_of_set (GdaSet *paramlist, GdauiBasicForm *form);
 static void paramlist_public_data_changed_cb (GdauiSet *paramlist, GdauiBasicForm *form);
 static void paramlist_param_attr_changed_cb (GdaSet *paramlist, GdaHolder *param,
 					     const gchar *att_name, const GValue *att_value, GdauiBasicForm *form);
+static void paramlist_holder_type_set_cb (GdaSet *paramlist, GdaHolder *param,
+					  GdauiBasicForm *form);
 
 static void entry_contents_modified (GdauiDataEntry *entry, SingleEntry *sentry);
 static void entry_expand_changed_cb (GdauiDataEntry *entry, SingleEntry *sentry);
@@ -352,6 +354,9 @@ get_rid_of_set (GdaSet *paramlist, GdauiBasicForm *form)
 	g_signal_handlers_disconnect_by_func (paramlist,
 					      G_CALLBACK (paramlist_param_attr_changed_cb), form);
 
+	g_signal_handlers_disconnect_by_func (paramlist,
+					      G_CALLBACK (paramlist_holder_type_set_cb), form);
+
 	g_object_unref (form->priv->set);
 	form->priv->set = NULL;
 
@@ -366,6 +371,24 @@ get_rid_of_set (GdaSet *paramlist, GdauiBasicForm *form)
 }
 
 static void
+paramlist_holder_type_set_cb (GdaSet *paramlist, GdaHolder *param,
+			      GdauiBasicForm *form)
+{
+	SingleEntry *sentry;
+
+	sentry = get_single_entry_for_holder (form, param);
+	if (sentry) {
+		create_entry_widget (sentry);
+		gdaui_data_entry_set_attributes (GDAUI_DATA_ENTRY (sentry->entry),
+						 form->priv->show_actions ? GDA_VALUE_ATTR_ACTIONS_SHOWN : 0,
+						 GDA_VALUE_ATTR_ACTIONS_SHOWN);
+		pack_entry_widget (sentry);
+		gdaui_basic_form_entry_set_visible (form, param, !sentry->hidden);
+	}
+}
+
+
+static void
 paramlist_public_data_changed_cb (GdauiSet *paramlist, GdauiBasicForm *form)
 {
 	/* here we want to re-define all the data entry widgets */
@@ -503,6 +526,8 @@ gdaui_basic_form_set_property (GObject *object,
 						  G_CALLBACK (paramlist_public_data_changed_cb), form);
 				g_signal_connect (form->priv->set, "holder-attr-changed",
 						  G_CALLBACK (paramlist_param_attr_changed_cb), form);
+				g_signal_connect (form->priv->set, "holder-type-set",
+						  G_CALLBACK (paramlist_holder_type_set_cb), form);
 
 				create_entries (form);
 				pack_entries_in_table (form);
diff --git a/libgda-ui/gdaui-init.c b/libgda-ui/gdaui-init.c
index 8870df7..49afa82 100644
--- a/libgda-ui/gdaui-init.c
+++ b/libgda-ui/gdaui-init.c
@@ -112,6 +112,9 @@ gdaui_new_data_entry (GType type, const gchar *plugin_name)
 	if (!gdaui_plugins_hash)
 		gdaui_plugins_hash = init_plugins_hash ();
 
+	if (type == G_TYPE_INVALID)
+		return (GdauiDataEntry *) gdaui_entry_none_new (GDA_TYPE_NULL);
+
 	dh = gda_get_default_handler (type);
 
 	if (plugin_name && *plugin_name) {
@@ -134,9 +137,7 @@ gdaui_new_data_entry (GType type, const gchar *plugin_name)
 	}
 
 	if (!entry) {
-		if (type == GDA_TYPE_NULL)
-			entry = (GdauiDataEntry *) gdaui_entry_none_new (GDA_TYPE_NULL);
-		else if (type == G_TYPE_STRING)
+		if (type == G_TYPE_STRING)
 			entry = (GdauiDataEntry *) gdaui_entry_string_new (dh, type, spec_options);
 		else if ((type == G_TYPE_INT64) ||
 			 (type == G_TYPE_UINT64) ||
diff --git a/libgda/gda-holder.c b/libgda/gda-holder.c
index 2d0f0e4..b26a1bc 100644
--- a/libgda/gda-holder.c
+++ b/libgda/gda-holder.c
@@ -1513,8 +1513,10 @@ bind_to_notify_cb (GdaHolder *bind_to, GParamSpec *pspec, GdaHolder *holder)
 	g_signal_handler_disconnect (holder->priv->simple_bind,
 				     holder->priv->simple_bind_notify_signal_id);
 	holder->priv->simple_bind_notify_signal_id = 0;
-	if (holder->priv->g_type == GDA_TYPE_NULL)
+	if (holder->priv->g_type == GDA_TYPE_NULL) {
 		holder->priv->g_type = bind_to->priv->g_type;
+		g_object_notify ((GObject*) holder, "g-type");
+	}
 	else if (holder->priv->g_type != bind_to->priv->g_type) {
 		/* break holder's binding because type differ */
 		g_warning (_("Cannot bind holders if their type is not the same, "
diff --git a/libgda/gda-set.c b/libgda/gda-set.c
index 430c4f3..de602bf 100644
--- a/libgda/gda-set.c
+++ b/libgda/gda-set.c
@@ -57,6 +57,8 @@ static void changed_holder_cb (GdaHolder *holder, GdaSet *dataset);
 static GError *validate_change_holder_cb (GdaHolder *holder, const GValue *value, GdaSet *dataset);
 static void source_changed_holder_cb (GdaHolder *holder, GdaSet *dataset);
 static void att_holder_changed_cb (GdaHolder *holder, const gchar *att_name, const GValue *att_value, GdaSet *dataset);
+static void holder_notify_cb (GdaHolder *holder, GParamSpec *pspec, GdaSet *dataset);
+
 
 static void compute_public_data (GdaSet *set);
 static gboolean gda_set_real_add_holder (GdaSet *set, GdaHolder *holder);
@@ -82,6 +84,7 @@ enum
 	HOLDER_ATTR_CHANGED,
 	VALIDATE_HOLDER_CHANGE,
 	VALIDATE_SET,
+	HOLDER_TYPE_SET,
 	LAST_SIGNAL
 };
 
@@ -311,11 +314,32 @@ gda_set_class_init (GdaSetClass *class)
 			      NULL, NULL,
 			      _gda_marshal_VOID__VOID, G_TYPE_NONE, 0);
 
+	/**
+	 * GdaSet::holder-type-set
+	 * @set: the #GdaSet
+	 * @holder: the #GdaHolder for which the #GType has been set
+	 *
+	 * Gets emitted when @holder in @set has its type finally set, in case
+	 * it was #GDA_TYPE_NULL
+	 *
+	 * Since: 4.2
+	 */
+	gda_set_signals[HOLDER_TYPE_SET] =
+		g_signal_new ("holder-type-set",
+			      G_TYPE_FROM_CLASS (object_class),
+			      G_SIGNAL_RUN_FIRST,
+			      G_STRUCT_OFFSET (GdaSetClass, holder_type_set),
+			      NULL, NULL,
+			      _gda_marshal_VOID__OBJECT, G_TYPE_NONE, 1,
+			      GDA_TYPE_HOLDER);
+
+
 	class->holder_changed = NULL;
 	class->validate_holder_change = m_validate_holder_change;
 	class->validate_set = m_validate_set;
 	class->holder_attr_changed = NULL;
 	class->public_data_changed = NULL;
+	class->holder_type_set = NULL;
 
 	/* Properties */
 	object_class->set_property = gda_set_set_property;
@@ -933,6 +957,9 @@ gda_set_remove_holder (GdaSet *set, GdaHolder *holder)
 		g_signal_handlers_disconnect_by_func (G_OBJECT (holder),
 						      G_CALLBACK (att_holder_changed_cb), set);
 	}
+	if (gda_holder_get_g_type (holder) == GDA_TYPE_NULL)
+		g_signal_handlers_disconnect_by_func (holder,
+						      G_CALLBACK (holder_notify_cb), set);
 
 	/* now destroy the GdaSetNode and the GdaSetSource if necessary */
 	node = gda_set_get_node (set, holder);
@@ -1203,6 +1230,17 @@ gda_set_add_holder (GdaSet *set, GdaHolder *holder)
 	return added;
 }
 
+static void
+holder_notify_cb (GdaHolder *holder, GParamSpec *pspec, GdaSet *dataset)
+{
+	GType gtype;
+	gtype = gda_holder_get_g_type (holder);
+	g_assert (gtype != GDA_TYPE_NULL);
+	g_signal_handlers_disconnect_by_func (holder,
+					      G_CALLBACK (holder_notify_cb), dataset);
+	g_signal_emit (dataset, gda_set_signals[HOLDER_TYPE_SET], 0, holder);
+}
+
 static gboolean
 gda_set_real_add_holder (GdaSet *set, GdaHolder *holder)
 {
@@ -1239,6 +1277,10 @@ gda_set_real_add_holder (GdaSet *set, GdaHolder *holder)
 			g_signal_connect (G_OBJECT (holder), "attribute-changed",
 					  G_CALLBACK (att_holder_changed_cb), set);
 		}
+		if (gda_holder_get_g_type (holder) == GDA_TYPE_NULL)
+			g_signal_connect (G_OBJECT (holder), "notify::g-type",
+					  G_CALLBACK (holder_notify_cb), set);
+
 		return TRUE;
 	}
 	else if (similar == holder)
diff --git a/libgda/gda-set.h b/libgda/gda-set.h
index ad96d33..4b649d6 100644
--- a/libgda/gda-set.h
+++ b/libgda/gda-set.h
@@ -103,10 +103,10 @@ struct _GdaSetClass
 	void                  (*holder_attr_changed)   (GdaSet *set, GdaHolder *holder, 
 							const gchar *attr_name, const GValue *attr_value);
 	void                  (*public_data_changed)   (GdaSet *set);
+	void                  (*holder_type_set)       (GdaSet *set, GdaHolder *holder);
 
 	/*< private >*/
 	/* Padding for future expansion */
-	void (*_gda_reserved1) (void);
 	void (*_gda_reserved2) (void);
 	void (*_gda_reserved3) (void);
 	void (*_gda_reserved4) (void);



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]