[glade3] * gladeui/glade-palette.[ch], gladeui/glade-project.[ch], gladeui/glade-app.[ch], src/glade-wind



commit 78097b2f3bcc96709f17bd914a93c8f162152e67
Author: Tristan Van Berkom <tristan van berkom gmail com>
Date:   Tue Jan 4 16:06:04 2011 +0900

    	* gladeui/glade-palette.[ch], gladeui/glade-project.[ch], gladeui/glade-app.[ch],
    	  src/glade-window.c:
    	  - Removed glade_app_get_palette()
    	  - Moved "pointer-mode" property from GladeApp to GladeProject
    	  - Palette now in charge of driving pointer mode on the project it's registered to
    	  - GladeWindow now watches/sets the pointer mode on the currently set project (with
    	    its "selector" and "drag/resize" toolbuttons).

 ChangeLog                   |   10 +
 gladeui/glade-app.c         |  180 --------
 gladeui/glade-app.h         |   51 +--
 gladeui/glade-cursor.c      |   38 +-
 gladeui/glade-cursor.h      |    6 +-
 gladeui/glade-fixed.c       |   36 +-
 gladeui/glade-palette.c     | 1006 ++++++++++++++++++++-----------------------
 gladeui/glade-palette.h     |   11 +-
 gladeui/glade-placeholder.c |   26 +-
 gladeui/glade-popup.c       |   68 ++--
 gladeui/glade-project.c     |  205 +++++++---
 gladeui/glade-project.h     |  279 ++++++------
 src/glade-window.c          |  140 ++++---
 13 files changed, 960 insertions(+), 1096 deletions(-)
---
diff --git a/ChangeLog b/ChangeLog
index b535d62..352fac1 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,13 @@
+2011-01-04  Tristan Van Berkom <tristanvb openismus com>
+
+	* gladeui/glade-palette.[ch], gladeui/glade-project.[ch], gladeui/glade-app.[ch],
+	  src/glade-window.c:
+	  - Removed glade_app_get_palette()
+	  - Moved "pointer-mode" property from GladeApp to GladeProject
+	  - Palette now in charge of driving pointer mode on the project it's registered to
+	  - GladeWindow now watches/sets the pointer mode on the currently set project (with
+	    its "selector" and "drag/resize" toolbuttons).
+
 2011-01-03  Tristan Van Berkom <tristanvb openismus com>
 
 	* gladeui/glade-app.[ch]:
diff --git a/gladeui/glade-app.c b/gladeui/glade-app.c
index 48874a2..7995270 100644
--- a/gladeui/glade-app.c
+++ b/gladeui/glade-app.c
@@ -62,17 +62,10 @@ enum
   LAST_SIGNAL
 };
 
-enum
-{
-  PROP_0,
-  PROP_POINTER_MODE
-};
-
 struct _GladeAppPrivate
 {
   GtkWidget *window;
 
-  GladePalette *palette;        /* See glade-palette */
   GladeClipboard *clipboard;    /* See glade-clipboard */
   GList *catalogs;              /* See glade-catalog */
 
@@ -85,8 +78,6 @@ struct _GladeAppPrivate
                                  * GladeWidgets.
                                  */
   GtkAccelGroup *accel_group;   /* Default acceleration group for this app */
-
-  GladePointerMode pointer_mode;        /* Current mode for the pointer in the workspace */
 };
 
 static guint glade_app_signals[LAST_SIGNAL] = { 0 };
@@ -105,26 +96,6 @@ static void glade_init_check (void);
 
 G_DEFINE_TYPE (GladeApp, glade_app, G_TYPE_OBJECT);
 
-
-GType
-glade_pointer_mode_get_type (void)
-{
-  static GType etype = 0;
-
-  if (etype == 0)
-    {
-      static const GEnumValue values[] = {
-        {GLADE_POINTER_SELECT, "select", "Select widgets"},
-        {GLADE_POINTER_ADD_WIDGET, "add", "Add widgets"},
-        {GLADE_POINTER_DRAG_RESIZE, "drag-resize", "Drag and resize widgets"},
-        {0, NULL, NULL}
-      };
-      etype = g_enum_register_static ("GladePointerMode", values);
-    }
-  return etype;
-}
-
-
 /*****************************************************************
  *                    GObjectClass                               *
  *****************************************************************/
@@ -158,11 +129,6 @@ glade_app_dispose (GObject * app)
 {
   GladeAppPrivate *priv = GLADE_APP_GET_PRIVATE (app);
 
-  if (priv->palette)
-    {
-      g_object_unref (priv->palette);
-      priv->palette = NULL;
-    }
   if (priv->clipboard)
     {
       g_object_unref (priv->clipboard);
@@ -194,40 +160,6 @@ glade_app_finalize (GObject * app)
   G_OBJECT_CLASS (glade_app_parent_class)->finalize (app);
 }
 
-static void
-glade_app_set_property (GObject * object,
-                        guint property_id,
-                        const GValue * value, GParamSpec * pspec)
-{
-  switch (property_id)
-    {
-      case PROP_POINTER_MODE:
-        glade_app_set_pointer_mode (g_value_get_enum (value));
-        break;
-      default:
-        G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
-        break;
-    }
-}
-
-static void
-glade_app_get_property (GObject * object,
-                        guint property_id, GValue * value, GParamSpec * pspec)
-{
-  GladeApp *app = GLADE_APP (object);
-
-
-  switch (property_id)
-    {
-      case PROP_POINTER_MODE:
-        g_value_set_enum (value, app->priv->pointer_mode);
-        break;
-      default:
-        G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
-        break;
-    }
-}
-
 /*****************************************************************
  *                    GladeAppClass                              *
  *****************************************************************/
@@ -373,10 +305,6 @@ glade_app_init (GladeApp * app)
   /* Initialize app objects */
   app->priv->catalogs = (GList *) glade_catalog_load_all ();
 
-  /* Create palette */
-  app->priv->palette = (GladePalette *) glade_palette_new (app->priv->catalogs);
-  g_object_ref_sink (app->priv->palette);
-
   /* Create clipboard */
   app->priv->clipboard = glade_clipboard_new ();
 
@@ -394,12 +322,8 @@ glade_app_class_init (GladeAppClass * klass)
   object_class->constructor = glade_app_constructor;
   object_class->dispose = glade_app_dispose;
   object_class->finalize = glade_app_finalize;
-  object_class->get_property = glade_app_get_property;
-  object_class->set_property = glade_app_set_property;
 
   klass->signal_editor_created = glade_app_signal_editor_created_default;
-  klass->show_properties = NULL;
-  klass->hide_properties = NULL;
 
   /**
    * GladeApp::signal-editor-created:
@@ -438,13 +362,6 @@ glade_app_class_init (GladeAppClass * klass)
                     G_TYPE_NONE, 3,
                     G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING);
 
-  g_object_class_install_property
-      (object_class, PROP_POINTER_MODE,
-       g_param_spec_enum
-       ("pointer-mode", _("Pointer Mode"),
-        _("Current mode for the pointer in the workspace"),
-        GLADE_TYPE_POINTER_MODE, GLADE_POINTER_SELECT, G_PARAM_READWRITE));
-
   g_type_class_add_private (klass, sizeof (GladeAppPrivate));
 }
 
@@ -654,13 +571,6 @@ glade_app_get_window (void)
   return app->priv->window;
 }
 
-GladePalette *
-glade_app_get_palette (void)
-{
-  GladeApp *app = glade_app_get ();
-  return app->priv->palette;
-}
-
 GladeClipboard *
 glade_app_get_clipboard (void)
 {
@@ -746,34 +656,9 @@ glade_app_get_project_by_path (const gchar * project_path)
 }
 
 void
-glade_app_show_properties (gboolean raise)
-{
-  GladeApp *app = glade_app_get ();
-
-  if (GLADE_APP_GET_CLASS (app)->show_properties)
-    GLADE_APP_GET_CLASS (app)->show_properties (app, raise);
-  else
-    g_critical ("%s not implemented\n", G_STRFUNC);
-}
-
-void
-glade_app_hide_properties (void)
-{
-  GladeApp *app = glade_app_get ();
-
-  if (GLADE_APP_GET_CLASS (app)->hide_properties)
-    GLADE_APP_GET_CLASS (app)->hide_properties (app);
-  else
-    g_critical ("%s not implemented\n", G_STRFUNC);
-
-}
-
-void
 glade_app_add_project (GladeProject * project)
 {
   GladeApp *app;
-  GladeDesignView *view;
-  GladeDesignLayout *layout;
 
   g_return_if_fail (GLADE_IS_PROJECT (project));
 
@@ -785,31 +670,6 @@ glade_app_add_project (GladeProject * project)
 
   /* Take a reference for GladeApp here... */
   app->priv->projects = g_list_append (app->priv->projects, g_object_ref (project));
-
-  /* Select the first window in the project */
-  if (g_list_length (app->priv->projects) == 1 ||
-      !(view = glade_design_view_get_from_project (project)) ||
-      !(layout = glade_design_view_get_layout (view)) ||
-      !gtk_bin_get_child (GTK_BIN (layout)))
-    {
-      const GList *node;
-      for (node = glade_project_get_objects (project);
-           node != NULL; node = g_list_next (node))
-        {
-          GObject *obj = G_OBJECT (node->data);
-
-          if (GTK_IS_WIDGET (obj) &&
-              gtk_widget_get_has_window (GTK_WIDGET (obj)))
-            {
-              glade_project_selection_set (project, obj, TRUE);
-              glade_widget_show (glade_widget_get_from_gobject (obj));
-              break;
-            }
-        }
-    }
-
-  /* XXX I think the palette & editor should detect this by itself */
-  gtk_widget_set_sensitive (GTK_WIDGET (app->priv->palette), TRUE);
 }
 
 void
@@ -822,14 +682,6 @@ glade_app_remove_project (GladeProject * project)
 
   app->priv->projects = g_list_remove (app->priv->projects, project);
 
-  /* If no more projects */
-  if (app->priv->projects == NULL)
-    {
-      /* XXX I think the palette & editor should detect this. */
-      gtk_widget_set_sensitive (GTK_WIDGET (app->priv->palette), FALSE);
-
-    }
-
   /* Its safe to just release the project as the project emits a
    * "close" signal and everyone is responsable for cleaning up at
    * that point.
@@ -837,38 +689,6 @@ glade_app_remove_project (GladeProject * project)
   g_object_unref (project);
 }
 
-/**
- * glade_app_set_pointer_mode:
- * @mode: A #GladePointerMode
- *
- * Sets the #GladePointerMode
- */
-void
-glade_app_set_pointer_mode (GladePointerMode mode)
-{
-  GladeApp *app = glade_app_get ();
-
-  app->priv->pointer_mode = mode;
-
-  g_object_notify (G_OBJECT (app), "pointer-mode");
-}
-
-
-/**
- * glade_app_get_pointer_mode:
- *
- * Gets the current #GladePointerMode
- * 
- * Returns: The #GladePointerMode
- */
-GladePointerMode
-glade_app_get_pointer_mode (void)
-{
-  GladeApp *app = glade_app_get ();
-
-  return app->priv->pointer_mode;
-}
-
 /*
  * glade_app_set_accel_group:
  *
diff --git a/gladeui/glade-app.h b/gladeui/glade-app.h
index af7a905..e741b60 100644
--- a/gladeui/glade-app.h
+++ b/gladeui/glade-app.h
@@ -36,8 +36,6 @@ G_BEGIN_DECLS
 #define GLADE_IS_APP_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GLADE_TYPE_APP))
 #define GLADE_APP_GET_CLASS(o)    (G_TYPE_INSTANCE_GET_CLASS ((o), GLADE_APP, GladeAppClass))
 
-#define GLADE_TYPE_POINTER_MODE   (glade_pointer_mode_get_type())
-
 #define GLADE_ENV_CATALOG_PATH    "GLADE_CATALOG_PATH"
 #define GLADE_ENV_MODULE_PATH     "GLADE_MODULE_PATH"
 
@@ -45,42 +43,19 @@ typedef struct _GladeApp         GladeApp;
 typedef struct _GladeAppPrivate  GladeAppPrivate;
 typedef struct _GladeAppClass    GladeAppClass;
 
-/**
- * GladePointerMode:
- * @GLADE_POINTER_SELECT:      Mouse pointer used for selecting widgets
- * @GLADE_POINTER_ADD_WIDGET:  Mouse pointer used for adding widgets
- * @GLADE_POINTER_DRAG_RESIZE: Mouse pointer used for dragging and 
- *                             resizing widgets in containers
- *
- * Indicates what the pointer is used for in the workspace.
- */
-enum _GladePointerMode
-{
-	GLADE_POINTER_SELECT = 0,
-	GLADE_POINTER_ADD_WIDGET,
-	GLADE_POINTER_DRAG_RESIZE
-};
-typedef enum _GladePointerMode GladePointerMode;
-
-
 struct _GladeApp
 {
-	GObject parent_instance;
-	
-	GladeAppPrivate *priv;
+  GObject parent_instance;
+
+  GladeAppPrivate *priv;
 };
 
 struct _GladeAppClass
 {
-	GObjectClass parent_class;
-	
-	/* class methods */
-	void   (*  show_properties) (GladeApp* app,
-				     gboolean  raise);
-	void   (*  hide_properties) (GladeApp* app);
-
-	/* signals */
-	void   (*  signal_editor_created) (GladeApp *app, GladeSignalEditor *signal_editor);
+  GObjectClass parent_class;
+
+  /* signals */
+  void   (*  signal_editor_created) (GladeApp *app, GladeSignalEditor *signal_editor);
 };
 
  
@@ -88,8 +63,6 @@ GType              glade_app_get_type   (void) G_GNUC_CONST;
 
 GladeApp*          glade_app_new        (void);
 
-GType              glade_pointer_mode_get_type (void) G_GNUC_CONST;
-
 GladeApp*          glade_app_get        (void);
 
 void               glade_app_set_window (GtkWidget *window);
@@ -102,14 +75,8 @@ GList             *glade_app_get_catalogs (void);
 
 GladeCatalog      *glade_app_get_catalog (const gchar *name);
 
-GladePalette*      glade_app_get_palette (void);
-
 GladeClipboard*    glade_app_get_clipboard (void);
 
-GladePointerMode   glade_app_get_pointer_mode (void);
- 
-void               glade_app_set_pointer_mode (GladePointerMode mode);
-
 void               glade_app_add_project (GladeProject *project);
  
 void               glade_app_remove_project (GladeProject *project);
@@ -122,10 +89,6 @@ gboolean           glade_app_is_project_loaded (const gchar *project_path);
  
 GladeProject*      glade_app_get_project_by_path (const gchar *project_path);
  
