[gthumb] added ability to drag files with the middle mouse button to allow the user to choose the action to p
- From: Paolo Bacchilega <paobac src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gthumb] added ability to drag files with the middle mouse button to allow the user to choose the action to p
- Date: Sun, 23 Jan 2011 10:29:40 +0000 (UTC)
commit 661aae066d620ded9c6eed97f3594d8d0f49d024
Author: Paolo Bacchilega <paobac src gnome org>
Date: Sun Jan 23 11:13:11 2011 +0100
added ability to drag files with the middle mouse button to allow the user to choose the action to perform
[new feature]
extensions/file_manager/callbacks.c | 18 ++++-
gthumb/gth-browser.c | 11 ++-
gthumb/gth-file-list.c | 4 +-
gthumb/gth-icon-view.c | 20 ++++++-
gthumb/gtk-utils.c | 116 +++++++++++++++++++++++++++++++++++
gthumb/gtk-utils.h | 4 +
6 files changed, 162 insertions(+), 11 deletions(-)
---
diff --git a/extensions/file_manager/callbacks.c b/extensions/file_manager/callbacks.c
index 23322ac..14bbb0a 100644
--- a/extensions/file_manager/callbacks.c
+++ b/extensions/file_manager/callbacks.c
@@ -272,20 +272,28 @@ gth_file_list_drag_data_received (GtkWidget *file_view,
g_signal_stop_emission_by_name (file_view, "drag-data-received");
/*
- if ((gdk_drag_context_get_action (context) == GDK_ACTION_COPY)
- || (gdk_drag_context_get_action (context) == GDK_ACTION_MOVE))
+ if ((gdk_drag_context_get_suggested_action (context) == GDK_ACTION_COPY)
+ || (gdk_drag_context_get_suggested_action (context) == GDK_ACTION_MOVE))
{
success = TRUE;
}
*/
- if ((context->action == GDK_ACTION_COPY)
- || (context->action == GDK_ACTION_MOVE))
+ if ((context->suggested_action == GDK_ACTION_COPY)
+ || (context->suggested_action == GDK_ACTION_MOVE)
+ || (context->suggested_action == GDK_ACTION_ASK))
{
success = TRUE;
}
+ if (context->suggested_action == GDK_ACTION_ASK) {
+ context->action = _gtk_menu_ask_drag_drop_action (file_view, context->actions, time);
+ success = context->action != 0;
+ }
+
gtk_drag_finish (context, success, FALSE, time);
+ if (! success)
+ return;
uris = gtk_selection_data_get_uris (selection_data);
selected_files = _g_file_list_new_from_uriv (uris);
@@ -449,6 +457,8 @@ gth_file_list_drag_motion (GtkWidget *file_view,
data->scroll_event = 0;
}
}
+ else if (context->suggested_action == GDK_ACTION_ASK)
+ gdk_drag_status (context, GDK_ACTION_ASK, time);
else
gdk_drag_status (context, GDK_ACTION_COPY, time);
diff --git a/gthumb/gth-browser.c b/gthumb/gth-browser.c
index 1765e92..3478434 100644
--- a/gthumb/gth-browser.c
+++ b/gthumb/gth-browser.c
@@ -2512,10 +2512,10 @@ folder_tree_drag_data_received (GtkWidget *tree_view,
success = FALSE;
}
- gtk_drag_finish (context, success, FALSE, time);
-
- if (! success)
+ if (! success) {
+ gtk_drag_finish (context, FALSE, FALSE, time);
return;
+ }
destination = gth_folder_tree_get_file (GTH_FOLDER_TREE (browser->priv->folder_tree), path);
uris = gtk_selection_data_get_uris (selection_data);
@@ -2523,6 +2523,8 @@ folder_tree_drag_data_received (GtkWidget *tree_view,
if (file_list != NULL)
gth_hook_invoke ("gth-browser-folder-tree-drag-data-received", browser, destination, file_list, suggested_action);
+ gtk_drag_finish (context, TRUE, FALSE, time);
+
_g_object_list_unref (file_list);
g_strfreev (uris);
_g_object_unref (destination);
@@ -2550,7 +2552,8 @@ folder_tree_drag_data_get_cb (GtkWidget *widget,
if (file_source == NULL)
return;
- drag_context->suggested_action = gth_file_source_can_cut (file_source, file_data->file) ? GDK_ACTION_MOVE : GDK_ACTION_COPY;
+ if (drag_context->actions && GDK_ACTION_MOVE)
+ drag_context->suggested_action = gth_file_source_can_cut (file_source, file_data->file) ? GDK_ACTION_MOVE : GDK_ACTION_COPY;
uris = g_new (char *, 2);
uris[0] = g_file_get_uri (file_data->file);
diff --git a/gthumb/gth-file-list.c b/gthumb/gth-file-list.c
index 815f20b..d7daa45 100644
--- a/gthumb/gth-file-list.c
+++ b/gthumb/gth-file-list.c
@@ -666,10 +666,10 @@ gth_file_list_construct (GthFileList *file_list,
gtk_target_list_add_text_targets (target_list, 0);
targets = gtk_target_table_new_from_list (target_list, &n_targets);
gth_file_view_enable_drag_source (GTH_FILE_VIEW (file_list->priv->view),
- GDK_BUTTON1_MASK,
+ GDK_BUTTON1_MASK | GDK_BUTTON2_MASK,
targets,
n_targets,
- GDK_ACTION_MOVE | GDK_ACTION_COPY);
+ GDK_ACTION_COPY | GDK_ACTION_MOVE | GDK_ACTION_ASK);
gtk_target_list_unref (target_list);
gtk_target_table_free (targets, n_targets);
diff --git a/gthumb/gth-icon-view.c b/gthumb/gth-icon-view.c
index 00559ec..cd570d3 100644
--- a/gthumb/gth-icon-view.c
+++ b/gthumb/gth-icon-view.c
@@ -44,6 +44,7 @@ struct _GthIconViewPrivate {
GdkDragAction drag_actions;
gboolean dragging : 1; /* Whether the user is dragging items. */
+ int drag_button;
gboolean drag_started : 1; /* Whether the drag has started. */
int drag_start_x; /* The position where the drag started. */
int drag_start_y;
@@ -556,6 +557,20 @@ icon_view_button_press_event_cb (GtkWidget *widget,
return TRUE;
}
+ if ((event->button == 2) && (event->type == GDK_BUTTON_PRESS)) {
+ /* This can be the start of a dragging action. */
+
+ if (! (event->state & GDK_CONTROL_MASK)
+ && ! (event->state & GDK_SHIFT_MASK)
+ && icon_view->priv->drag_source_enabled)
+ {
+ icon_view->priv->dragging = TRUE;
+ icon_view->priv->drag_button = 2;
+ icon_view->priv->drag_start_x = event->x;
+ icon_view->priv->drag_start_y = event->y;
+ }
+ }
+
if ((event->button == 1) && (event->type == GDK_BUTTON_PRESS)) {
GtkTreePath *path;
int pos;
@@ -576,6 +591,7 @@ icon_view_button_press_event_cb (GtkWidget *widget,
&& icon_view->priv->drag_source_enabled)
{
icon_view->priv->dragging = TRUE;
+ icon_view->priv->drag_button = 1;
icon_view->priv->drag_start_x = event->x;
icon_view->priv->drag_start_y = event->y;
}
@@ -686,8 +702,10 @@ icon_view_motion_notify_event_cb (GtkWidget *widget,
context = gtk_drag_begin (widget,
icon_view->priv->drag_target_list,
icon_view->priv->drag_actions,
- 1,
+ icon_view->priv->drag_button,
(GdkEvent *) event);
+ if (icon_view->priv->drag_button == 2)
+ context->suggested_action = GDK_ACTION_ASK;
dnd_icon = gtk_icon_view_create_drag_icon (GTK_ICON_VIEW (icon_view), path);
gdk_drawable_get_size (dnd_icon, &width, &height);
diff --git a/gthumb/gtk-utils.c b/gthumb/gtk-utils.c
index 82d4f55..337d711 100644
--- a/gthumb/gtk-utils.c
+++ b/gthumb/gtk-utils.c
@@ -1124,3 +1124,119 @@ _gtk_info_bar_clear_action_area (GtkInfoBar *info_bar)
{
_gtk_container_remove_children (GTK_CONTAINER (gtk_info_bar_get_action_area (info_bar)), NULL, NULL);
}
+
+
+/* -- _gtk_menu_ask_drag_drop_action -- */
+
+
+typedef struct {
+ GMainLoop *loop;
+ GdkDragAction action;
+} DropActionData;
+
+
+static void
+ask_drag_drop_action_menu_deactivate_cb (GtkMenuShell *menushell,
+ gpointer user_data)
+{
+ DropActionData *drop_data = user_data;
+
+ if (g_main_loop_is_running (drop_data->loop))
+ g_main_loop_quit (drop_data->loop);
+}
+
+
+static void
+ask_drag_drop_action_item_activate_cb (GtkMenuItem *menuitem,
+ gpointer user_data)
+{
+ DropActionData *drop_data = user_data;
+
+ drop_data->action = GPOINTER_TO_INT (g_object_get_data (G_OBJECT (menuitem), "drop-action"));
+ if (g_main_loop_is_running (drop_data->loop))
+ g_main_loop_quit (drop_data->loop);
+}
+
+
+static void
+_gtk_menu_ask_drag_drop_action_append_item (GtkWidget *menu,
+ const char *label,
+ GdkDragAction actions,
+ GdkDragAction action,
+ DropActionData *drop_data)
+{
+ GtkWidget *item;
+
+ item = gtk_menu_item_new_with_mnemonic (label);
+ g_object_set_data (G_OBJECT (item), "drop-action", GINT_TO_POINTER (action));
+ gtk_widget_set_sensitive (item, ((actions & action) != 0));
+ gtk_widget_show (item);
+ gtk_menu_shell_append (GTK_MENU_SHELL (menu), item);
+
+ g_signal_connect (item,
+ "activate",
+ G_CALLBACK (ask_drag_drop_action_item_activate_cb),
+ drop_data);
+}
+
+
+GdkDragAction
+_gtk_menu_ask_drag_drop_action (GtkWidget *widget,
+ GdkDragAction actions,
+ guint32 activate_time)
+{
+ DropActionData drop_data;
+ GtkWidget *menu;
+ GtkWidget *item;
+
+ drop_data.action = 0;
+ drop_data.loop = g_main_loop_new (NULL, FALSE);
+
+ menu = gtk_menu_new ();
+ gtk_menu_set_screen (GTK_MENU (menu), gtk_widget_get_screen (widget));
+
+ _gtk_menu_ask_drag_drop_action_append_item (menu,
+ _("_Copy Here"),
+ actions,
+ GDK_ACTION_COPY,
+ &drop_data);
+ _gtk_menu_ask_drag_drop_action_append_item (menu,
+ _("_Move Here"),
+ actions,
+ GDK_ACTION_MOVE,
+ &drop_data);
+ _gtk_menu_ask_drag_drop_action_append_item (menu,
+ _("_Link Here"),
+ actions,
+ GDK_ACTION_LINK,
+ &drop_data);
+
+ item = gtk_separator_menu_item_new ();
+ gtk_widget_show (item);
+ gtk_menu_shell_append (GTK_MENU_SHELL (menu), item);
+
+ item = gtk_menu_item_new_with_label (_("Cancel"));
+ gtk_widget_show (item);
+ gtk_menu_shell_append (GTK_MENU_SHELL (menu), item);
+
+ g_signal_connect (menu,
+ "deactivate",
+ G_CALLBACK (ask_drag_drop_action_menu_deactivate_cb),
+ &drop_data);
+
+ gtk_menu_popup (GTK_MENU (menu),
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ 0,
+ activate_time);
+ gtk_grab_add (menu);
+ g_main_loop_run (drop_data.loop);
+
+ gtk_grab_remove (menu);
+ gtk_widget_destroy (menu);
+ g_main_loop_unref (drop_data.loop);
+
+ return drop_data.action;
+}
diff --git a/gthumb/gtk-utils.h b/gthumb/gtk-utils.h
index 988f283..c01c8a7 100644
--- a/gthumb/gtk-utils.h
+++ b/gthumb/gtk-utils.h
@@ -125,6 +125,10 @@ void _gtk_window_resize_to_fit_screen_height
int default_width);
void _gtk_info_bar_clear_action_area (GtkInfoBar *info_bar);
+GdkDragAction _gtk_menu_ask_drag_drop_action (GtkWidget *widget,
+ GdkDragAction actions,
+ guint32 activate_time);
+
G_END_DECLS
#endif
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]