[libgda] GdaBrowser: use the new PopupContainer widget whenever possible



commit e656c13f810d9c8a3cfaca6e9446d51e77c6e8aa
Author: Vivien Malerba <malerba gnome-db org>
Date:   Sun Aug 16 15:32:11 2009 +0200

    GdaBrowser: use the new PopupContainer widget whenever possible

 tools/browser/popup-container.c                  |   64 ++++++++-
 tools/browser/popup-container.h                  |    3 +-
 tools/browser/schema-browser/objects-index.c     |   35 +-----
 tools/browser/schema-browser/relations-diagram.c |  174 ++--------------------
 4 files changed, 74 insertions(+), 202 deletions(-)
---
diff --git a/tools/browser/popup-container.c b/tools/browser/popup-container.c
index 50025e8..cda8573 100644
--- a/tools/browser/popup-container.c
+++ b/tools/browser/popup-container.c
@@ -34,6 +34,7 @@ static void popup_container_init       (PopupContainer *container,
 				       PopupContainerClass *klass);
 static void popup_container_dispose   (GObject *object);
 static void popup_container_show   (GtkWidget *widget);
+static void popup_container_hide   (GtkWidget *widget);
 
 static GObjectClass *parent_class = NULL;
 
@@ -51,6 +52,7 @@ popup_container_class_init (PopupContainerClass *klass)
 
 	object_class->dispose = popup_container_dispose;
 	widget_class->show = popup_container_show;
+	widget_class->hide = popup_container_hide;
 }
 
 static gboolean
@@ -217,6 +219,13 @@ popup_container_show (GtkWidget *widget)
                               gtk_get_current_event_time ());
 }
 
+static void
+popup_container_hide (GtkWidget *widget)
+{
+	GTK_WIDGET_CLASS (parent_class)->hide (widget);
+	gtk_grab_remove (widget);
+}
+
 GType
 popup_container_get_type (void)
 {
@@ -240,15 +249,64 @@ popup_container_get_type (void)
 	return type;
 }
 
+static void
+popup_position (PopupContainer *container, gint *out_x, gint *out_y)
+{
+	GtkWidget *button;
+	button = g_object_get_data (G_OBJECT (container), "__poswidget");
+
+	gint x, y;
+        gint bwidth, bheight;
+        GtkRequisition req;
+
+        gtk_widget_size_request (button, &req);
+
+        gdk_window_get_origin (button->window, &x, &y);
+
+        x += button->allocation.x;
+        y += button->allocation.y;
+        bwidth = button->allocation.width;
+        bheight = button->allocation.height;
+
+        x += bwidth - req.width;
+        y += bheight;
+
+        if (x < 0)
+                x = 0;
+
+        if (y < 0)
+                y = 0;
+
+	*out_x = x;
+	*out_y = y;
+}
+
 /**
- * popup_container_new
- *
+ * popup_container_new_with_func
  *
+ * Returns:
+ */
+GtkWidget *
+popup_container_new (GtkWidget *position_widget)
+{
+	PopupContainer *container;
+	g_return_val_if_fail (GTK_IS_WIDGET (position_widget), NULL);
+	
+	container = POPUP_CONTAINER (g_object_new (POPUP_CONTAINER_TYPE, "type", GTK_WINDOW_POPUP,
+						   NULL));
+	g_object_set_data (G_OBJECT (container), "__poswidget", position_widget);
+	container->priv->position_func = popup_position;
+	return (GtkWidget*) container;
+}
+
+
+/**
+ * popup_container_new_with_func
  *
  * Returns:
  */
 GtkWidget *