-void               glade_app_show_properties (gboolean raise);
- 
-void               glade_app_hide_properties (void);
- 
 gint               glade_app_config_save (void);
  
 void               glade_app_set_transient_parent (GtkWindow *parent);
diff --git a/gladeui/glade-cursor.c b/gladeui/glade-cursor.c
index 647efdd..1cdf43e 100644
--- a/gladeui/glade-cursor.c
+++ b/gladeui/glade-cursor.c
@@ -55,29 +55,22 @@ set_cursor_recurse (GtkWidget * widget, GdkCursor * gdk_cursor)
     }
 }
 
-
 static void
-set_cursor (GdkCursor * gdk_cursor)
+set_cursor (GladeProject *project,
+	    GdkCursor    *gdk_cursor)
 {
-  GladeProject *project;
-  GList *list, *projects;
+  GList *list;
 
-  for (projects = glade_app_get_projects ();
-       projects; projects = projects->next)
+  for (list = (GList *) glade_project_get_objects (project);
+       list; list = list->next)
     {
-      project = projects->data;
-
-      for (list = (GList *) glade_project_get_objects (project);
-           list; list = list->next)
-        {
-          GObject *object = list->data;
+      GObject *object = list->data;
 
-          if (GTK_IS_WIDGET (object) &&
-              gtk_widget_get_has_window (GTK_WIDGET (object)))
-            {
-              set_cursor_recurse (GTK_WIDGET (object), gdk_cursor);
-            }
-        }
+      if (GTK_IS_WIDGET (object) &&
+	  gtk_widget_get_has_window (GTK_WIDGET (object)))
+	{
+	  set_cursor_recurse (GTK_WIDGET (object), gdk_cursor);
+	}
     }
 }
 
@@ -90,7 +83,9 @@ set_cursor (GdkCursor * gdk_cursor)
  * (also sets the cursor on all visible project widgets)
  */
 void
-glade_cursor_set (GdkWindow * window, GladeCursorType type)
+glade_cursor_set (GladeProject    *project,
+		  GdkWindow       *window, 
+		  GladeCursorType  type)
 {
   GladeWidgetAdaptor *adaptor;
   GdkCursor *the_cursor = NULL;
@@ -103,13 +98,12 @@ glade_cursor_set (GdkWindow * window, GladeCursorType type)
         break;
       case GLADE_CURSOR_ADD_WIDGET:
         if ((adaptor =
-             glade_palette_get_current_item (glade_app_get_palette ())) != NULL)
+             glade_project_get_add_item (project)) != NULL)
           {
             g_object_get (adaptor, "cursor", &the_cursor, NULL);
 
             if (the_cursor == NULL)
               the_cursor = cursor->add_widget;
-
           }
         else
           the_cursor = cursor->add_widget;
@@ -145,7 +139,7 @@ glade_cursor_set (GdkWindow * window, GladeCursorType type)
         break;
     }
 
-  set_cursor (cursor->selector);
+  set_cursor (project, cursor->selector);
   gdk_window_set_cursor (window, the_cursor);
 }
 
diff --git a/gladeui/glade-cursor.h b/gladeui/glade-cursor.h
index 992dcfa..c7a085c 100644
--- a/gladeui/glade-cursor.h
+++ b/gladeui/glade-cursor.h
@@ -45,8 +45,10 @@ typedef enum {
 	GLADE_CURSOR_DRAG
 } GladeCursorType;
 
-void               glade_cursor_init (void);
-void               glade_cursor_set (GdkWindow *window, GladeCursorType type);
+void               glade_cursor_init                  (void);
+void               glade_cursor_set                   (GladeProject    *project,
+						       GdkWindow       *window, 
+						       GladeCursorType  type);
 const GdkPixbuf*   glade_cursor_get_add_widget_pixbuf (void);
 
 G_END_DECLS
