[gimp] app: Support multi-column DnD in toolbox window
- From: Martin Nordholts <martinn src gnome org>
- To: svn-commits-list gnome org
- Cc:
- Subject: [gimp] app: Support multi-column DnD in toolbox window
- Date: Fri, 22 Jan 2010 19:47:02 +0000 (UTC)
commit ba37aaa5328630ec423c1d56766469b7e2c96dc2
Author: Martin Nordholts <martinn src gnome org>
Date: Fri Jan 22 20:48:34 2010 +0100
app: Support multi-column DnD in toolbox window
Add a drag handler to the toolbox so it's possible to create
multi-column docks in the toolbox dock window.
app/widgets/gimppanedbox.c | 15 +++
app/widgets/gimptoolbox-dnd.c | 12 ++
app/widgets/gimptoolbox.c | 259 +++++++++++++++++++++++++++++-----------
app/widgets/gimptoolbox.h | 2 +
4 files changed, 217 insertions(+), 71 deletions(-)
---
diff --git a/app/widgets/gimppanedbox.c b/app/widgets/gimppanedbox.c
index fe7f56a..18f5b94 100644
--- a/app/widgets/gimppanedbox.c
+++ b/app/widgets/gimppanedbox.c
@@ -37,6 +37,7 @@
#include "gimpdockbook.h"
#include "gimpmenudock.h"
#include "gimppanedbox.h"
+#include "gimptoolbox.h"
#include "gimpwidgets-utils.h"
#include "gimp-log.h"
@@ -157,18 +158,32 @@ gimp_paned_box_set_widget_drag_handler (GtkWidget *widget,
/* Hook us in for drag events. We could abstract this properly and
* put gimp_paned_box_will_handle_drag() in an interface for
* example, but it doesn't feel worth it at this point
+ *
+ * Note that we don't have 'else if's because a widget can be both a
+ * dock and a toolbox for example, in which case we want to set a
+ * drag handler in two ways
+ *
+ * We so need to introduce som abstractions here...
*/
+
if (GIMP_IS_DOCKBOOK (widget))
{
gimp_dockbook_set_drag_handler (GIMP_DOCKBOOK (widget),
drag_handler);
}
+
if (GIMP_IS_DOCK (widget))
{
GimpPanedBox *dock_paned_box = NULL;
dock_paned_box = GIMP_PANED_BOX (gimp_dock_get_vbox (GIMP_DOCK (widget)));
gimp_paned_box_set_drag_handler (dock_paned_box, drag_handler);
}
+
+ if (GIMP_IS_TOOLBOX (widget))
+ {
+ GimpToolbox *toolbox = GIMP_TOOLBOX (widget);
+ gimp_toolbox_set_drag_handler (toolbox, drag_handler);
+ }
}
static void
diff --git a/app/widgets/gimptoolbox-dnd.c b/app/widgets/gimptoolbox-dnd.c
index 451c7c2..1846ada 100644
--- a/app/widgets/gimptoolbox-dnd.c
+++ b/app/widgets/gimptoolbox-dnd.c
@@ -96,10 +96,22 @@ gimp_toolbox_dnd_init (GimpToolbox *toolbox)
/* We need to set this on the toolbox to make gimp-remote
* work. Remove this when we have gotten rid of gimp-remote.
*/
+ gtk_drag_dest_set (GTK_WIDGET (toolbox),
+ 0, NULL, 0,
+ GDK_ACTION_COPY | GDK_ACTION_MOVE);
gimp_dnd_uri_list_dest_add (GTK_WIDGET (toolbox),
gimp_toolbox_drop_uri_list,
context);
+ /* Before caling any dnd helper functions, setup the drag
+ * destination manually since we want to handle all drag events
+ * manually, otherwise we would not be able to give the drag handler
+ * a chance to handle drag events
+ */
+ gtk_drag_dest_set (gimp_toolbox_get_vbox (toolbox),
+ 0, NULL, 0,
+ GDK_ACTION_COPY | GDK_ACTION_MOVE);
+
gimp_dnd_uri_list_dest_add (gimp_toolbox_get_vbox (toolbox),
gimp_toolbox_drop_uri_list,
context);
diff --git a/app/widgets/gimptoolbox.c b/app/widgets/gimptoolbox.c
index 0fe87fa..9a69f53 100644
--- a/app/widgets/gimptoolbox.c
+++ b/app/widgets/gimptoolbox.c
@@ -42,6 +42,7 @@
#include "gimpdialogfactory.h"
#include "gimpdockwindow.h"
#include "gimphelp-ids.h"
+#include "gimppanedbox.h"
#include "gimptoolbox.h"
#include "gimptoolbox-color-area.h"
#include "gimptoolbox-dnd.h"
@@ -91,80 +92,88 @@ struct _GimpToolboxPrivate
gint tool_columns;
gint area_rows;
gint area_columns;
+
+ GimpPanedBox *drag_handler;
};
-static GObject * gimp_toolbox_constructor (GType type,
- guint n_params,
- GObjectConstructParam *params);
-static void gimp_toolbox_set_property (GObject *object,
- guint property_id,
- const GValue *value,
- GParamSpec *pspec);
-static void gimp_toolbox_get_property (GObject *object,
- guint property_id,
- GValue *value,
- GParamSpec *pspec);
-
-static void gimp_toolbox_size_allocate (GtkWidget *widget,
- GtkAllocation *allocation);
-static void gimp_toolbox_style_set (GtkWidget *widget,
- GtkStyle *previous_style);
-static gboolean gimp_toolbox_button_press_event (GtkWidget *widget,
- GdkEventButton *event);
-static gboolean gimp_toolbox_expose_event (GtkWidget *widget,
- GdkEventExpose *event);
-
-static gchar * gimp_toolbox_get_title (GimpDock *dock);
-static void gimp_toolbox_set_host_geometry_hints
- (GimpDock *dock,
- GtkWindow *window);
-static void gimp_toolbox_book_added (GimpDock *dock,
- GimpDockbook *dockbook);
-static void gimp_toolbox_book_removed (GimpDock *dock,
- GimpDockbook *dockbook);
-
-static void toolbox_create_tools (GimpToolbox *toolbox,
- GimpContext *context);
-static GtkWidget * toolbox_create_color_area (GimpToolbox *toolbox,
- GimpContext *context);
-static GtkWidget * toolbox_create_foo_area (GimpToolbox *toolbox,
- GimpContext *context);
-static GtkWidget * toolbox_create_image_area (GimpToolbox *toolbox,
- GimpContext *context);
-
-static void toolbox_area_notify (GimpGuiConfig *config,
- GParamSpec *pspec,
- GtkWidget *area);
-static void toolbox_wilber_notify (GimpGuiConfig *config,
- GParamSpec *pspec,
- GtkWidget *wilber);
-
-static void toolbox_tool_changed (GimpContext *context,
- GimpToolInfo *tool_info,
- GimpToolbox *toolbox);
-
-static void toolbox_tool_reorder (GimpContainer *container,
- GimpToolInfo *tool_info,
- gint index,
- GtkWidget *wrap_box);
-static void toolbox_tool_visible_notify (GimpToolInfo *tool_info,
- GParamSpec *pspec,
- GtkWidget *button);
-
-static void toolbox_tool_button_toggled (GtkWidget *widget,
- GimpToolbox *toolbox);
-static gboolean toolbox_tool_button_press (GtkWidget *widget,
- GdkEventButton *bevent,
- GimpToolbox *toolbox);
-
-static gboolean toolbox_check_device (GtkWidget *widget,
- GdkEvent *event,
- Gimp *gimp);
-
-static void toolbox_paste_received (GtkClipboard *clipboard,
- const gchar *text,
- gpointer data);
+static GObject * gimp_toolbox_constructor (GType type,
+ guint n_params,
+ GObjectConstructParam *params);
+static void gimp_toolbox_set_property (GObject *object,
+ guint property_id,
+ const GValue *value,
+ GParamSpec *pspec);
+static void gimp_toolbox_get_property (GObject *object,
+ guint property_id,
+ GValue *value,
+ GParamSpec *pspec);
+static void gimp_toolbox_size_allocate (GtkWidget *widget,
+ GtkAllocation *allocation);
+static void gimp_toolbox_style_set (GtkWidget *widget,
+ GtkStyle *previous_style);
+static gboolean gimp_toolbox_button_press_event (GtkWidget *widget,
+ GdkEventButton *event);
+static gboolean gimp_toolbox_expose_event (GtkWidget *widget,
+ GdkEventExpose *event);
+static void gimp_toolbox_drag_leave (GtkWidget *widget,
+ GdkDragContext *context,
+ guint time,
+ GimpToolbox *toolbox);
+static gboolean gimp_toolbox_drag_motion (GtkWidget *widget,
+ GdkDragContext *context,
+ gint x,
+ gint y,
+ guint time,
+ GimpToolbox *toolbox);
+static gboolean gimp_toolbox_drag_drop (GtkWidget *widget,
+ GdkDragContext *context,
+ gint x,
+ gint y,
+ guint time,
+ GimpToolbox *toolbox);
+static gchar * gimp_toolbox_get_title (GimpDock *dock);
+static void gimp_toolbox_set_host_geometry_hints (GimpDock *dock,
+ GtkWindow *window);
+static void gimp_toolbox_book_added (GimpDock *dock,
+ GimpDockbook *dockbook);
+static void gimp_toolbox_book_removed (GimpDock *dock,
+ GimpDockbook *dockbook);
+static void toolbox_create_tools (GimpToolbox *toolbox,
+ GimpContext *context);
+static GtkWidget * toolbox_create_color_area (GimpToolbox *toolbox,
+ GimpContext *context);
+static GtkWidget * toolbox_create_foo_area (GimpToolbox *toolbox,
+ GimpContext *context);
+static GtkWidget * toolbox_create_image_area (GimpToolbox *toolbox,
+ GimpContext *context);
+static void toolbox_area_notify (GimpGuiConfig *config,
+ GParamSpec *pspec,
+ GtkWidget *area);
+static void toolbox_wilber_notify (GimpGuiConfig *config,
+ GParamSpec *pspec,
+ GtkWidget *wilber);
+static void toolbox_tool_changed (GimpContext *context,
+ GimpToolInfo *tool_info,
+ GimpToolbox *toolbox);
+static void toolbox_tool_reorder (GimpContainer *container,
+ GimpToolInfo *tool_info,
+ gint index,
+ GtkWidget *wrap_box);
+static void toolbox_tool_visible_notify (GimpToolInfo *tool_info,
+ GParamSpec *pspec,
+ GtkWidget *button);
+static void toolbox_tool_button_toggled (GtkWidget *widget,
+ GimpToolbox *toolbox);
+static gboolean toolbox_tool_button_press (GtkWidget *widget,
+ GdkEventButton *bevent,
+ GimpToolbox *toolbox);
+static gboolean toolbox_check_device (GtkWidget *widget,
+ GdkEvent *event,
+ Gimp *gimp);
+static void toolbox_paste_received (GtkClipboard *clipboard,
+ const gchar *text,
+ gpointer data);
G_DEFINE_TYPE (GimpToolbox, gimp_toolbox, GIMP_TYPE_DOCK)
@@ -267,6 +276,28 @@ gimp_toolbox_constructor (GType type,
gtk_box_reorder_child (GTK_BOX (main_vbox), toolbox->p->vbox, 0);
gtk_widget_show (toolbox->p->vbox);
+ /* Use g_signal_connect() also for the toolbox itself so we can pass
+ * data and reuse the same function for the vbox
+ */
+ g_signal_connect (toolbox, "drag-leave",
+ G_CALLBACK (gimp_toolbox_drag_leave),
+ toolbox);
+ g_signal_connect (toolbox, "drag-motion",
+ G_CALLBACK (gimp_toolbox_drag_motion),
+ toolbox);
+ g_signal_connect (toolbox, "drag-drop",
+ G_CALLBACK (gimp_toolbox_drag_drop),
+ toolbox);
+ g_signal_connect (toolbox->p->vbox, "drag-leave",
+ G_CALLBACK (gimp_toolbox_drag_leave),
+ toolbox);
+ g_signal_connect (toolbox->p->vbox, "drag-motion",
+ G_CALLBACK (gimp_toolbox_drag_motion),
+ toolbox);
+ g_signal_connect (toolbox->p->vbox, "drag-drop",
+ G_CALLBACK (gimp_toolbox_drag_drop),
+ toolbox);
+
toolbox->p->header = gtk_frame_new (NULL);
gtk_frame_set_shadow_type (GTK_FRAME (toolbox->p->header), GTK_SHADOW_NONE);
gtk_box_pack_start (GTK_BOX (toolbox->p->vbox), toolbox->p->header,
@@ -660,6 +691,83 @@ gimp_toolbox_expose_event (GtkWidget *widget,
return FALSE;
}
+static void
+gimp_toolbox_drag_leave (GtkWidget *widget,
+ GdkDragContext *context,
+ guint time,
+ GimpToolbox *toolbox)
+{
+ gimp_highlight_widget (widget, FALSE);
+}
+
+static gboolean
+gimp_toolbox_drag_motion (GtkWidget *widget,
+ GdkDragContext *context,
+ gint x,
+ gint y,
+ guint time,
+ GimpToolbox *toolbox)
+{
+ gboolean other_will_handle = FALSE;
+ gboolean we_will_handle = FALSE;
+ gboolean handled = FALSE;
+
+ other_will_handle = gimp_paned_box_will_handle_drag (toolbox->p->drag_handler,
+ widget,
+ context,
+ x, y,
+ time);
+ we_will_handle = (gtk_drag_dest_find_target (widget, context, NULL) !=
+ GDK_NONE);
+
+ g_printerr ("%s: %d %d\n", G_STRFUNC, other_will_handle, we_will_handle);
+
+ handled = ! other_will_handle && we_will_handle;
+ gdk_drag_status (context, handled ? GDK_ACTION_MOVE : 0, time);
+ gimp_highlight_widget (widget, handled);
+ return handled;
+}
+
+static gboolean
+gimp_toolbox_drag_drop (GtkWidget *widget,
+ GdkDragContext *context,
+ gint x,
+ gint y,
+ guint time,
+ GimpToolbox *toolbox)
+{
+ gboolean handled = FALSE;
+
+ if (gimp_paned_box_will_handle_drag (toolbox->p->drag_handler,
+ widget,
+ context,
+ x, y,
+ time))
+ {
+ /* Make event fall through to the drag handler */
+ handled = FALSE;
+ }
+ else
+ {
+ GdkAtom target = gtk_drag_dest_find_target (widget, context, NULL);
+
+ if (target != GDK_NONE)
+ {
+ /* The URI handlers etc will handle this */
+ gtk_drag_get_data (widget, context, target, time);
+ handled = TRUE;
+ }
+ }
+
+ if (handled)
+ gtk_drag_finish (context,
+ TRUE /*success*/,
+ (context->action == GDK_ACTION_MOVE) /*del*/,
+ time);
+
+ return handled;
+}
+
static gchar *
gimp_toolbox_get_title (GimpDock *dock)
{
@@ -779,6 +887,15 @@ gimp_toolbox_get_vbox (GimpToolbox *toolbox)
return toolbox->p->vbox;
}
+void
+gimp_toolbox_set_drag_handler (GimpToolbox *toolbox,
+ GimpPanedBox *drag_handler)
+{
+ g_return_if_fail (GIMP_IS_TOOLBOX (toolbox));
+
+ toolbox->p->drag_handler = drag_handler;
+}
+
/* private functions */
diff --git a/app/widgets/gimptoolbox.h b/app/widgets/gimptoolbox.h
index efaf23d..a404715 100644
--- a/app/widgets/gimptoolbox.h
+++ b/app/widgets/gimptoolbox.h
@@ -54,6 +54,8 @@ GimpContext * gimp_toolbox_get_context (GimpToolbox *toolbox)
GimpDialogFactory * gimp_toolbox_get_dialog_factory (GimpToolbox *toolbox);
GimpUIManager * gimp_toolbox_get_ui_manager (GimpToolbox *toolbox);
GtkWidget * gimp_toolbox_get_vbox (GimpToolbox *toolbox);
+void gimp_toolbox_set_drag_handler (GimpToolbox *toolbox,
+ GimpPanedBox *drag_handler);
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]