-popup_container_new (PopupContainerPositionFunc pos_func)
+popup_container_new_with_func (PopupContainerPositionFunc pos_func)
 {
 	PopupContainer *container;
 
diff --git a/tools/browser/popup-container.h b/tools/browser/popup-container.h
index ba917fc..836225b 100644
--- a/tools/browser/popup-container.h
+++ b/tools/browser/popup-container.h
@@ -49,7 +49,8 @@ struct _PopupContainerClass {
 };
 
 GType                  popup_container_get_type (void) G_GNUC_CONST;
-GtkWidget             *popup_container_new      (PopupContainerPositionFunc pos_func);
+GtkWidget             *popup_container_new (GtkWidget *position_widget);
+GtkWidget             *popup_container_new_with_func (PopupContainerPositionFunc pos_func);
 
 G_END_DECLS
 
diff --git a/tools/browser/schema-browser/objects-index.c b/tools/browser/schema-browser/objects-index.c
index 05e6ca0..772f44c 100644
--- a/tools/browser/schema-browser/objects-index.c
+++ b/tools/browser/schema-browser/objects-index.c
@@ -294,45 +294,12 @@ add_to_schema_data (ObjectsIndex *index, SchemaData *sd, GdaMetaDbObject *dbo)
 	gtk_text_buffer_insert (index->priv->tbuffer, &iter, " ", -1);
 }
 
-static void popup_position (PopupContainer *container, gint *out_x, gint *out_y);
 static gboolean key_press_event (GtkWidget *text_view, GdkEventKey *event, ObjectsIndex *index);
 static gboolean event_after (GtkWidget *text_view, GdkEvent *ev, ObjectsIndex *index);
 static gboolean motion_notify_event (GtkWidget *text_view, GdkEventMotion *event, ObjectsIndex *index);
 static gboolean visibility_notify_event (GtkWidget *text_view, GdkEventVisibility *event, ObjectsIndex *index);
 
 static void