diff --git a/gladeui/glade-fixed.c b/gladeui/glade-fixed.c
index 307ce90..eb4fbf4 100644
--- a/gladeui/glade-fixed.c
+++ b/gladeui/glade-fixed.c
@@ -557,11 +557,12 @@ glade_fixed_handle_child_event (GladeFixed * fixed,
   GtkWidget *fixed_widget, *child_widget;
   gint fixed_x, fixed_y, child_x, child_y;
   gboolean handled = FALSE, sig_handled;
+  GladeProject *project = glade_widget_get_project (GLADE_WIDGET (fixed));
 
   fixed_widget = GTK_WIDGET (glade_widget_get_object (GLADE_WIDGET (fixed)));
   child_widget = GTK_WIDGET (glade_widget_get_object (child));
 
-  pointer_mode = glade_app_get_pointer_mode ();
+  pointer_mode = glade_project_get_pointer_mode (project);
 
   /* when widget->window points to a parent window, these calculations
    * would be wrong if we based them on the GTK_WIDGET (fixed)->window,
@@ -590,16 +591,16 @@ glade_fixed_handle_child_event (GladeFixed * fixed,
           {
             if ((event_state & GDK_SHIFT_MASK) ||
                 pointer_mode == GLADE_POINTER_DRAG_RESIZE)
-              glade_cursor_set (((GdkEventAny *) event)->window, operation);
+              glade_cursor_set (project, ((GdkEventAny *) event)->window, operation);
             else if (pointer_mode == GLADE_POINTER_SELECT)
-              glade_cursor_set (((GdkEventAny *) event)->window,
+              glade_cursor_set (project, ((GdkEventAny *) event)->window,
                                 GLADE_CURSOR_SELECTOR);
 
           }
         else if (fixed->configuring && !(event_state & GDK_BUTTON1_MASK))
           {
             /* Cancel drags that no longer have mouse down */
-            glade_cursor_set (((GdkEventAny *) event)->window, operation);
+            glade_cursor_set (project, ((GdkEventAny *) event)->window, operation);
 
             glade_fixed_cancel_operation (fixed, operation);
             handled = TRUE;
@@ -611,7 +612,7 @@ glade_fixed_handle_child_event (GladeFixed * fixed,
                                     &fixed->mouse_x, &fixed->mouse_y);
 
             glade_fixed_configure_widget (fixed, child);
-            glade_cursor_set (((GdkEventAny *) event)->window,
+            glade_cursor_set (project, ((GdkEventAny *) event)->window,
                               fixed->operation);
             handled = TRUE;
           }
@@ -631,7 +632,7 @@ glade_fixed_handle_child_event (GladeFixed * fixed,
             glade_fixed_save_state (fixed, child);
 
             fixed->operation = operation;
-            glade_cursor_set (((GdkEventAny *) event)->window,
+            glade_cursor_set (project, ((GdkEventAny *) event)->window,
                               fixed->operation);
 
             g_signal_emit (G_OBJECT (fixed),
@@ -647,9 +648,9 @@ glade_fixed_handle_child_event (GladeFixed * fixed,
 
             if ((event_state & GDK_SHIFT_MASK) ||
                 pointer_mode == GLADE_POINTER_DRAG_RESIZE)
-              glade_cursor_set (((GdkEventAny *) event)->window, operation);
+              glade_cursor_set (project, ((GdkEventAny *) event)->window, operation);
             else
-              glade_cursor_set (((GdkEventAny *) event)->window,
+              glade_cursor_set (project, ((GdkEventAny *) event)->window,
                                 GLADE_CURSOR_SELECTOR);
 
             glade_fixed_cancel_operation (fixed, operation);
@@ -667,6 +668,7 @@ glade_fixed_child_event (GladeWidget * gwidget,
                          GdkEvent * event, GladeFixed * fixed)
 {
   GtkWidget *event_widget;
+  GladeProject *project = glade_widget_get_project (gwidget);
 
   /* Get the basic event info... */
   gdk_window_get_user_data (((GdkEventAny *) event)->window,
@@ -686,9 +688,9 @@ glade_fixed_child_event (GladeWidget * gwidget,
    * the palette.
    */
   if (GLADE_IS_FIXED (gwidget) &&
-      glade_app_get_pointer_mode () == GLADE_POINTER_ADD_WIDGET)
+      glade_project_get_pointer_mode (project) == GLADE_POINTER_ADD_WIDGET)
     {
-      glade_cursor_set (((GdkEventAny *) event)->window,
+      glade_cursor_set (project, ((GdkEventAny *) event)->window,
                         GLADE_CURSOR_ADD_WIDGET);
       return FALSE;
     }
@@ -795,9 +797,10 @@ glade_fixed_event (GladeWidget * gwidget_fixed, GdkEvent * event)
   GladeFixed *fixed = GLADE_FIXED (gwidget_fixed);
   GladeWidgetAdaptor *adaptor;
   GtkWidget *event_widget;
+  GladeProject *project = glade_widget_get_project (gwidget_fixed);
   gboolean handled = FALSE;
 
-  adaptor = glade_palette_get_current_item (glade_app_get_palette ());
+  adaptor = glade_project_get_add_item (project);
 
   /* Get the event widget and the deep widget */
   gdk_window_get_user_data (((GdkEventAny *) event)->window,
@@ -843,24 +846,23 @@ glade_fixed_event (GladeWidget * gwidget_fixed, GdkEvent * event)
                                       glade_widget_get_project (GLADE_WIDGET (fixed)));
                 fixed->creating = FALSE;
 
-                glade_palette_deselect_current_item (glade_app_get_palette (),
-                                                     TRUE);
+		glade_project_set_add_item (project, NULL);
 
                 handled = TRUE;
               }
           }
         break;
       case GDK_MOTION_NOTIFY:
-        if (glade_app_get_pointer_mode () == GLADE_POINTER_ADD_WIDGET)
+        if (glade_project_get_pointer_mode (project) == GLADE_POINTER_ADD_WIDGET)
           {
-            glade_cursor_set (((GdkEventAny *) event)->window,
+            glade_cursor_set (project, ((GdkEventAny *) event)->window,
                               GLADE_CURSOR_ADD_WIDGET);
 
             handled = TRUE;
           }
         else if (GLADE_IS_FIXED (glade_widget_get_parent (gwidget_fixed)) == FALSE &&
-                 glade_app_get_pointer_mode () == GLADE_POINTER_SELECT)
-          glade_cursor_set (((GdkEventAny *) event)->window,
+                 glade_project_get_pointer_mode (project) == GLADE_POINTER_SELECT)
+          glade_cursor_set (project, ((GdkEventAny *) event)->window,
                             GLADE_CURSOR_SELECTOR);
         break;
       default:
diff --git a/gladeui/glade-palette.c b/gladeui/glade-palette.c
index fa0cb52..11f3bf9 100644
--- a/gladeui/glade-palette.c
+++ b/gladeui/glade-palette.c
@@ -64,16 +64,16 @@ struct _GladePalettePrivate
   GtkWidget *create_root_button;
 
   GtkWidget *toolpalette;
-  GtkWidget *current_item;
 
   GladeItemAppearance item_appearance;
-  gboolean use_small_item_icons;
-  gboolean sticky_selection_mode;       /* whether sticky_selection mode has been enabled */
+  gboolean            use_small_item_icons;
+
+  GladeWidgetAdaptor *local_selection;
+  GHashTable         *button_table;
 };
 
 enum
 {
-  TOGGLED,
   REFRESH,
   LAST_SIGNAL
 };
@@ -81,534 +81,222 @@ enum
 enum
 {
   PROP_0,
-  PROP_CURRENT_ITEM,
   PROP_ITEM_APPEARANCE,
   PROP_USE_SMALL_ITEM_ICONS,
   PROP_SHOW_SELECTOR_BUTTON,
-  PROP_CATALOGS,
   PROP_PROJECT
 };
 
 static guint glade_palette_signals[LAST_SIGNAL] = { 0 };
 
-static void glade_palette_append_item_group (GladePalette * palette,
-                                             GladeWidgetGroup * group);
-static void glade_palette_refresh           (GladePalette * palette);
+static void glade_palette_append_item_group (GladePalette        *palette,
+                                             GladeWidgetGroup    *group);
+static void glade_palette_update_appearance (GladePalette        *palette);
 
-static void glade_palette_update_appearance (GladePalette * palette);
+static void palette_item_toggled_cb         (GtkToggleToolButton *button, 
+					     GladePalette        *palette);
 
 G_DEFINE_TYPE (GladePalette, glade_palette, GTK_TYPE_VBOX)
 
-static void
-selector_button_toggled_cb (GtkToggleButton * button,
-			    GladePalette * palette)
-{
-  if (gtk_toggle_button_get_active (button))
-    {
-      glade_palette_deselect_current_item (palette, FALSE);
-    }
-  else if (glade_palette_get_current_item (palette) == NULL)
-    {
-      gtk_toggle_button_set_active (button, TRUE);
-    }
-}
 
+/*******************************************************
+ *                   Project Signals                   *
+ *******************************************************/
 static void
-glade_palette_set_catalogs (GladePalette * palette, GList * catalogs)
+palette_item_refresh_cb (GladePalette *palette,
+			 GtkWidget    *item)
 {
-  GladePalettePrivate *priv;
-  GList *l;
-
-  g_return_if_fail (GLADE_IS_PALETTE (palette));
-  priv = palette->priv;
+  GladeProject       *project;
+  GladeSupportMask    support;
+  GladeWidgetAdaptor *adaptor;
+  gchar              *warning, *text;
 
-  priv->catalogs = catalogs;
+  adaptor = g_object_get_data (G_OBJECT (item), "glade-widget-adaptor");
+  g_assert (adaptor);
 
-  for (l = (GList *) priv->catalogs; l; l = l->next)
+  if ((project = palette->priv->project) &&
+      (warning = glade_project_verify_widget_adaptor (project, adaptor,
+						      &support)) != NULL)
     {
-      GList *groups = glade_catalog_get_widget_groups (GLADE_CATALOG (l->data));
+      /* set sensitivity */
+      gtk_widget_set_sensitive (GTK_WIDGET (item),
+                                !(support & GLADE_SUPPORT_MISMATCH));
 
-      for (; groups; groups = groups->next)
-        {
-          GladeWidgetGroup *group = GLADE_WIDGET_GROUP (groups->data);
+      if (support & GLADE_SUPPORT_DEPRECATED)
+        /* XXX Todo, draw a cross overlaying the widget icon */
+        gtk_tool_button_set_stock_id (GTK_TOOL_BUTTON (item),
+                                      GTK_STOCK_DIALOG_WARNING);
+      else
+        gtk_tool_button_set_icon_name (GTK_TOOL_BUTTON (item),
+                                       glade_widget_adaptor_get_icon_name (adaptor));
 
-          if (glade_widget_group_get_adaptors (group))
-            glade_palette_append_item_group (palette, group);
-        }
+      /* prepend widget title */
+      text = g_strdup_printf ("%s: %s", glade_widget_adaptor_get_title (adaptor), warning);
+      gtk_widget_set_tooltip_text (item, text);
+      g_free (text);
+      g_free (warning);
     }
-}
-
-GladeProject *
-glade_palette_get_project (GladePalette *palette)
-{
-  g_return_val_if_fail (GLADE_IS_PALETTE (palette), NULL);
-
-  return palette->priv->project;
-}
-
-void
-glade_palette_set_project (GladePalette *palette,
-			   GladeProject *project)
-{
-  g_return_if_fail (GLADE_IS_PALETTE (palette));
-
-  if (palette->priv->project != project)
+  else
     {
-
-      if (palette->priv->project)
-	{
-	  g_signal_handlers_disconnect_by_func (G_OBJECT (palette->priv->project),
-						G_CALLBACK (glade_palette_refresh),
-						palette);
-	}
-
-      palette->priv->project = project;
-
-      if (palette->priv->project)
-	{
-	  g_signal_connect_swapped (G_OBJECT (palette->priv->project), "targets-changed",
-				    G_CALLBACK (glade_palette_refresh), palette);
-	  g_signal_connect_swapped (G_OBJECT (palette->priv->project), "parse-finished",
-				    G_CALLBACK (glade_palette_refresh), palette);
-	}
-
-      glade_palette_refresh (palette);
-
-      g_object_notify (G_OBJECT (palette), "project");
+      gtk_widget_set_tooltip_text (GTK_WIDGET (item), 
+				   glade_widget_adaptor_get_title (adaptor));
+      gtk_widget_set_sensitive (GTK_WIDGET (item), TRUE);
+      gtk_tool_button_set_icon_name (GTK_TOOL_BUTTON (item),
+                                     glade_widget_adaptor_get_icon_name (adaptor));
     }
 }
 
-/**
- * glade_palette_set_item_appearance:
- * @palette: a #GladePalette
- * @item_appearance: the item appearance
- *
- * Sets the appearance of the palette items.
- */
-void
-glade_palette_set_item_appearance (GladePalette * palette,
-                                   GladeItemAppearance item_appearance)
+static void
+glade_palette_refresh (GladePalette * palette)
 {
-  GladePalettePrivate *priv;
-
   g_return_if_fail (GLADE_IS_PALETTE (palette));
 
-  priv = palette->priv;
-
-  if (priv->item_appearance != item_appearance)
-    {
-      priv->item_appearance = item_appearance;
-
-      glade_palette_update_appearance (palette);
-
-      g_object_notify (G_OBJECT (palette), "item-appearance");
-    }
+  g_signal_emit (G_OBJECT (palette), glade_palette_signals[REFRESH], 0);
 }
 
-/**
- * glade_palette_set_use_small_item_icons:
- * @palette: a #GladePalette
- * @use_small_item_icons: Whether to use small item icons
- *
- * Sets whether to use small item icons.
- */
-void
-glade_palette_set_use_small_item_icons (GladePalette * palette,
-                                        gboolean use_small_item_icons)
+static void
+project_add_item_changed_cb (GladeProject *project,
+			     GParamSpec   *pspec,
+			     GladePalette *palette)
 {
-  GladePalettePrivate *priv;
-  g_return_if_fail (GLADE_IS_PALETTE (palette));
-  priv = palette->priv;
+  GtkToggleToolButton *selection = NULL;
+  GladePalettePrivate *priv = palette->priv;
 
-  if (priv->use_small_item_icons != use_small_item_icons)
+  if (priv->local_selection)
     {
-      priv->use_small_item_icons = use_small_item_icons;
+      selection = g_hash_table_lookup (priv->button_table, 
+				       glade_widget_adaptor_get_name (priv->local_selection));
 
-      glade_palette_update_appearance (palette);
-
-      g_object_notify (G_OBJECT (palette), "use-small-item-icons");
+      g_signal_handlers_block_by_func (selection, palette_item_toggled_cb, palette);
+      gtk_toggle_tool_button_set_active (selection, FALSE);
+      g_signal_handlers_unblock_by_func (selection, palette_item_toggled_cb, palette);
 
+      glade_project_set_pointer_mode (priv->project, GLADE_POINTER_SELECT);
     }
 
-}
+  priv->local_selection = glade_project_get_add_item (priv->project);
 
-/**
- * glade_palette_set_show_selector_button:
- * @palette: a #GladePalette
- * @show_selector_button: whether to show selector button
- *
- * Sets whether to show the internal widget selector button
- */
-void
-glade_palette_set_show_selector_button (GladePalette * palette,
-                                        gboolean show_selector_button)
-{
-  GladePalettePrivate *priv;
-  g_return_if_fail (GLADE_IS_PALETTE (palette));
-  priv = palette->priv;
-
-  if (gtk_widget_get_visible (priv->selector_hbox) != show_selector_button)
+  if (priv->local_selection)
     {
-      if (show_selector_button)
-        gtk_widget_show (priv->selector_hbox);
-      else
-        gtk_widget_hide (priv->selector_hbox);
+      selection = g_hash_table_lookup (priv->button_table, 
+				       glade_widget_adaptor_get_name (priv->local_selection));
 
-      g_object_notify (G_OBJECT (palette), "show-selector-button");
+      g_signal_handlers_block_by_func (selection, palette_item_toggled_cb, palette);
+      gtk_toggle_tool_button_set_active (selection, TRUE);
+      g_signal_handlers_unblock_by_func (selection, palette_item_toggled_cb, palette);
 
+      glade_project_set_pointer_mode (priv->project, GLADE_POINTER_ADD_WIDGET);
     }
-
 }
 
-/* override GtkWidget::show_all since we have internal widgets we wish to keep
- * hidden unless we decide otherwise, like the hidden selector button.
- */
+/*******************************************************
+ *                    Local Signals                    *
+ *******************************************************/
 static void
-glade_palette_show_all (GtkWidget * widget)
+root_button_toggled_cb (GtkToggleButton * button,
+			GladePalette * palette)
 {
-  gtk_widget_show (widget);
-}
+  GladeWidgetAdaptor  *add_item;
+  GladePalettePrivate *priv = palette->priv;
 
-static void
-glade_palette_set_property (GObject * object,
-                            guint prop_id,
-                            const GValue * value, GParamSpec * pspec)
-{
-  GladePalette *palette = GLADE_PALETTE (object);
+  if (!priv->project)
+    return;
 
-  switch (prop_id)
+  add_item = glade_project_get_add_item (priv->project);
+  if (add_item)
     {
-    case PROP_PROJECT:
-      glade_palette_set_project (palette, (GladeProject *)g_value_get_object (value));
-      break;
-    case PROP_USE_SMALL_ITEM_ICONS:
-      glade_palette_set_use_small_item_icons (palette,
-					      g_value_get_boolean (value));
-      break;
-    case PROP_ITEM_APPEARANCE:
-      glade_palette_set_item_appearance (palette, g_value_get_enum (value));
-      break;
-    case PROP_SHOW_SELECTOR_BUTTON:
-      glade_palette_set_show_selector_button (palette,
-					      g_value_get_boolean (value));
-      break;
-    case PROP_CATALOGS:
-      glade_palette_set_catalogs (palette, g_value_get_pointer (value));
-      break;
-    default:
-      G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
-      break;
-    }
-}
-
-static void
-glade_palette_get_property (GObject * object,
-                            guint prop_id, GValue * value, GParamSpec * pspec)
-{
-  GladePalette *palette = GLADE_PALETTE (object);
-  GladePalettePrivate *priv = palette->priv;
+      glade_command_create (add_item, NULL, NULL, priv->project);
 
-  switch (prop_id)
-    {
-    case PROP_PROJECT:
-      g_value_set_object (value, priv->project);
-      break;
-    case PROP_CURRENT_ITEM:
-      if (priv->current_item)
-	g_value_set_pointer (value, g_object_get_data
-			     (G_OBJECT (priv->current_item),
-			      "glade-widget-adaptor"));
-      else
-	g_value_set_pointer (value, NULL);
-      
-      break;
-    case PROP_USE_SMALL_ITEM_ICONS:
-      g_value_set_boolean (value, priv->use_small_item_icons);
-      break;
-    case PROP_SHOW_SELECTOR_BUTTON:
-      g_value_set_boolean (value,
-			   gtk_widget_get_visible (priv->selector_button));
-      break;
-    case PROP_ITEM_APPEARANCE:
-      g_value_set_enum (value, priv->item_appearance);
-      break;
-    case PROP_CATALOGS:
-      g_value_set_pointer (value, (gpointer) priv->catalogs);
-      break;
-    default:
-      G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
-      break;
+      g_signal_handlers_block_by_func (priv->project, project_add_item_changed_cb, palette);
+      glade_project_set_add_item (priv->project, NULL);
+      g_signal_handlers_unblock_by_func (priv->project, project_add_item_changed_cb, palette);
     }
 }
 
 static void
-glade_palette_dispose (GObject * object)
+selector_button_toggled_cb (GtkToggleButton *button,
+			    GladePalette    *palette)
 {
-  GladePalettePrivate *priv;
-
-  priv = GLADE_PALETTE (object)->priv;
-
-  priv->catalogs = NULL;
-
-  G_OBJECT_CLASS (glade_palette_parent_class)->dispose (object);
-}
-
-static void
-glade_palette_finalize (GObject * object)
-{
-  GladePalettePrivate *priv;
-
-  priv = GLADE_PALETTE (object)->priv;
-
-  G_OBJECT_CLASS (glade_palette_parent_class)->finalize (object);
-}
-
-static void
-glade_palette_toggled (GladePalette * palette)
-{
-  GladeWidgetAdaptor *adaptor;
-  GladeWidget *widget;
+  GladePalettePrivate *priv = palette->priv;
 
-  g_return_if_fail (GLADE_IS_PALETTE (palette));
-  adaptor = glade_palette_get_current_item (palette);
+  if (!priv->project)
+    return;
 
-  /* class may be NULL if the selector was pressed */
-  if (adaptor && GWA_IS_TOPLEVEL (adaptor))
+  if (gtk_toggle_button_get_active (button))
     {
-      /* Inappropriate toplevel classes for libglade are
-       * disabled so no chance of creating a non-window toplevel here
-       */
-      widget = glade_palette_create_root_widget (palette, adaptor);
+      g_signal_handlers_block_by_func (priv->project, project_add_item_changed_cb, palette);
+      glade_project_set_add_item (priv->project, NULL);
+      g_signal_handlers_unblock_by_func (priv->project, project_add_item_changed_cb, palette);
     }
+  else if (glade_project_get_add_item (priv->project) == NULL)
+    gtk_toggle_button_set_active (button, TRUE);
 }
 
 static void
-glade_palette_class_init (GladePaletteClass * klass)
+palette_item_toggled_cb (GtkToggleToolButton *button, GladePalette *palette)
 {
-  GObjectClass *object_class;
-  GtkWidgetClass *widget_class;
-
-  object_class = G_OBJECT_CLASS (klass);
-  widget_class = GTK_WIDGET_CLASS (klass);
-
-  klass->toggled = glade_palette_toggled;
-
-  object_class->get_property = glade_palette_get_property;
-  object_class->set_property = glade_palette_set_property;
-  object_class->dispose = glade_palette_dispose;
-  object_class->finalize = glade_palette_finalize;
-
-  widget_class->show_all = glade_palette_show_all;
-
-  glade_palette_signals[TOGGLED] =
-      g_signal_new ("toggled",
-                    G_TYPE_FROM_CLASS (object_class),
-                    G_SIGNAL_RUN_LAST,
-                    G_STRUCT_OFFSET (GladePaletteClass, toggled),
-                    NULL, NULL, g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0);
-
-  glade_palette_signals[REFRESH] =
-      g_signal_new ("refresh",
-                    G_TYPE_FROM_CLASS (object_class),
-                    G_SIGNAL_RUN_LAST,
-                    G_STRUCT_OFFSET (GladePaletteClass, refresh),
-                    NULL, NULL, g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0);
-
-  g_object_class_install_property (object_class,
-                                   PROP_PROJECT,
-                                   g_param_spec_object ("project",
-							"Project",
-							"This palette's current project",
-							GLADE_TYPE_PROJECT,
-							G_PARAM_READWRITE));
-
-  g_object_class_install_property (object_class,
-                                   PROP_ITEM_APPEARANCE,
-                                   g_param_spec_enum ("item-appearance",
-                                                      "Item Appearance",
-                                                      "The appearance of the palette items",
-                                                      GLADE_TYPE_ITEM_APPEARANCE,
-                                                      GLADE_ITEM_ICON_ONLY,
-                                                      G_PARAM_READWRITE));
-
-  g_object_class_install_property (object_class,
-                                   PROP_ITEM_APPEARANCE,
-                                   g_param_spec_boolean ("use-small-item-icons",
-                                                         "Use Small Item Icons",
-                                                         "Whether to use small icons to represent items",
-                                                         FALSE,
-                                                         G_PARAM_READWRITE));
-
-  g_object_class_install_property (object_class,
-                                   PROP_ITEM_APPEARANCE,
-                                   g_param_spec_boolean ("show-selector-button",
-                                                         "Show Selector Button",
-                                                         "Whether to show the internal selector button",
-                                                         TRUE,
-                                                         G_PARAM_READWRITE));
-
-  g_object_class_install_property (object_class,
-                                   PROP_CURRENT_ITEM,
-                                   g_param_spec_pointer ("current-item",
-                                                         "Current Item Class",
-                                                         "The GladeWidgetAdaptor of the currently selected item",
-                                                         G_PARAM_READABLE));
-
-  g_object_class_install_property (object_class,
-                                   PROP_CATALOGS,
-                                   g_param_spec_pointer ("catalogs",
-                                                         "Widget catalogs",
-                                                         "The widget catalogs for the palette",
-                                                         G_PARAM_CONSTRUCT_ONLY
-                                                         | G_PARAM_READWRITE));
-
-  g_type_class_add_private (object_class, sizeof (GladePalettePrivate));
-}
-
-GladeWidget *
-glade_palette_create_root_widget (GladePalette * palette,
-                                  GladeWidgetAdaptor * adaptor)
-{
-  GladeWidget *widget;
-
-  /* Dont deselect palette if create is canceled by user in query dialog */
-  if ((widget =
-       glade_command_create (adaptor, NULL, NULL, palette->priv->project)) != NULL)
-    glade_palette_deselect_current_item (palette, FALSE);
-
-  return widget;
-}
-
-static void
-glade_palette_on_button_toggled (GtkWidget * button, GladePalette * palette)
-{
-  GladePalettePrivate *priv;
-  GdkModifierType mask;
-  GladeWidgetAdaptor *adaptor;
-  gboolean is_root_active;
-
-  g_return_if_fail (GLADE_IS_PALETTE (palette));
-  g_return_if_fail (GTK_IS_TOGGLE_TOOL_BUTTON (button) ||
-                    GTK_IS_TOGGLE_BUTTON (button));
-  priv = palette->priv;
-
-  is_root_active =
-      gtk_toggle_button_get_active (GTK_TOGGLE_BUTTON
-                                    (priv->create_root_button));
-
-  if (button == priv->create_root_button && priv->current_item &&
-      is_root_active)
-    {
-      adaptor = glade_palette_get_current_item (palette);
-      glade_palette_create_root_widget (palette, adaptor);
-      return;
-    }
+  GladePalettePrivate *priv = palette->priv;
+  GladeWidgetAdaptor  *adaptor;
+  GtkToggleToolButton *selection = NULL;
 
-  g_return_if_fail (GTK_IS_TOGGLE_TOOL_BUTTON (button));
+  if (!priv->project)
+    return;
 
   adaptor = g_object_get_data (G_OBJECT (button), "glade-widget-adaptor");
   if (!adaptor)
     return;
 
-  /* if we are toggling currently active item into non-active state */
-  if (priv->current_item == button)
+  /* Start by unselecting the currently selected item if any */
+  if (priv->local_selection)
     {
-      priv->current_item = NULL;
-      g_object_notify (G_OBJECT (palette), "current-item");
+      selection = g_hash_table_lookup (priv->button_table, 
+				       glade_widget_adaptor_get_name (priv->local_selection));
 
-      glade_app_set_pointer_mode (GLADE_POINTER_SELECT);
-
-      gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (priv->selector_button),
-                                    TRUE);
+      g_signal_handlers_block_by_func (selection, palette_item_toggled_cb, palette);
+      gtk_toggle_tool_button_set_active (selection, FALSE);
+      g_signal_handlers_unblock_by_func (selection, palette_item_toggled_cb, palette);
+      
+      priv->local_selection = NULL;
 
-      priv->sticky_selection_mode = FALSE;
+      g_signal_handlers_block_by_func (priv->project, project_add_item_changed_cb, palette);
+      glade_project_set_add_item (priv->project, NULL);
+      g_signal_handlers_unblock_by_func (priv->project, project_add_item_changed_cb, palette);
 
-      g_signal_emit (G_OBJECT (palette), glade_palette_signals[TOGGLED], 0);
+      gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (priv->selector_button), TRUE);
 
-      return;
+      glade_project_set_pointer_mode (priv->project, GLADE_POINTER_SELECT);
     }
 
-  /* now we are interested only in buttons which toggle from inactive to active */
-  if (!gtk_toggle_tool_button_get_active (GTK_TOGGLE_TOOL_BUTTON (button)))
+  if (!gtk_toggle_tool_button_get_active (button))
     return;
 
-  if (priv->current_item && (button != priv->current_item))
-    gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON
-                                       (priv->current_item), FALSE);
-
-  priv->current_item = button;
-
-  if (is_root_active)
+  /* Auto-create toplevel types */
+  if (GWA_IS_TOPLEVEL (adaptor))
     {
-      glade_palette_create_root_widget (palette, adaptor);
-      return;
-    }
-
-  g_object_notify (G_OBJECT (palette), "current-item");
-
-  glade_app_set_pointer_mode (GLADE_POINTER_ADD_WIDGET);
-
-  gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (priv->selector_button),
-                                FALSE);
-
-  /* check whether to enable sticky selection */
-  gdk_window_get_pointer (gtk_widget_get_window (button), NULL, NULL, &mask);
-  priv->sticky_selection_mode = (!GWA_IS_TOPLEVEL (adaptor)) &&
-      (mask & GDK_CONTROL_MASK);
+      glade_command_create (adaptor, NULL, NULL, priv->project);
 
-  g_signal_emit (G_OBJECT (palette), glade_palette_signals[TOGGLED], 0);
-}
-
-
-static void
-glade_palette_item_refresh (GladePalette *palette, 
-			    GtkWidget    *item)
-{
-  GladeProject *project;
-  GladeSupportMask support;
-  GladeWidgetAdaptor *adaptor;
-  gchar *warning, *text;
-
-  adaptor = g_object_get_data (G_OBJECT (item), "glade-widget-adaptor");
-  g_assert (adaptor);
-
-  if ((project = palette->priv->project) &&
-      (warning =
-       glade_project_verify_widget_adaptor (project, adaptor,
-                                            &support)) != NULL)
-    {
-      /* set sensitivity */
-      gtk_widget_set_sensitive (GTK_WIDGET (item),
-                                !(support & GLADE_SUPPORT_MISMATCH));
-
-      if (support & GLADE_SUPPORT_DEPRECATED)
-        /* XXX Todo, draw a cross overlaying the widget icon */
-        gtk_tool_button_set_stock_id (GTK_TOOL_BUTTON (item),
-                                      GTK_STOCK_DIALOG_WARNING);
-      else
-        gtk_tool_button_set_icon_name (GTK_TOOL_BUTTON (item),
-                                       glade_widget_adaptor_get_icon_name (adaptor));
-
-      /* prepend widget title */
-      text = g_strdup_printf ("%s: %s", glade_widget_adaptor_get_title (adaptor), warning);
-      gtk_widget_set_tooltip_text (item, text);
-      g_free (text);
-      g_free (warning);
+      g_signal_handlers_block_by_func (button, palette_item_toggled_cb, palette);
+      gtk_toggle_tool_button_set_active (button, FALSE);
+      g_signal_handlers_unblock_by_func (button, palette_item_toggled_cb, palette);
     }
   else
     {
-      gtk_widget_set_tooltip_text (GTK_WIDGET (item), 
-				   glade_widget_adaptor_get_title (adaptor));
-      gtk_widget_set_sensitive (GTK_WIDGET (item), TRUE);
-      gtk_tool_button_set_icon_name (GTK_TOOL_BUTTON (item),
-                                     glade_widget_adaptor_get_icon_name (adaptor));
+      g_signal_handlers_block_by_func (priv->project, project_add_item_changed_cb, palette);
+      glade_project_set_add_item (priv->project, adaptor);
+      g_signal_handlers_unblock_by_func (priv->project, project_add_item_changed_cb, palette);
+
+      gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON (priv->selector_button), FALSE);
+
+      priv->local_selection = adaptor;
+
+      glade_project_set_pointer_mode (priv->project, GLADE_POINTER_ADD_WIDGET);
     }
 }
 
-
 static gint
-glade_palette_item_button_press (GtkWidget * button,
-                                 GdkEventButton * event, GtkToolItem * item)
+palette_item_button_press_cb (GtkWidget      *button,
+			      GdkEventButton *event, 
+			      GtkToolItem    *item)
 {
   if (glade_popup_is_popup_event (event))
     {
@@ -625,6 +313,9 @@ glade_palette_item_button_press (GtkWidget * button,
   return FALSE;
 }
 
+/*******************************************************
+ *          Building Widgets/Populating catalog        *
+ *******************************************************/
 static GtkWidget *
 glade_palette_new_item (GladePalette * palette, GladeWidgetAdaptor * adaptor)
 {
@@ -645,22 +336,26 @@ glade_palette_new_item (GladePalette * palette, GladeWidgetAdaptor * adaptor)
   gtk_widget_show (box);
   gtk_container_add (GTK_CONTAINER (box), label);
   gtk_tool_button_set_label_widget (GTK_TOOL_BUTTON (item), box);
-  glade_palette_item_refresh (palette, item);
+  palette_item_refresh_cb (palette, item);
 
   /* Update selection when the item is pushed */
   g_signal_connect (G_OBJECT (item), "toggled",
-                    G_CALLBACK (glade_palette_on_button_toggled), palette);
+                    G_CALLBACK (palette_item_toggled_cb), palette);
 
   /* Update palette item when active project state changes */
   g_signal_connect (G_OBJECT (palette), "refresh",
-		    G_CALLBACK (glade_palette_item_refresh), item);
+		    G_CALLBACK (palette_item_refresh_cb), item);
 
   /* Fire Glade palette popup menus */
   g_signal_connect (G_OBJECT (button), "button-press-event",
-                    G_CALLBACK (glade_palette_item_button_press), item);
+                    G_CALLBACK (palette_item_button_press_cb), item);
 
   gtk_widget_show (item);
 
+  g_hash_table_insert (palette->priv->button_table, 
+		       g_strdup (glade_widget_adaptor_get_name (adaptor)), 
+		       item);
+
   return item;
 }
 
@@ -702,8 +397,7 @@ glade_palette_new_item_group (GladePalette * palette, GladeWidgetGroup * group)
 
   /* set default expanded state */
   gtk_tool_item_group_set_collapsed (GTK_TOOL_ITEM_GROUP (item_group),
-                                     glade_widget_group_get_expanded (group) ==
-                                     FALSE);
+                                     glade_widget_group_get_expanded (group) == FALSE);
 
   gtk_widget_show (item_group);
 
@@ -722,34 +416,26 @@ glade_palette_append_item_group (GladePalette * palette,
 }
 
 static void
-glade_palette_update_appearance (GladePalette * palette)
+glade_palette_populate (GladePalette * palette)
 {
   GladePalettePrivate *priv;
-  GtkToolbarStyle style;
-  GtkIconSize size;
+  GList *l;
 
+  g_return_if_fail (GLADE_IS_PALETTE (palette));
   priv = palette->priv;
 
-  size = priv->use_small_item_icons ? GTK_ICON_SIZE_MENU : GTK_ICON_SIZE_BUTTON;
-
-  switch (priv->item_appearance)
+  for (l = (GList *) glade_app_get_catalogs (); l; l = l->next)
     {
-      case GLADE_ITEM_ICON_AND_LABEL:
-        style = GTK_TOOLBAR_BOTH_HORIZ;
-        break;
-      case GLADE_ITEM_ICON_ONLY:
-        style = GTK_TOOLBAR_ICONS;
-        break;
-      case GLADE_ITEM_LABEL_ONLY:
-        style = GTK_TOOLBAR_TEXT;
-        break;
-      default:
-        g_assert_not_reached ();
-        break;
-    }
+      GList *groups = glade_catalog_get_widget_groups (GLADE_CATALOG (l->data));
 
-  gtk_tool_palette_set_icon_size (GTK_TOOL_PALETTE (priv->toolpalette), size);
-  gtk_tool_palette_set_style (GTK_TOOL_PALETTE (priv->toolpalette), style);
+      for (; groups; groups = groups->next)
+        {
+          GladeWidgetGroup *group = GLADE_WIDGET_GROUP (groups->data);
+
+          if (glade_widget_group_get_adaptors (group))
+            glade_palette_append_item_group (palette, group);
+        }
+    }
 }
 
 static GtkWidget *
@@ -792,24 +478,208 @@ glade_palette_create_create_root_button (GladePalette * palette)
   gtk_button_set_label (GTK_BUTTON (create_root_button), "gtk-add");
 
   g_signal_connect (G_OBJECT (create_root_button), "toggled",
-                    G_CALLBACK (glade_palette_on_button_toggled), palette);
+                    G_CALLBACK (root_button_toggled_cb), palette);
 
   return create_root_button;
 }
 