-popup_position (PopupContainer *container, gint *out_x, gint *out_y)
-{
-	GtkWidget *button;
-	button = g_object_get_data (G_OBJECT (container), "button");
-
-	gint x, y;
-        gint bwidth, bheight;
-        GtkRequisition req;
-
-        gtk_widget_size_request (button, &req);
-
-        gdk_window_get_origin (button->window, &x, &y);
-
-        x += button->allocation.x;
-        y += button->allocation.y;
-        bwidth = button->allocation.width;
-        bheight = button->allocation.height;
-
-        x += bwidth - req.width;
-        y += bheight;
-
-        if (x < 0)
-                x = 0;
-
-        if (y < 0)
-                y = 0;
-
-	*out_x = x;
-	*out_y = y;
-}
-
-static void
 text_tag_table_foreach_cb (GtkTextTag *tag, const gchar *find)
 {
 	const gchar *name;
@@ -422,7 +389,7 @@ objects_index_new (BrowserConnection *bcnc)
 	g_object_set (G_OBJECT (wid), "label", NULL, NULL);
 	
 	GtkWidget *popup;
-	popup = popup_container_new (popup_position);
+	popup = popup_container_new (wid);
 	index->priv->popup_container = popup;
 	g_signal_connect_swapped (wid, "clicked",
 				  G_CALLBACK (gtk_widget_show), popup);
diff --git a/tools/browser/schema-browser/relations-diagram.c b/tools/browser/schema-browser/relations-diagram.c
index d367698..9e2facd 100644
--- a/tools/browser/schema-browser/relations-diagram.c
+++ b/tools/browser/schema-browser/relations-diagram.c
@@ -28,6 +28,7 @@
 #include "../cc-gray-bar.h"
 #include "../canvas/browser-canvas-db-relations.h"
 #include <gdk/gdkkeysyms.h>
+#include "../popup-container.h"
 
 struct _RelationsDiagramPrivate {
 	BrowserConnection *bcnc;
@@ -37,7 +38,7 @@ struct _RelationsDiagramPrivate {
 	GtkWidget *canvas;
 	GtkWidget *save_button;
 
-	GtkWidget *window; /* to enter canvas's name */
+	GtkWidget *popup_container; /* to enter canvas's name */
 	GtkWidget *name_entry;
 	GtkWidget *real_save_button;
 };
@@ -95,7 +96,7 @@ relations_diagram_init (RelationsDiagram *diagram, RelationsDiagramClass *klass)
 {
 	diagram->priv = g_new0 (RelationsDiagramPrivate, 1);
 	diagram->priv->fav_id = -1;
-	diagram->priv->window = NULL;
+	diagram->priv->popup_container = NULL;
 }
 
 static void
@@ -111,8 +112,8 @@ relations_diagram_dispose (GObject *object)
 			g_object_unref (diagram->priv->bcnc);
 		}
 
-		if (diagram->priv->window)
-			gtk_widget_destroy (diagram->priv->window);
+		if (diagram->priv->popup_container)
+			gtk_widget_destroy (diagram->priv->popup_container);
 
 		g_free (diagram->priv);
 		diagram->priv = NULL;
@@ -173,107 +174,10 @@ meta_changed_cb (BrowserConnection *bcnc, GdaMetaStruct *mstruct, RelationsDiagr
 	g_object_set (G_OBJECT (diagram->priv->canvas), "meta-struct", mstruct, NULL);
 }
 
-
 /*
  * POPUP
  */
 static void
-position_popup (RelationsDiagram *diagram)
-{
-        gint x, y;
-        gint bwidth, bheight;
-        GtkRequisition req;
-
-        gtk_widget_size_request (diagram->priv->window, &req);
-
-        gdk_window_get_origin (diagram->priv->save_button->window, &x, &y);
-
-        x += diagram->priv->save_button->allocation.x;
-        y += diagram->priv->save_button->allocation.y;
-        bwidth = diagram->priv->save_button->allocation.width;
-        bheight = diagram->priv->save_button->allocation.height;
-
-        x += bwidth - req.width;
-        y += bheight;
-
-        if (x < 0)
-                x = 0;
-
-        if (y < 0)
-                y = 0;
-
-        gtk_window_move (GTK_WINDOW (diagram->priv->window), x, y);
-}
-
-
-
-static gboolean
-popup_grab_on_window (GdkWindow *window, guint32 activate_time)
-{
-        if ((gdk_pointer_grab (window, TRUE,
-                               GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK |
-                               GDK_POINTER_MOTION_MASK,
-                               NULL, NULL, activate_time) == 0)) {
-                if (gdk_keyboard_grab (window, TRUE,
-                                       activate_time) == 0)
-                        return TRUE;
-                else {
-                        gdk_pointer_ungrab (activate_time);
-                        return FALSE;
-                }
-        }
-        return FALSE;
-}
-
-
-static gboolean
-delete_popup (GtkWidget *widget, RelationsDiagram *diagram)
-{
-	gtk_widget_hide (diagram->priv->window);
-        gtk_grab_remove (diagram->priv->window);
-	return TRUE;
-}
-
-static gboolean
-key_press_popup (GtkWidget *widget, GdkEventKey *event, RelationsDiagram *diagram)
-{
-	if (event->keyval != GDK_Escape)
-                return FALSE;
-
-        g_signal_stop_emission_by_name (widget, "key_press_event");
-	gtk_widget_hide (diagram->priv->window);
-        gtk_grab_remove (diagram->priv->window);
-        return TRUE;
-}
-
-static gboolean
-button_press_popup (GtkWidget *widget, GdkEventButton *event, RelationsDiagram *diagram)
-{
-	GtkWidget *child;
-
-        child = gtk_get_event_widget ((GdkEvent *) event);
-
-        /* We don't ask for button press events on the grab widget, so
-         *  if an event is reported directly to the grab widget, it must
-         *  be on a window outside the application (and thus we remove
-         *  the popup window). Otherwise, we check if the widget is a child
-         *  of the grab widget, and only remove the popup window if it
-         *  is not.
-         */
-        if (child != widget) {
-                while (child) {
-                        if (child == widget)
-                                return FALSE;
-                        child = child->parent;
-                }
-        }
-	gtk_widget_hide (diagram->priv->window);
-        gtk_grab_remove (diagram->priv->window);
-        return TRUE;
-}
-
-
-static void
 real_save_clicked_cb (GtkWidget *button, RelationsDiagram *diagram)
 {
 	gchar *str;
@@ -294,8 +198,7 @@ real_save_clicked_cb (GtkWidget *button, RelationsDiagram *diagram)
 	}
 	fav.contents = str;
 	
-	gtk_widget_hide (diagram->priv->window);
-	gtk_grab_remove (diagram->priv->window);
+	gtk_widget_hide (diagram->priv->popup_container);
 	
 	bfav = browser_connection_get_favorites (diagram->priv->bcnc);
 	if (! browser_favorites_add (bfav, 0, &fav, ORDER_KEY_SCHEMA, G_MAXINT, &lerror)) {
@@ -318,20 +221,11 @@ save_clicked_cb (GtkWidget *button, RelationsDiagram *diagram)
 {
 	gchar *str;
 
-	if (!diagram->priv->window) {
+	if (!diagram->priv->popup_container) {
 		GtkWidget *window, *wid, *hbox;
 
-		window = gtk_window_new (GTK_WINDOW_POPUP);
-		gtk_widget_set_events (window, gtk_widget_get_events (window) | GDK_KEY_PRESS_MASK);
-		gtk_window_set_resizable (GTK_WINDOW (window), FALSE);
-		gtk_container_set_border_width (GTK_CONTAINER (window), 5);
-		g_signal_connect (G_OBJECT (window), "delete_event",
-				  G_CALLBACK (delete_popup), diagram);
-		g_signal_connect (G_OBJECT (window), "key_press_event",
-				  G_CALLBACK (key_press_popup), diagram);
-		g_signal_connect (G_OBJECT (window), "button_press_event",
-				  G_CALLBACK (button_press_popup), diagram);
-		diagram->priv->window = window;
+		window = popup_container_new (button);
+		diagram->priv->popup_container = window;
 
 		hbox = gtk_hbox_new (FALSE, 0);
 		gtk_container_add (GTK_CONTAINER (window), hbox);
@@ -365,55 +259,7 @@ save_clicked_cb (GtkWidget *button, RelationsDiagram *diagram)
 		gtk_widget_show_all (hbox);
 	}
 
-	if (!popup_grab_on_window (button->window, gtk_get_current_event_time ()))
-                return;
-	position_popup (diagram);
-	gtk_grab_add (diagram->priv->window);
-        gtk_widget_show (diagram->priv->window);
-
-	GdkScreen *screen;
-	gint swidth, sheight;
-	gint root_x, root_y;
-	gint wwidth, wheight;
-	gboolean do_move = FALSE;
-	screen = gtk_window_get_screen (GTK_WINDOW (diagram->priv->window));
-	if (screen) {
-		swidth = gdk_screen_get_width (screen);
-		sheight = gdk_screen_get_height (screen);
-	}
-	else {
-		swidth = gdk_screen_width ();
-		sheight = gdk_screen_height ();
-	}
-	gtk_window_get_position (GTK_WINDOW (diagram->priv->window), &root_x, &root_y);
-	gtk_window_get_size (GTK_WINDOW (diagram->priv->window), &wwidth, &wheight);
-	if (root_x + wwidth > swidth) {
-		do_move = TRUE;
-		root_x = swidth - wwidth;
-	}
-	else if (root_x < 0) {
-		do_move = TRUE;
-		root_x = 0;
-	}
-	if (root_y + wheight > sheight) {
-		do_move = TRUE;
-		root_y = sheight - wheight;
-	}
-	else if (root_y < 0) {
-		do_move = TRUE;
-		root_y = 0;
-	}
-	if (do_move)
-		gtk_window_move (GTK_WINDOW (diagram->priv->window), root_x, root_y);
-
-	str = gtk_editable_get_chars (GTK_EDITABLE (diagram->priv->name_entry), 0, -1);
-	if (!*str)
-		gtk_widget_grab_focus (diagram->priv->name_entry);
-	else
-		gtk_widget_grab_focus (diagram->priv->real_save_button);
-	g_free (str);
-        popup_grab_on_window (diagram->priv->window->window,
-                              gtk_get_current_event_time ());
+        gtk_widget_show (diagram->priv->popup_container);
 }
 
 



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