+/*******************************************************
+ *                    Class & methods                  *
+ *******************************************************/
+
+/* override GtkWidget::show_all since we have internal widgets we wish to keep
+ * hidden unless we decide otherwise, like the hidden selector button.
+ */
+static void
+glade_palette_show_all (GtkWidget * widget)
+{
+  gtk_widget_show (widget);
+}
+
+static void
+glade_palette_set_property (GObject * object,
+                            guint prop_id,
+                            const GValue * value, GParamSpec * pspec)
+{
+  GladePalette *palette = GLADE_PALETTE (object);
+
+  switch (prop_id)
+    {
+    case PROP_PROJECT:
+      glade_palette_set_project (palette, (GladeProject *)g_value_get_object (value));
+      break;
+    case PROP_USE_SMALL_ITEM_ICONS:
+      glade_palette_set_use_small_item_icons (palette,
+					      g_value_get_boolean (value));
+      break;
+    case PROP_ITEM_APPEARANCE:
+      glade_palette_set_item_appearance (palette, g_value_get_enum (value));
+      break;
+    case PROP_SHOW_SELECTOR_BUTTON:
+      glade_palette_set_show_selector_button (palette,
+					      g_value_get_boolean (value));
+      break;
+    default:
+      G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
+      break;
+    }
+}
+
+static void
+glade_palette_get_property (GObject * object,
+                            guint prop_id, GValue * value, GParamSpec * pspec)
+{
+  GladePalette *palette = GLADE_PALETTE (object);
+  GladePalettePrivate *priv = palette->priv;
+
+  switch (prop_id)
+    {
+    case PROP_PROJECT:
+      g_value_set_object (value, priv->project);
+      break;
+    case PROP_USE_SMALL_ITEM_ICONS:
+      g_value_set_boolean (value, priv->use_small_item_icons);
+      break;
+    case PROP_SHOW_SELECTOR_BUTTON:
+      g_value_set_boolean (value,
+			   gtk_widget_get_visible (priv->selector_button));
+      break;
+    case PROP_ITEM_APPEARANCE:
+      g_value_set_enum (value, priv->item_appearance);
+      break;
+    default:
+      G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
+      break;
+    }
+}
+
+static void
+glade_palette_dispose (GObject * object)
+{
+  GladePalettePrivate *priv;
+
+  priv = GLADE_PALETTE (object)->priv;
+
+  priv->catalogs = NULL;
+
+  G_OBJECT_CLASS (glade_palette_parent_class)->dispose (object);
+}
+
+static void
+glade_palette_finalize (GObject * object)
+{
+  GladePalettePrivate *priv;
+
+  priv = GLADE_PALETTE (object)->priv;
+
+  g_hash_table_destroy (priv->button_table);
+
+  G_OBJECT_CLASS (glade_palette_parent_class)->finalize (object);
+}
+
+static void
+glade_palette_update_appearance (GladePalette * palette)
+{
+  GladePalettePrivate *priv;
+  GtkToolbarStyle style;
+  GtkIconSize size;
+
+  priv = palette->priv;
+
+  size = priv->use_small_item_icons ? GTK_ICON_SIZE_MENU : GTK_ICON_SIZE_BUTTON;
+
+  switch (priv->item_appearance)
+    {
+      case GLADE_ITEM_ICON_AND_LABEL:
+        style = GTK_TOOLBAR_BOTH_HORIZ;
+        break;
+      case GLADE_ITEM_ICON_ONLY:
+        style = GTK_TOOLBAR_ICONS;
+        break;
+      case GLADE_ITEM_LABEL_ONLY:
+        style = GTK_TOOLBAR_TEXT;
+        break;
+      default:
+        g_assert_not_reached ();
+        break;
+    }
+
+  gtk_tool_palette_set_icon_size (GTK_TOOL_PALETTE (priv->toolpalette), size);
+  gtk_tool_palette_set_style (GTK_TOOL_PALETTE (priv->toolpalette), style);
+}
+
+static void
+glade_palette_class_init (GladePaletteClass * klass)
+{
+  GObjectClass *object_class;
+  GtkWidgetClass *widget_class;
+
+  object_class = G_OBJECT_CLASS (klass);
+  widget_class = GTK_WIDGET_CLASS (klass);
+
+  object_class->get_property = glade_palette_get_property;
+  object_class->set_property = glade_palette_set_property;
+  object_class->dispose = glade_palette_dispose;
+  object_class->finalize = glade_palette_finalize;
+
+  widget_class->show_all = glade_palette_show_all;
+
+  glade_palette_signals[REFRESH] =
+      g_signal_new ("refresh",
+                    G_TYPE_FROM_CLASS (object_class),
+                    G_SIGNAL_RUN_LAST,
+                    G_STRUCT_OFFSET (GladePaletteClass, refresh),
+                    NULL, NULL, g_cclosure_marshal_VOID__VOID, G_TYPE_NONE, 0);
+
+  g_object_class_install_property (object_class,
+                                   PROP_PROJECT,
+                                   g_param_spec_object ("project",
+							"Project",
+							"This palette's current project",
+							GLADE_TYPE_PROJECT,
+							G_PARAM_READWRITE));
+
+  g_object_class_install_property (object_class,
+                                   PROP_ITEM_APPEARANCE,
+                                   g_param_spec_enum ("item-appearance",
+                                                      "Item Appearance",
+                                                      "The appearance of the palette items",
+                                                      GLADE_TYPE_ITEM_APPEARANCE,
+                                                      GLADE_ITEM_ICON_ONLY,
+                                                      G_PARAM_READWRITE));
+
+  g_object_class_install_property (object_class,
+                                   PROP_ITEM_APPEARANCE,
+                                   g_param_spec_boolean ("use-small-item-icons",
+                                                         "Use Small Item Icons",
+                                                         "Whether to use small icons to represent items",
+                                                         FALSE,
+                                                         G_PARAM_READWRITE));
+
+  g_object_class_install_property (object_class,
+                                   PROP_ITEM_APPEARANCE,
+                                   g_param_spec_boolean ("show-selector-button",
+                                                         "Show Selector Button",
+                                                         "Whether to show the internal selector button",
+                                                         TRUE,
+                                                         G_PARAM_READWRITE));
+
+  g_type_class_add_private (object_class, sizeof (GladePalettePrivate));
+}
+
 static void
 glade_palette_init (GladePalette * palette)
 {
   GladePalettePrivate *priv;
-  GtkWidget *sw;
+  GtkWidget           *sw;
 
   priv = palette->priv = GLADE_PALETTE_GET_PRIVATE (palette);
 
-  priv->catalogs = NULL;
-  priv->current_item = NULL;
-  priv->item_appearance = GLADE_ITEM_ICON_ONLY;
+  priv->button_table = g_hash_table_new_full (g_str_hash, g_str_equal,
+					      (GDestroyNotify)g_free, NULL);
+
+  priv->item_appearance      = GLADE_ITEM_ICON_ONLY;
   priv->use_small_item_icons = FALSE;
-  priv->sticky_selection_mode = FALSE;
 
   /* create selector button */
   priv->selector_button = glade_palette_create_selector_button (palette);
@@ -846,83 +716,165 @@ glade_palette_init (GladePalette * palette)
   glade_palette_update_appearance (palette);
 
   gtk_widget_set_no_show_all (GTK_WIDGET (palette), TRUE);
-}
 
-/**
- * glade_palette_get_current_item:
- * @palette: a #GladePalette
- *
- * Gets the #GladeWidgetAdaptor of the currently selected item.
- *
- * Returns: the #GladeWidgetAdaptor of currently selected item, or NULL
- *          if no item is selected.
- */
-GladeWidgetAdaptor *
-glade_palette_get_current_item (GladePalette * palette)
-{
-  g_return_val_if_fail (GLADE_IS_PALETTE (palette), NULL);
+  glade_palette_populate (palette);
+}
 
-  if (palette->priv->current_item)
-    return g_object_get_data (G_OBJECT (palette->priv->current_item),
-                              "glade-widget-adaptor");
 
-  return NULL;
-}
+/*******************************************************
+ *                         API                         *
+ *******************************************************/
 
 /**
  * glade_palette_new:
- * @catalogs: the widget catalogs for the palette.
  *
  * Creates a new #GladePalette widget
  *
  * Returns: a new #GladePalette
  */
 GtkWidget *
-glade_palette_new (const GList * catalogs)
+glade_palette_new (void)
 {
   GladePalette *palette;
 
-  g_return_val_if_fail (catalogs != NULL, NULL);
-
   palette = g_object_new (GLADE_TYPE_PALETTE,
                           "spacing", 2,
                           "item-appearance", GLADE_ITEM_ICON_ONLY,
-                          "catalogs", catalogs, NULL);
+                          NULL);
 
   return GTK_WIDGET (palette);
 }
 
+
+GladeProject *
+glade_palette_get_project (GladePalette *palette)
+{
+  g_return_val_if_fail (GLADE_IS_PALETTE (palette), NULL);
+
+  return palette->priv->project;
+}
+
+void
+glade_palette_set_project (GladePalette *palette,
+			   GladeProject *project)
+{
+  g_return_if_fail (GLADE_IS_PALETTE (palette));
+
+  if (palette->priv->project != project)
+    {
+      if (palette->priv->project)
+	{
+	  g_signal_handlers_disconnect_by_func (G_OBJECT (palette->priv->project),
+						G_CALLBACK (glade_palette_refresh),
+						palette);
+
+	  g_signal_handlers_disconnect_by_func (G_OBJECT (palette->priv->project),
+						G_CALLBACK (project_add_item_changed_cb),
+						palette);
+
+	  g_object_unref (palette->priv->project);
+	}
+
+      palette->priv->project = project;
+
+      if (palette->priv->project)
+	{
+	  g_signal_connect_swapped (G_OBJECT (palette->priv->project), "targets-changed",
+				    G_CALLBACK (glade_palette_refresh), palette);
+	  g_signal_connect_swapped (G_OBJECT (palette->priv->project), "parse-finished",
+				    G_CALLBACK (glade_palette_refresh), palette);
+
+	  g_signal_connect (G_OBJECT (palette->priv->project), "notify::add-item",
+			    G_CALLBACK (project_add_item_changed_cb), palette);
+
+	  g_object_ref (palette->priv->project);
+
+	  project_add_item_changed_cb (project, NULL, palette);
+	}
+
+      glade_palette_refresh (palette);
+
+      g_object_notify (G_OBJECT (palette), "project");
+    }
+}
+
 /**
- * glade_palette_deselect_current_item:
+ * glade_palette_set_item_appearance:
  * @palette: a #GladePalette
- * @sticky_aware: whether to consider sticky selection mode
+ * @item_appearance: the item appearance
  *
- * Deselects the currently selected item
+ * Sets the appearance of the palette items.
  */
 void
-glade_palette_deselect_current_item (GladePalette * palette,
-                                     gboolean sticky_aware)
+glade_palette_set_item_appearance (GladePalette * palette,
+                                   GladeItemAppearance item_appearance)
 {
+  GladePalettePrivate *priv;
+
   g_return_if_fail (GLADE_IS_PALETTE (palette));
 
-  if (sticky_aware && palette->priv->sticky_selection_mode)
-    return;
+  priv = palette->priv;
+
+  if (priv->item_appearance != item_appearance)
+    {
+      priv->item_appearance = item_appearance;
+
+      glade_palette_update_appearance (palette);
+
+      g_object_notify (G_OBJECT (palette), "item-appearance");
+    }
+}
+
+/**
+ * glade_palette_set_use_small_item_icons:
+ * @palette: a #GladePalette
+ * @use_small_item_icons: Whether to use small item icons
+ *
+ * Sets whether to use small item icons.
+ */
+void
+glade_palette_set_use_small_item_icons (GladePalette * palette,
+                                        gboolean use_small_item_icons)
+{
+  GladePalettePrivate *priv;
+  g_return_if_fail (GLADE_IS_PALETTE (palette));
+  priv = palette->priv;
 
-  if (palette->priv->current_item)
+  if (priv->use_small_item_icons != use_small_item_icons)
     {
-      gtk_toggle_tool_button_set_active (GTK_TOGGLE_TOOL_BUTTON
-                                         (palette->priv->current_item), FALSE);
-      gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON
-                                    (palette->priv->selector_button), TRUE);
-      gtk_toggle_button_set_active (GTK_TOGGLE_BUTTON
-                                    (palette->priv->create_root_button), FALSE);
+      priv->use_small_item_icons = use_small_item_icons;
+
+      glade_palette_update_appearance (palette);
 
-      palette->priv->current_item = NULL;
-      g_object_notify (G_OBJECT (palette), "current-item");
+      g_object_notify (G_OBJECT (palette), "use-small-item-icons");
 
-      glade_app_set_pointer_mode (GLADE_POINTER_SELECT);
+    }
 
-      g_signal_emit (G_OBJECT (palette), glade_palette_signals[TOGGLED], 0);
+}
+
+/**
+ * glade_palette_set_show_selector_button:
+ * @palette: a #GladePalette
+ * @show_selector_button: whether to show selector button
+ *
+ * Sets whether to show the internal widget selector button
+ */
+void
+glade_palette_set_show_selector_button (GladePalette * palette,
+                                        gboolean show_selector_button)
+{
+  GladePalettePrivate *priv;
+  g_return_if_fail (GLADE_IS_PALETTE (palette));
+  priv = palette->priv;
+
+  if (gtk_widget_get_visible (priv->selector_hbox) != show_selector_button)
+    {
+      if (show_selector_button)
+        gtk_widget_show (priv->selector_hbox);
+      else
+        gtk_widget_hide (priv->selector_hbox);
+
+      g_object_notify (G_OBJECT (palette), "show-selector-button");
 
     }
 
@@ -969,17 +921,3 @@ glade_palette_get_show_selector_button (GladePalette * palette)
 
   return gtk_widget_get_visible (palette->priv->selector_hbox);
 }
-
-/**
- * glade_palette_refresh:
- * @palette: a #GladePalette
- *
- * Refreshes project dependant states of palette buttons
- */
-static void
-glade_palette_refresh (GladePalette * palette)
-{
-  g_return_if_fail (GLADE_IS_PALETTE (palette));
-
-  g_signal_emit (G_OBJECT (palette), glade_palette_signals[REFRESH], 0);
-}
diff --git a/gladeui/glade-palette.h b/gladeui/glade-palette.h
index 64aab95..efea332 100644
--- a/gladeui/glade-palette.h
+++ b/gladeui/glade-palette.h
@@ -56,7 +56,6 @@ struct _GladePaletteClass
 {
   GtkVBoxClass parent_class;
 
-  void    (* toggled)    (GladePalette *palette);
   void    (* refresh)    (GladePalette *palette);
 };
 
@@ -70,17 +69,12 @@ typedef enum
 
 GType                glade_palette_get_type                 (void) G_GNUC_CONST;
 
-GtkWidget           *glade_palette_new                      (const GList  *catalogs);
+GtkWidget           *glade_palette_new                      (void);
 
 GladeProject        *glade_palette_get_project              (GladePalette *palette);
 void                 glade_palette_set_project              (GladePalette *palette,
 							     GladeProject *project);
 
-void                 glade_palette_deselect_current_item    (GladePalette *palette,
-							     gboolean      sticky_aware);
-
-GladeWidgetAdaptor  *glade_palette_get_current_item         (GladePalette *palette);
-
 GladeItemAppearance  glade_palette_get_item_appearance      (GladePalette *palette);
 
 void                 glade_palette_set_item_appearance      (GladePalette       *palette,
@@ -96,9 +90,6 @@ void		     glade_palette_set_show_selector_button (GladePalette *palette,
 							     
 gboolean             glade_palette_get_show_selector_button (GladePalette *palette);
 
-GladeWidget         *glade_palette_create_root_widget       (GladePalette *palette,
-							     GladeWidgetAdaptor *adaptor);
-
 G_END_DECLS
 
 #endif /* __GLADE_PALETTE_H__ */
diff --git a/gladeui/glade-placeholder.c b/gladeui/glade-placeholder.c
index 06d5a68..bdefaeb 100644
--- a/gladeui/glade-placeholder.c
+++ b/gladeui/glade-placeholder.c
@@ -407,6 +407,7 @@ glade_placeholder_motion_notify_event (GtkWidget * widget,
 {
   GladePointerMode pointer_mode;
   GladeWidget *gparent, *gparent_parent = NULL;
+  GladeProject *project;
 
   g_return_val_if_fail (GLADE_IS_PLACEHOLDER (widget), FALSE);
 
@@ -414,7 +415,8 @@ glade_placeholder_motion_notify_event (GtkWidget * widget,
   if (gparent)
     gparent_parent = glade_widget_get_parent (gparent);
 
-  pointer_mode = glade_app_get_pointer_mode ();
+  project      = glade_placeholder_get_project (GLADE_PLACEHOLDER (widget));
+  pointer_mode = glade_project_get_pointer_mode (project);
 
   if (pointer_mode == GLADE_POINTER_SELECT &&
       /* If we are the child of a widget that is in a GladeFixed, then
@@ -423,9 +425,9 @@ glade_placeholder_motion_notify_event (GtkWidget * widget,
        * concurrencies I suppose).
        */
       (gparent_parent && GLADE_IS_FIXED (gparent_parent)) == FALSE)
-    glade_cursor_set (event->window, GLADE_CURSOR_SELECTOR);
+    glade_cursor_set (project, event->window, GLADE_CURSOR_SELECTOR);
   else if (pointer_mode == GLADE_POINTER_ADD_WIDGET)
-    glade_cursor_set (event->window, GLADE_CURSOR_ADD_WIDGET);
+    glade_cursor_set (project, event->window, GLADE_CURSOR_ADD_WIDGET);
 
   return FALSE;
 }
@@ -433,19 +435,16 @@ glade_placeholder_motion_notify_event (GtkWidget * widget,
 static gboolean
 glade_placeholder_button_press (GtkWidget * widget, GdkEventButton * event)
 {
-  GladePlaceholder *placeholder;
-  GladeProject *project;
+  GladePlaceholder   *placeholder;
+  GladeProject       *project;
   GladeWidgetAdaptor *adaptor;
-  GladePalette *palette;
-  gboolean handled = FALSE;
+  gboolean            handled = FALSE;
 
   g_return_val_if_fail (GLADE_IS_PLACEHOLDER (widget), FALSE);
 
-  adaptor = glade_palette_get_current_item (glade_app_get_palette ());
-
-  palette = glade_app_get_palette ();
   placeholder = GLADE_PLACEHOLDER (widget);
-  project = glade_placeholder_get_project (placeholder);
+  project     = glade_placeholder_get_project (placeholder);
+  adaptor     = glade_project_get_add_item (project);
 
   if (!gtk_widget_has_focus (widget))
     gtk_widget_grab_focus (widget);
@@ -464,11 +463,10 @@ glade_placeholder_button_press (GtkWidget * widget, GdkEventButton * event)
                */
               glade_command_create (adaptor, parent, placeholder, project);
 
-              glade_palette_deselect_current_item (glade_app_get_palette (),
-                                                   TRUE);
+	      glade_project_set_add_item (project, NULL);
 
               /* reset the cursor */
-              glade_cursor_set (event->window, GLADE_CURSOR_SELECTOR);
+              glade_cursor_set (project, event->window, GLADE_CURSOR_SELECTOR);
             }
           handled = TRUE;
         }
diff --git a/gladeui/glade-popup.c b/gladeui/glade-popup.c
index 02b0e3f..5b66850 100644
--- a/gladeui/glade-popup.c
+++ b/gladeui/glade-popup.c
@@ -94,35 +94,37 @@ glade_popup_placeholder_add_cb (GtkMenuItem * item,
                                 GladePlaceholder * placeholder)
 {
   GladeWidgetAdaptor *adaptor;
-  GladeWidget *parent;
+  GladeWidget        *parent;
+  GladeProject       *project;
 
-  adaptor = glade_palette_get_current_item (glade_app_get_palette ());
-  g_return_if_fail (adaptor != NULL);
 
-  parent = glade_placeholder_get_parent (placeholder);
+  parent  = glade_placeholder_get_parent (placeholder);
+  project = glade_placeholder_get_project (placeholder);
+  adaptor = glade_project_get_add_item (project);
+
+  g_return_if_fail (adaptor != NULL);
 
   if (!glade_util_check_and_warn_scrollable
       (parent, adaptor, glade_app_get_window ()))
     {
       glade_command_create (adaptor, parent,
                             placeholder,
-                            glade_placeholder_get_project (placeholder));
+                            project);
 
-      glade_palette_deselect_current_item (glade_app_get_palette (), TRUE);
+      glade_project_set_add_item (project, NULL);
     }
 }
 
+typedef struct {
+  GladeWidgetAdaptor *adaptor;
+  GladeProject       *project;
+} RootAddData;
+
 static void
-glade_popup_root_add_cb (GtkMenuItem * item, gpointer * user_data)
+glade_popup_root_add_cb (GtkMenuItem *item, 
+			 RootAddData *data)
 {
-  GladeWidgetAdaptor *adaptor = (GladeWidgetAdaptor *) user_data;
-  GladePalette *palette = glade_app_get_palette ();
-
-  if (!adaptor)
-    adaptor = glade_palette_get_current_item (palette);
-  g_return_if_fail (adaptor != NULL);
-
-  glade_palette_create_root_widget (palette, adaptor);
+  glade_command_create (data->adaptor, NULL, NULL, data->project);
 }
 
 static void
@@ -414,20 +416,29 @@ glade_popup_create_menu (GladeWidget      *widget,
 			 GladeProject     *project,
 			 gboolean          packing)
 {
-  GtkWidget *popup_menu;
-  GtkWidget *separator;
-  gboolean sensitive;
-  GladePlaceholder *tmp_placeholder;
-  gchar *book;
+  GtkWidget          *popup_menu;
+  GtkWidget          *separator;
+  gboolean            sensitive;
+  GladePlaceholder   *tmp_placeholder;
+  GladeWidgetAdaptor *adaptor;
+  gchar              *book;
 
   popup_menu = gtk_menu_new ();
 
-  if (glade_palette_get_current_item (glade_app_get_palette ()))
+  adaptor = glade_project_get_add_item (project);
+
+  if (adaptor)
     {
+      RootAddData *data = g_new (RootAddData, 1);
+
+      data->adaptor = adaptor;
+      data->project = project;
+      g_object_set_data_full (G_OBJECT (popup_menu), "root-data-destroy-me", 
+			      data, (GDestroyNotify)g_free);
+
       tmp_placeholder = placeholder;
       if (!tmp_placeholder && widget)
-	tmp_placeholder =
-	  find_placeholder (glade_widget_get_object (widget));
+	tmp_placeholder = find_placeholder (glade_widget_get_object (widget));
 
       glade_popup_append_item (popup_menu, NULL, _("_Add widget here"),
 			       NULL, tmp_placeholder != NULL,
@@ -435,7 +446,7 @@ glade_popup_create_menu (GladeWidget      *widget,
 			       tmp_placeholder);
 
       glade_popup_append_item (popup_menu, NULL, _("Add widget as _toplevel"),
-                               NULL, TRUE, glade_popup_root_add_cb, NULL);
+                               NULL, TRUE, glade_popup_root_add_cb, data);
 
       separator = gtk_menu_item_new ();
       gtk_menu_shell_append (GTK_MENU_SHELL (popup_menu), separator);
@@ -596,6 +607,7 @@ glade_popup_palette_pop (GladePalette       *palette,
   gchar *book = NULL;
   gint button;
   gint event_time;
+  RootAddData *data;
 
   g_return_if_fail (GLADE_IS_WIDGET_ADAPTOR (adaptor));
 
@@ -603,8 +615,14 @@ glade_popup_palette_pop (GladePalette       *palette,
 
   project = glade_palette_get_project (palette);
 
+  data = g_new (RootAddData, 1);
+  data->adaptor = adaptor;
+  data->project = project;
+  g_object_set_data_full (G_OBJECT (popup_menu), "root-data-destroy-me", 
+			  data, (GDestroyNotify)g_free);
+
   glade_popup_append_item (popup_menu, NULL, _("Add widget as _toplevel"), NULL,
-                           TRUE, glade_popup_root_add_cb, adaptor);
+                           TRUE, glade_popup_root_add_cb, data);
 
   g_object_get (adaptor, "book", &book, NULL);
   if (book && glade_util_have_devhelp ())
diff --git a/gladeui/glade-project.c b/gladeui/glade-project.c
index da30e8c..4bc7ee1 100644
--- a/gladeui/glade-project.c
+++ b/gladeui/glade-project.c
@@ -74,7 +74,9 @@ enum
   PROP_HAS_SELECTION,
   PROP_PATH,
   PROP_READ_ONLY,
-  PROP_PREVIEWABLE
+  PROP_PREVIEWABLE,
+  PROP_ADD_ITEM,
+  PROP_POINTER_MODE
 };
 
 struct _GladeProjectPrivate
@@ -83,17 +85,8 @@ struct _GladeProjectPrivate
 
   gint unsaved_number;          /* A unique number for this project if it is untitled */
 
-  gboolean readonly;            /* A flag that is set if the project is readonly */
-
-  gboolean loading;             /* A flags that is set when the project is loading */
-
-  gboolean modified;            /* A flag that is set when a project has unsaved modifications
-                                 * if this flag is not set we don't have to query
-                                 * for confirmation after a close or exit is
-                                 * requested
-                                 */
-
-  gboolean previewable;
+  GladeWidgetAdaptor *add_item; /* The next item to add to the project.
+				 */
 
   gint stamp;                   /* A a random int per instance of project used to stamp/check the
                                  * GtkTreeIter->stamps */
@@ -107,7 +100,6 @@ struct _GladeProjectPrivate
                                  * of #GtkWidget items.
                                  */
   guint selection_changed_id;
-  gboolean has_selection;       /* Whether the project has a selection */
 
   GladeNameContext *toplevel_names;     /* Context for uniqueness of names at the toplevel */
   GList *toplevels;                     /* List of toplevels with thier own naming contexts */
@@ -116,8 +108,6 @@ struct _GladeProjectPrivate
   GList *undo_stack;            /* A stack with the last executed commands */
   GList *prev_redo_item;        /* Points to the item previous to the redo items */
 
-  gboolean first_modification_is_na;    /* the flag indicates that  the first_modification item has been lost */
-
   GList *first_modification;    /* we record the first modification, so that we
                                  * can set "modification" to FALSE when we
                                  * undo this modification
@@ -152,13 +142,26 @@ struct _GladeProjectPrivate
   GtkWidget *relative_path_entry;
   GtkWidget *full_path_button;
 
+  /* Store preview processes, so we can kill them on close */
+  GHashTable *preview_channels;
+
   /* For the loading progress bars ("load-progress" signal) */
   gint progress_step;
   gint progress_full;
-  gboolean load_cancel;
 
-  /* Store preview processes, so we can kill them on close */
-  GHashTable *preview_channels;
+  /* Flags */
+  guint load_cancel : 1;
+  guint first_modification_is_na : 1;  /* indicates that the first_modification item has been lost */
+  guint has_selection : 1;       /* Whether the project has a selection */
+  guint previewable : 1;
+  guint readonly : 1;            /* A flag that is set if the project is readonly */
+  guint loading : 1;             /* A flags that is set when the project is loading */
+  guint modified : 1;            /* A flag that is set when a project has unsaved modifications
+				  * if this flag is not set we don't have to query
+				  * for confirmation after a close or exit is
+				  * requested
+				  */
+  guint pointer_mode : 2;        /* The currently effective GladePointerMode */
 };
 
 typedef struct
@@ -180,6 +183,24 @@ typedef struct
 } ChannelWatchPair;
 
 
+GType
+glade_pointer_mode_get_type (void)
+{
+  static GType etype = 0;
+
+  if (etype == 0)
+    {
+      static const GEnumValue values[] = {
+        {GLADE_POINTER_SELECT, "select", "Select widgets"},
+        {GLADE_POINTER_ADD_WIDGET, "add", "Add widgets"},
+        {GLADE_POINTER_DRAG_RESIZE, "drag-resize", "Drag and resize widgets"},
+        {0, NULL, NULL}
+      };
+      etype = g_enum_register_static ("GladePointerMode", values);
+    }
+  return etype;
+}
+
 static void glade_project_set_target_version (GladeProject * project,
                                               const gchar * catalog,
                                               guint16 major, guint16 minor);
@@ -231,10 +252,12 @@ static void glade_project_model_get_iter_for_object (GladeProject * project,
 G_DEFINE_TYPE_WITH_CODE (GladeProject, glade_project, G_TYPE_OBJECT,
                          G_IMPLEMENT_INTERFACE (GTK_TYPE_TREE_MODEL,
                                                 gtk_tree_model_iface_init))
+
+
 /*******************************************************************
                             GObjectClass
  *******************************************************************/
-     static GladeIDAllocator *get_unsaved_number_allocator (void)
+static GladeIDAllocator *get_unsaved_number_allocator (void)
 {
   if (unsaved_number_allocator == NULL)
     unsaved_number_allocator = glade_id_allocator_new ();
@@ -357,24 +380,30 @@ glade_project_get_property (GObject * object,
 
   switch (prop_id)
     {
-      case PROP_MODIFIED:
-        g_value_set_boolean (value, project->priv->modified);
-        break;
-      case PROP_HAS_SELECTION:
-        g_value_set_boolean (value, project->priv->has_selection);
-        break;
-      case PROP_PATH:
-        g_value_set_string (value, project->priv->path);
-        break;
-      case PROP_READ_ONLY:
-        g_value_set_boolean (value, project->priv->readonly);
-        break;
-      case PROP_PREVIEWABLE:
-        g_value_set_boolean (value, project->priv->previewable);
-        break;
-      default:
-        G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
-        break;
+    case PROP_MODIFIED:
+      g_value_set_boolean (value, project->priv->modified);
+      break;
+    case PROP_HAS_SELECTION:
+      g_value_set_boolean (value, project->priv->has_selection);
+      break;
+    case PROP_PATH:
+      g_value_set_string (value, project->priv->path);
+      break;
+    case PROP_READ_ONLY:
+      g_value_set_boolean (value, project->priv->readonly);
+      break;
+    case PROP_PREVIEWABLE:
+      g_value_set_boolean (value, project->priv->previewable);
+      break;
+    case PROP_ADD_ITEM:
+      g_value_set_object (value, project->priv->add_item);
+      break;
+    case PROP_POINTER_MODE:
+      g_value_set_enum (value, project->priv->pointer_mode);
+      break;
+    default:
+      G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
+      break;
     }
 }
 
@@ -397,7 +426,11 @@ glade_project_get_property (GObject * object,
 static void
 glade_project_set_modified (GladeProject * project, gboolean modified)
 {
-  GladeProjectPrivate *priv = project->priv;
+  GladeProjectPrivate *priv;
+
+  g_return_if_fail (GLADE_IS_PROJECT (project));
+
+  priv = project->priv;
 
   if (priv->modified != modified)
     {
@@ -413,6 +446,71 @@ glade_project_set_modified (GladeProject * project, gboolean modified)
     }
 }
 
+/**
+ * glade_project_get_modified:
+ * @project: a #GladeProject
+ *
+ * Get's whether the project has been modified since it was last saved.
+ *
+ * Returns: %TRUE if the project has been modified since it was last saved
+ */
+gboolean
+glade_project_get_modified (GladeProject * project)
+{
+  g_return_val_if_fail (GLADE_IS_PROJECT (project), FALSE);
+
+  return project->priv->modified;
+}
+
+void
+glade_project_set_pointer_mode (GladeProject       *project,
+				GladePointerMode    mode)
+{
+  g_return_if_fail (GLADE_IS_PROJECT (project));
+
+  if (project->priv->pointer_mode != mode)
+    {
+      project->priv->pointer_mode = mode;
+
+      g_object_notify (G_OBJECT (project), "pointer-mode");
+    }
+}
+
+GladePointerMode
+glade_project_get_pointer_mode (GladeProject *project)
+{
+  g_return_val_if_fail (GLADE_IS_PROJECT (project), FALSE);
+
+  return project->priv->pointer_mode;
+}
+
+
+void
+glade_project_set_add_item (GladeProject       *project,
+			    GladeWidgetAdaptor *adaptor)
+{
+  GladeProjectPrivate *priv;
+
+  g_return_if_fail (GLADE_IS_PROJECT (project));
+
+  priv = project->priv;
+
+  if (priv->add_item != adaptor)
+    {
+      priv->add_item = adaptor;
+
+      g_object_notify (G_OBJECT (project), "add-item");
+    }
+}
+
+GladeWidgetAdaptor *
+glade_project_get_add_item (GladeProject *project)
+{
+  g_return_val_if_fail (GLADE_IS_PROJECT (project), NULL);
+
+  return project->priv->add_item;
+}
+
 /*******************************************************************
                           GladeProjectClass
  *******************************************************************/
@@ -938,7 +1036,22 @@ glade_project_class_init (GladeProjectClass * klass)
                                                          FALSE,
                                                          G_PARAM_READABLE));
 
+  g_object_class_install_property (object_class,
+                                   PROP_ADD_ITEM,
+                                   g_param_spec_object ("add-item",
+							_("Add Item"),
+							_("The current item to add to the project"),
+							GLADE_TYPE_WIDGET_ADAPTOR,
+							G_PARAM_READABLE));
 
+  g_object_class_install_property (object_class,
+                                   PROP_POINTER_MODE,
+                                   g_param_spec_enum ("pointer-mode",
+						      _("Pointer Mode"),
+						      _("The currently effective GladePointerMode"),
+						      GLADE_TYPE_POINTER_MODE,
+						      GLADE_POINTER_SELECT,
+						      G_PARAM_READABLE));
 
   g_type_class_add_private (klass, sizeof (GladeProjectPrivate));
 }
@@ -3745,22 +3858,6 @@ glade_project_get_objects (GladeProject * project)
   return project->priv->objects;
 }
 
-/** 
- * glade_project_get_modified:
- * @project: a #GladeProject
- *
- * Get's whether the project has been modified since it was last saved.
- *
- * Returns: #TRUE if the project has been modified since it was last saved
- */
-gboolean
-glade_project_get_modified (GladeProject * project)
-{
-  g_return_val_if_fail (GLADE_IS_PROJECT (project), FALSE);
-
-  return project->priv->modified;
-}
-
 void
 glade_project_set_naming_policy (GladeProject * project,
                                  GladeNamingPolicy policy)
diff --git a/gladeui/glade-project.h b/gladeui/glade-project.h
index fa64862..99b2bce 100644
--- a/gladeui/glade-project.h
+++ b/gladeui/glade-project.h
@@ -15,16 +15,35 @@ G_BEGIN_DECLS
 #define GLADE_IS_PROJECT(obj)         (G_TYPE_CHECK_INSTANCE_TYPE ((obj), GLADE_TYPE_PROJECT))
 #define GLADE_IS_PROJECT_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), GLADE_TYPE_PROJECT))
 #define GLADE_PROJECT_GET_CLASS(obj)  (G_TYPE_INSTANCE_GET_CLASS ((obj), GLADE_TYPE_PROJECT, GladeProjectClass))
+#define GLADE_TYPE_POINTER_MODE       (glade_pointer_mode_get_type())
 
 typedef struct _GladeProjectPrivate  GladeProjectPrivate;
 typedef struct _GladeProjectClass    GladeProjectClass;
+typedef enum   _GladePointerMode     GladePointerMode;
+typedef enum   _GladeSupportMask     GladeSupportMask;
 
-typedef enum
+/**
+ * GladePointerMode:
+ * @GLADE_POINTER_SELECT:      Mouse pointer used for selecting widgets
+ * @GLADE_POINTER_ADD_WIDGET:  Mouse pointer used for adding widgets
+ * @GLADE_POINTER_DRAG_RESIZE: Mouse pointer used for dragging and 
+ *                             resizing widgets in containers
+ *
+ * Indicates what the pointer is used for in the workspace.
+ */
+enum _GladePointerMode
 {
-	GLADE_SUPPORT_OK                   = 0,
-	GLADE_SUPPORT_DEPRECATED           = (0x01 << 0),
-	GLADE_SUPPORT_MISMATCH             = (0x01 << 1)
-} GladeSupportMask;
+  GLADE_POINTER_SELECT = 0,
+  GLADE_POINTER_ADD_WIDGET,
+  GLADE_POINTER_DRAG_RESIZE
+};
+
+enum _GladeSupportMask
+{
+  GLADE_SUPPORT_OK                   = 0,
+  GLADE_SUPPORT_DEPRECATED           = (0x01 << 0),
+  GLADE_SUPPORT_MISMATCH             = (0x01 << 1)
+};
 
 /**
  * GladeProjectModelColumns:
@@ -83,147 +102,121 @@ struct _GladeProjectClass
 };
 
 
-GType          glade_project_get_type            (void) G_GNUC_CONST;
-
-GladeProject  *glade_project_new                 (void);
-
-GladeProject  *glade_project_load                (const gchar  *path);
-gboolean       glade_project_load_from_file      (GladeProject *project, 
-						  const gchar  *path);
-
-gboolean       glade_project_save                (GladeProject *project, 
-						  const gchar   *path, 
-						  GError       **error);
-
-void           glade_project_preview             (GladeProject *project, GladeWidget *gwidget);
-
-const gchar   *glade_project_get_path            (GladeProject *project);
-
-gchar         *glade_project_get_name            (GladeProject *project);
-
-
-void           glade_project_undo                (GladeProject *project);
-
-void           glade_project_redo                (GladeProject *project);
-
-GladeCommand  *glade_project_next_undo_item      (GladeProject *project);
-
-GladeCommand  *glade_project_next_redo_item      (GladeProject *project);
-
-void           glade_project_push_undo           (GladeProject *project, 
-						  GladeCommand *cmd);
-
-GtkWidget     *glade_project_undo_items          (GladeProject *project);
-
-GtkWidget     *glade_project_redo_items          (GladeProject *project);
-
-void           glade_project_reset_path          (GladeProject *project);
-
-gboolean       glade_project_get_readonly        (GladeProject *project);
-
-const GList   *glade_project_get_objects         (GladeProject *project);
-
-void           glade_project_add_object          (GladeProject *project, 
-						  GObject      *object);
-
-void           glade_project_remove_object       (GladeProject *project, 
-						  GObject      *object);
-
-gboolean       glade_project_has_object          (GladeProject *project, 
-						  GObject      *object);
+GType               glade_pointer_mode_get_type       (void) G_GNUC_CONST;
+GType               glade_project_get_type            (void) G_GNUC_CONST;
+
+GladeProject       *glade_project_new                 (void);
+GladeProject       *glade_project_load                (const gchar         *path);
+gboolean            glade_project_load_from_file      (GladeProject        *project, 
+						       const gchar         *path);
+gboolean            glade_project_save                (GladeProject        *project, 
+						       const gchar         *path, 
+						       GError             **error);
+void                glade_project_push_progress        (GladeProject       *project);
+gboolean            glade_project_load_cancelled       (GladeProject       *project);
+void                glade_project_cancel_load          (GladeProject       *project);
+
+void                glade_project_preview              (GladeProject       *project, 
+							GladeWidget        *gwidget);
+void                glade_project_preferences          (GladeProject       *project);
+
+/* Commands */
+void                glade_project_undo                 (GladeProject       *project);
+void                glade_project_redo                 (GladeProject       *project);
+GladeCommand       *glade_project_next_undo_item       (GladeProject       *project);
+GladeCommand       *glade_project_next_redo_item       (GladeProject       *project);
+void                glade_project_push_undo            (GladeProject       *project, 
+							GladeCommand       *cmd);
+GtkWidget          *glade_project_undo_items           (GladeProject       *project);
+GtkWidget          *glade_project_redo_items           (GladeProject       *project);
+
+/* Add/Remove Objects */
+const GList        *glade_project_get_objects          (GladeProject       *project);
+void                glade_project_add_object           (GladeProject       *project, 
+							GObject            *object);
+void                glade_project_remove_object        (GladeProject       *project, 
+							GObject            *object);
+gboolean            glade_project_has_object           (GladeProject       *project, 
+							GObject            *object);
+gchar              *glade_project_resource_fullpath    (GladeProject       *project,
+							const gchar        *resource);
+
+/* Widget names */
+GladeWidget        *glade_project_get_widget_by_name   (GladeProject       *project, 
+							GladeWidget        *ancestor,
+							const gchar        *name);
+void                glade_project_set_widget_name      (GladeProject       *project, 
+							GladeWidget        *widget, 
+							const gchar        *name);
+gchar              *glade_project_new_widget_name      (GladeProject       *project, 
+							GladeWidget        *widget, 
+							const gchar        *base_name);
+gboolean            glade_project_available_widget_name(GladeProject       *project, 
+							GladeWidget        *widget,
+							const gchar        *name);
 
-GladeWidget   *glade_project_get_widget_by_name  (GladeProject *project, 
-						  GladeWidget  *ancestor,
-						  const gchar  *name);
-
-void           glade_project_set_widget_name     (GladeProject *project, 
-						  GladeWidget  *widget, 
-						  const gchar  *name);
-
-gchar         *glade_project_new_widget_name     (GladeProject *project, 
-						  GladeWidget  *widget, 
-						  const gchar  *base_name);
-
-gboolean       glade_project_available_widget_name (GladeProject *project, GladeWidget  *widget,
-						    const gchar  *name);
 
 /* Selection */
-
-gboolean       glade_project_is_selected         (GladeProject *project,
-						  GObject      *object);
-
-void           glade_project_selection_set       (GladeProject *project,
-						  GObject      *object,
-						  gboolean      emit_signal);
-
-void           glade_project_selection_add       (GladeProject *project,
-						  GObject      *object,
-						  gboolean      emit_signal);
-
-void           glade_project_selection_remove    (GladeProject *project,
-						  GObject      *object,
-						  gboolean      emit_signal);
-
-void           glade_project_selection_clear     (GladeProject *project,
-						  gboolean      emit_signal);
-
-void           glade_project_selection_changed   (GladeProject *project);
-void           glade_project_queue_selection_changed (GladeProject *project);
-
-GList         *glade_project_selection_get       (GladeProject *project);
-
-gboolean       glade_project_get_has_selection   (GladeProject *project);
-
-gchar         *glade_project_resource_fullpath    (GladeProject  *project,
-						   const gchar   *resource);
- 
-gboolean       glade_project_is_loading           (GladeProject *project);
- 
-time_t         glade_project_get_file_mtime       (GladeProject *project);
-
-gboolean       glade_project_get_modified         (GladeProject *project);
-
-gboolean       glade_project_get_previewable      (GladeProject *project);
-
-void           glade_project_preferences          (GladeProject *project);
-
-void           glade_project_verify_properties    (GladeWidget  *widget);
-
-gchar         *glade_project_verify_widget_adaptor (GladeProject       *project,
-						    GladeWidgetAdaptor *adaptor,
-						    GladeSupportMask   *mask);
-
-void          glade_project_verify_project_for_ui (GladeProject  *project);
-
-GList        *glade_project_required_libs          (GladeProject       *project);
-
-void          glade_project_set_naming_policy      (GladeProject       *project,
-						    GladeNamingPolicy   policy);
-
-GladeNamingPolicy glade_project_get_naming_policy  (GladeProject       *project);
-void          glade_project_get_target_version     (GladeProject       *project,
-						    const gchar        *catalog,
-						    gint               *major,
-						    gint               *minor);
-
-void          glade_project_verify_property        (GladeProperty      *property);
-void          glade_project_verify_signal          (GladeWidget        *widget,
-						    GladeSignal        *signal);
-
-
-gchar        *glade_project_display_dependencies (GladeProject *project);
-
-void          glade_project_push_progress (GladeProject *project);
-gboolean      glade_project_load_cancelled (GladeProject *project);
-void          glade_project_cancel_load (GladeProject *project);
-
-
-/* Command central */
-void          glade_project_copy_selection (GladeProject     *project);
-void          glade_project_command_cut    (GladeProject     *project); 
-void          glade_project_command_paste  (GladeProject     *project, 
-					    GladePlaceholder *placeholder);
-void          glade_project_command_delete (GladeProject     *project);
+gboolean            glade_project_is_selected          (GladeProject       *project,
+							GObject            *object);
+void                glade_project_selection_set        (GladeProject       *project,
+							GObject            *object,
+							gboolean            emit_signal);
+void                glade_project_selection_add        (GladeProject       *project,
+							GObject            *object,
+							gboolean            emit_signal);
+void                glade_project_selection_remove     (GladeProject       *project,
+							GObject            *object,
+							gboolean            emit_signal);
+void                glade_project_selection_clear      (GladeProject       *project,
+							gboolean            emit_signal);
+void                glade_project_selection_changed    (GladeProject       *project);
+void                glade_project_queue_selection_changed (GladeProject    *project);
+GList              *glade_project_selection_get        (GladeProject       *project);
+gboolean            glade_project_get_has_selection    (GladeProject       *project);
+
+/* Accessors */ 
+const gchar        *glade_project_get_path             (GladeProject       *project);
+gchar              *glade_project_get_name             (GladeProject       *project);
+void                glade_project_reset_path           (GladeProject       *project);
+gboolean            glade_project_is_loading           (GladeProject       *project);
+time_t              glade_project_get_file_mtime       (GladeProject       *project);
+gboolean            glade_project_get_readonly         (GladeProject       *project);
+gboolean            glade_project_get_modified         (GladeProject       *project);
+gboolean            glade_project_get_previewable      (GladeProject       *project);
+gboolean            glade_project_get_previewable      (GladeProject       *project);
+void                glade_project_set_pointer_mode     (GladeProject       *project,
+							GladePointerMode    mode);
+GladePointerMode    glade_project_get_pointer_mode     (GladeProject       *project);
+void                glade_project_set_add_item         (GladeProject       *project,
+							GladeWidgetAdaptor *adaptor);
+GladeWidgetAdaptor *glade_project_get_add_item         (GladeProject       *project);
+void                glade_project_set_naming_policy    (GladeProject       *project,
+							GladeNamingPolicy   policy);
+GladeNamingPolicy   glade_project_get_naming_policy    (GladeProject       *project);
+void                glade_project_get_target_version   (GladeProject       *project,
+							const gchar        *catalog,
+							gint               *major,
+							gint               *minor);
+GList              *glade_project_required_libs        (GladeProject       *project);
+gchar              *glade_project_display_dependencies (GladeProject       *project);
+
+/* Verifications */
+void                glade_project_verify_properties    (GladeWidget        *widget);
+gchar              *glade_project_verify_widget_adaptor(GladeProject       *project,
+							GladeWidgetAdaptor *adaptor,
+							GladeSupportMask   *mask);
+void                glade_project_verify_project_for_ui(GladeProject       *project);
+void                glade_project_verify_property      (GladeProperty      *property);
+void                glade_project_verify_signal        (GladeWidget        *widget,
+							GladeSignal        *signal);
+
+/* General selection driven commands */
+void                glade_project_copy_selection       (GladeProject       *project);
+void                glade_project_command_cut          (GladeProject       *project); 
+void                glade_project_command_paste        (GladeProject       *project, 
+							GladePlaceholder   *placeholder);
+void                glade_project_command_delete       (GladeProject       *project);
 
 G_END_DECLS
 
diff --git a/src/glade-window.c b/src/glade-window.c
index 5f024b6..8c8e065 100644
--- a/src/glade-window.c
+++ b/src/glade-window.c
@@ -103,8 +103,8 @@ struct _GladeWindowPrivate
 
   GtkWidget *inspectors_notebook;
 
-  GladeEditor *editor;                  /* The editor */
-
+  GladeEditor  *editor;                 /* The editor */
+  GladePalette *palette;                /* The palette */
 
   GtkWidget *statusbar;                 /* A pointer to the status bar. */
   guint statusbar_menu_context_id;      /* The context id of the menu bar */
@@ -124,7 +124,6 @@ struct _GladeWindowPrivate
 
   GtkToggleToolButton *selector_button; /* the widget selector button (replaces the one in the palette) */
   GtkToggleToolButton *drag_resize_button;      /* sets the pointer to drag/resize mode */
-  gboolean setting_pointer_mode;        /* avoid feedback signal loops */
 
   GtkToolItem *undo;            /* customized buttons for undo/redo with history */
   GtkToolItem *redo;
@@ -462,16 +461,24 @@ add_actions (GladeWindow * window, GladeWidget * widget, GList * actions)
     clean_actions (window);
 }
 
+static GladeProject *
+get_active_project (GladeWindow *window)
+{
+  if (window->priv->active_view)
+    return glade_design_view_get_project (window->priv->active_view);
+
+  return NULL;
+}
+
 static void
 project_selection_changed_cb (GladeProject * project, GladeWindow * window)
 {
-  GladeProject *active_project = NULL;
+  GladeProject *active_project;
   GladeWidget  *glade_widget = NULL;
   GList        *list;
   gint          num;
 
-  if (window->priv->active_view)
-    active_project = glade_design_view_get_project (window->priv->active_view);
+  active_project = get_active_project (window);
 
   /* This is sometimes called with a NULL project (to make the label
    * insensitive with no projects loaded)
@@ -616,9 +623,7 @@ project_changed_cb (GladeProject *project,
 		    gboolean      execute,
 		    GladeWindow  *window)
 {
-  GladeProject *active_project;
-
-  active_project = glade_design_view_get_project (window->priv->active_view);
+  GladeProject *active_project = get_active_project (window);
   
   if (project == active_project)
     refresh_undo_redo (window, project);
@@ -708,11 +713,9 @@ static void
 project_notify_handler_cb (GladeProject * project, GParamSpec * spec,
                            GladeWindow * window)
 {
-  GladeProject *active_project;
+  GladeProject *active_project = get_active_project (window);
   GtkAction    *action;
 
-  active_project = glade_design_view_get_project (window->priv->active_view);
-
   if (strcmp (spec->name, "path") == 0 || strcmp (spec->name, "format") == 0)
     refresh_notebook_tab_for_project (window, project);
   else if (strcmp (spec->name, "modified") == 0)
@@ -766,54 +769,79 @@ clipboard_notify_handler_cb (GladeClipboard * clipboard, GParamSpec * spec,
 static void
 on_selector_button_toggled (GtkToggleToolButton * button, GladeWindow * window)
 {
-  if (window->priv->setting_pointer_mode)
-    return;
+  GladeProject *active_project = get_active_project (window);
 
   if (gtk_toggle_tool_button_get_active (window->priv->selector_button))
     {
-      glade_palette_deselect_current_item (glade_app_get_palette (), FALSE);
-      glade_app_set_pointer_mode (GLADE_POINTER_SELECT);
+      glade_project_set_add_item (active_project, NULL);
+      glade_project_set_pointer_mode (active_project, GLADE_POINTER_SELECT);
     }
   else
     gtk_toggle_tool_button_set_active (window->priv->selector_button, TRUE);
 }
 
 static void
-on_drag_resize_button_toggled (GtkToggleToolButton * button,
-                               GladeWindow * window)
+on_drag_resize_button_toggled (GtkToggleToolButton *button,
+                               GladeWindow         *window)
 {
-  if (window->priv->setting_pointer_mode)
-    return;
+  GladeProject *active_project = get_active_project (window);
 
   if (gtk_toggle_tool_button_get_active (window->priv->drag_resize_button))
-    glade_app_set_pointer_mode (GLADE_POINTER_DRAG_RESIZE);
+    glade_project_set_pointer_mode (active_project, GLADE_POINTER_DRAG_RESIZE);
   else
     gtk_toggle_tool_button_set_active (window->priv->drag_resize_button, TRUE);
 
 }
 
 static void
-on_pointer_mode_changed (GladeApp * app,
-                         GParamSpec * pspec, GladeWindow * window)
+on_pointer_mode_changed (GladeProject *project,
+                         GParamSpec   *pspec, 
+			 GladeWindow  *window)
 {
-  window->priv->setting_pointer_mode = TRUE;
+  GladeProject *active_project = get_active_project (window);
 
-  if (glade_app_get_pointer_mode () == GLADE_POINTER_SELECT)
-    gtk_toggle_tool_button_set_active (window->priv->selector_button, TRUE);
-  else
-    gtk_toggle_tool_button_set_active (window->priv->selector_button, FALSE);
+  if (!active_project)
+    {
+      gtk_widget_set_sensitive (GTK_WIDGET (window->priv->selector_button), FALSE);
+      gtk_widget_set_sensitive (GTK_WIDGET (window->priv->drag_resize_button), FALSE);
+      return;
+    }
+  else if (active_project != project)
+    return;
 
-  if (glade_app_get_pointer_mode () == GLADE_POINTER_DRAG_RESIZE)
-    gtk_toggle_tool_button_set_active (window->priv->drag_resize_button, TRUE);
+  gtk_widget_set_sensitive (GTK_WIDGET (window->priv->selector_button), TRUE);
+  gtk_widget_set_sensitive (GTK_WIDGET (window->priv->drag_resize_button), TRUE);
+
+  g_signal_handlers_block_by_func (window->priv->selector_button, 
+				   on_selector_button_toggled, window);
+  g_signal_handlers_block_by_func (window->priv->drag_resize_button, 
+				   on_drag_resize_button_toggled, window);
+
+  if (glade_project_get_pointer_mode (project) == GLADE_POINTER_SELECT)
+    {
+      gtk_toggle_tool_button_set_active (window->priv->selector_button, TRUE);
+      gtk_toggle_tool_button_set_active (window->priv->drag_resize_button, FALSE);
+    }
+  else if (glade_project_get_pointer_mode (project) == GLADE_POINTER_DRAG_RESIZE)
+    {
+      gtk_toggle_tool_button_set_active (window->priv->drag_resize_button, TRUE);
+      gtk_toggle_tool_button_set_active (window->priv->selector_button, FALSE);
+    }
   else
-    gtk_toggle_tool_button_set_active (window->priv->drag_resize_button, FALSE);
+    {
+      gtk_toggle_tool_button_set_active (window->priv->drag_resize_button, FALSE);
+      gtk_toggle_tool_button_set_active (window->priv->selector_button, FALSE);
+    }
 
-  window->priv->setting_pointer_mode = FALSE;
+  g_signal_handlers_unblock_by_func (window->priv->selector_button, 
+				     on_selector_button_toggled, window);
+  g_signal_handlers_unblock_by_func (window->priv->drag_resize_button, 
+				     on_drag_resize_button_toggled, window);
 }
 
 static void
-set_sensitivity_according_to_project (GladeWindow * window,
-                                      GladeProject * project)
+set_sensitivity_according_to_project (GladeWindow  *window,
+                                      GladeProject *project)
 {
   GtkAction *action;
 
@@ -1580,30 +1608,28 @@ preferences_cb (GtkAction * action, GladeWindow * window)
 static void
 undo_cb (GtkAction * action, GladeWindow * window)
 {
-  GladeProject *active_project;
+  GladeProject *active_project = get_active_project (window);
 
-  if (!window->priv->active_view)
+  if (!active_project)
     {
       g_warning ("undo should not be sensitive: we don't have a project");
       return;
     }
 
-  active_project = glade_design_view_get_project (window->priv->active_view);
   glade_project_undo (active_project);
 }
 
 static void
 redo_cb (GtkAction * action, GladeWindow * window)
 {
-  GladeProject *active_project;
+  GladeProject *active_project = get_active_project (window);
 
-  if (!window->priv->active_view)
+  if (!active_project)
     {
       g_warning ("redo should not be sensitive: we don't have a project");
       return;
     }
 
-  active_project = glade_design_view_get_project (window->priv->active_view);
   glade_project_redo (active_project);
 }
 
@@ -1647,7 +1673,7 @@ notebook_switch_page_cb (GtkNotebook * notebook,
 
   project = glade_design_view_get_project (view);
 
-  glade_palette_set_project (glade_app_get_palette (), project);
+  glade_palette_set_project (window->priv->palette, project);
 
   refresh_title (window);
   set_sensitivity_according_to_project (window, project);
@@ -1675,6 +1701,8 @@ notebook_switch_page_cb (GtkNotebook * notebook,
 
   /* Refresh the editor and some of the actions */
   project_selection_changed_cb (project, window);
+
+  on_pointer_mode_changed (project, NULL, window);
 }
 
 static void
@@ -1705,6 +1733,8 @@ notebook_tab_added_cb (GtkNotebook * notebook,
                     G_CALLBACK (project_notify_handler_cb), window);
   g_signal_connect (G_OBJECT (project), "notify::read-only",
                     G_CALLBACK (project_notify_handler_cb), window);
+  g_signal_connect (G_OBJECT (project), "notify::pointer-mode",
+                    G_CALLBACK (on_pointer_mode_changed), window);
   g_signal_connect (G_OBJECT (project), "selection-changed",
                     G_CALLBACK (project_selection_changed_cb), window);
   g_signal_connect (G_OBJECT (project), "targets-changed",
@@ -1752,6 +1782,9 @@ notebook_tab_removed_cb (GtkNotebook     *notebook,
   if (window->priv->num_tabs == 0)
     {
       gtk_widget_set_sensitive (GTK_WIDGET (window->priv->editor), FALSE);
+      gtk_widget_set_sensitive (GTK_WIDGET (window->priv->palette), FALSE);
+
+      glade_palette_set_project (window->priv->palette, NULL);
 
       window->priv->active_view = NULL;
     }
@@ -1770,13 +1803,20 @@ notebook_tab_removed_cb (GtkNotebook     *notebook,
   g_signal_handlers_disconnect_by_func (G_OBJECT (project),
                                         G_CALLBACK (project_changed_cb),
                                         window);
-
+  g_signal_handlers_disconnect_by_func (G_OBJECT (project),
+                                        G_CALLBACK (on_pointer_mode_changed),
+                                        window);
 
   gtk_notebook_remove_page (GTK_NOTEBOOK (window->priv->inspectors_notebook),
                             page_num);
 
   clean_actions (window);
 
+  /* Refresh the editor and some of the actions */
+  project_selection_changed_cb (project, window);
+
+  on_pointer_mode_changed (project, NULL, window);
+
   /* FIXME: this function needs to be preferably called somewhere else */
   glade_app_remove_project (project);
 
@@ -1784,9 +1824,6 @@ notebook_tab_removed_cb (GtkNotebook     *notebook,
 
   refresh_title (window);
 
-  /* Refresh the editor and some of the actions */
-  project_selection_changed_cb (project, window);
-
   if (window->priv->active_view)
     set_sensitivity_according_to_project (window,
                                           glade_design_view_get_project
@@ -1828,14 +1865,14 @@ palette_appearance_change_cb (GtkRadioAction * action,
 
   value = gtk_radio_action_get_current_value (action);
 
-  glade_palette_set_item_appearance (glade_app_get_palette (), value);
+  glade_palette_set_item_appearance (window->priv->palette, value);
 
 }
 
 static void
 palette_toggle_small_icons_cb (GtkAction * action, GladeWindow * window)
 {
-  glade_palette_set_use_small_item_icons (glade_app_get_palette (),
+  glade_palette_set_use_small_item_icons (window->priv->palette,
                                           gtk_toggle_action_get_active
                                           (GTK_TOGGLE_ACTION (action)));
 }
@@ -3291,6 +3328,10 @@ glade_window_init (GladeWindow * window)
   priv->editor = GLADE_EDITOR (glade_editor_new ());
   g_object_ref_sink (G_OBJECT (priv->editor));
 
+  /* palette */
+  priv->palette = GLADE_PALETTE (glade_palette_new ());
+  g_object_ref_sink (G_OBJECT (priv->palette));
+
   /* menubar */
   menubar = construct_menu (window);
   gtk_box_pack_start (GTK_BOX (vbox), menubar, FALSE, TRUE, 0);
@@ -3361,7 +3402,7 @@ glade_window_init (GladeWindow * window)
   gtk_widget_show (priv->notebook);
 
   /* palette */
-  palette = GTK_WIDGET (glade_app_get_palette ());
+  palette = GTK_WIDGET (priv->palette);
   glade_palette_set_show_selector_button (GLADE_PALETTE (palette), FALSE);
   gtk_paned_pack1 (GTK_PANED (hpaned2), palette, FALSE, FALSE);
   setup_dock (&priv->docks[DOCK_PALETTE], palette, 200, 540,
@@ -3437,9 +3478,6 @@ glade_window_init (GladeWindow * window)
                     G_CALLBACK (on_selector_button_toggled), window);
   g_signal_connect (G_OBJECT (priv->drag_resize_button), "toggled",
                     G_CALLBACK (on_drag_resize_button_toggled), window);
-  g_signal_connect (G_OBJECT (glade_app_get ()), "notify::pointer-mode",
-                    G_CALLBACK (on_pointer_mode_changed), window);
-
 
   /* support for opening a file by dragging onto the project window */
   gtk_drag_dest_set (GTK_WIDGET (window),



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