From f363c398d192499fd92fd4f64387a0fdf78b9a2f Mon Sep 17 00:00:00 2001 From: Eric Koegel Date: Fri, 25 Nov 2011 15:38:56 +0300 Subject: [PATCH 5/5] This patch adds support for a right click drag and drop popup menu to move or copy files to the desktop --- src/xfdesktop-file-utils.c | 3 +- src/xfdesktop-icon-view-manager.c | 111 ++++++++++++++++++++++++++++++++++++- src/xfdesktop-icon-view.c | 19 ++++-- 3 files changed, 123 insertions(+), 10 deletions(-) diff --git a/src/xfdesktop-file-utils.c b/src/xfdesktop-file-utils.c index 75bf0ce..b7491de 100644 --- a/src/xfdesktop-file-utils.c +++ b/src/xfdesktop-file-utils.c @@ -1377,9 +1377,8 @@ xfdesktop_file_utils_transfer_files(GdkDragAction action, g_return_val_if_fail(source_files != NULL && G_IS_FILE(source_files->data), FALSE); g_return_val_if_fail(target_files != NULL && G_IS_FILE(target_files->data), FALSE); - g_return_val_if_fail(screen == NULL || GDK_IS_SCREEN(screen), FALSE); - if(!screen) + if(!screen || !GDK_IS_SCREEN(screen)) screen = gdk_display_get_default_screen(gdk_display_get_default()); fileman_proxy = xfdesktop_file_utils_peek_filemanager_proxy(); diff --git a/src/xfdesktop-icon-view-manager.c b/src/xfdesktop-icon-view-manager.c index efab2ec..b49d9c9 100644 --- a/src/xfdesktop-icon-view-manager.c +++ b/src/xfdesktop-icon-view-manager.c @@ -23,7 +23,7 @@ #endif #include - +#include #include "xfdesktop-icon-view-manager.h" #include "xfdesktop-icon-view.h" @@ -82,6 +82,109 @@ xfdesktop_icon_view_manager_fini(XfdesktopIconViewManager *manager) iface->manager_fini(manager); } + + +static void xfdesktop_dnd_item(GtkWidget *item, GdkDragAction *action) +{ + XfdesktopIconViewManager *manager; + XfdesktopIcon *drop_icon; + GdkDragContext *context; + guint16 *row; + guint16 *col; + guint *time_; + + manager = g_object_get_data(G_OBJECT(item), "manager"); + drop_icon = g_object_get_data(G_OBJECT(item), "drop_icon"); + context = g_object_get_data(G_OBJECT(item), "context"); + row = g_object_get_data(G_OBJECT(item), "row"); + col = g_object_get_data(G_OBJECT(item), "col"); + time_ = g_object_get_data(G_OBJECT(item), "time"); + + context->action = *action; + xfdesktop_icon_view_manager_drag_drop(manager, drop_icon, context, *row, *col, *time_); + + g_free(row); + g_free(col); + g_free(time_); +} + + +static void xfdesktop_dnd_menu (XfdesktopIconViewManager *manager, + XfdesktopIcon *drop_icon, + GdkDragContext *context, + guint16 row, + guint16 col, + guint time_) +{ + GtkWidget *menu; + GtkWidget *item; + static GdkDragAction action_copy = GDK_ACTION_COPY; + static GdkDragAction action_move = GDK_ACTION_MOVE; + /*static GdkDragAction action_link = GDK_ACTION_LINK;*/ + guint16 *temp_row, *temp_col; + guint *temp_time; + menu = gtk_menu_new(); + + /* Allocate these variables so they don't go out of scope */ + temp_row = g_try_malloc(sizeof(guint16)); + temp_col = g_try_malloc(sizeof(guint16)); + temp_time = g_try_malloc(sizeof(guint)); + + g_return_if_fail(temp_row != NULL); + g_return_if_fail(temp_col != NULL); + g_return_if_fail(temp_time != NULL); + + *temp_row = row; + *temp_col = col; + *temp_time = time_; + + item = gtk_image_menu_item_new_with_mnemonic(_("Copy _Here")); + gtk_menu_shell_append(GTK_MENU_SHELL(menu), item); + g_signal_connect(G_OBJECT(item), "activate", G_CALLBACK(xfdesktop_dnd_item), &action_copy); + g_object_set_data(G_OBJECT(item), "manager", manager); + g_object_set_data(G_OBJECT(item), "drop_icon", drop_icon); + g_object_set_data(G_OBJECT(item), "context", context); + g_object_set_data(G_OBJECT(item), "row", temp_row); + g_object_set_data(G_OBJECT(item), "col", temp_col); + g_object_set_data(G_OBJECT(item), "time", temp_time); + gtk_widget_show (item); + + item = gtk_image_menu_item_new_with_mnemonic(_("_Move Here")); + gtk_menu_shell_append(GTK_MENU_SHELL(menu), item); + g_signal_connect(G_OBJECT(item), "activate", G_CALLBACK(xfdesktop_dnd_item), &action_move); + g_object_set_data(G_OBJECT(item), "manager", manager); + g_object_set_data(G_OBJECT(item), "drop_icon", drop_icon); + g_object_set_data(G_OBJECT(item), "context", context); + g_object_set_data(G_OBJECT(item), "row", temp_row); + g_object_set_data(G_OBJECT(item), "col", temp_col); + g_object_set_data(G_OBJECT(item), "time", temp_time); + gtk_widget_show (item); + + /* FIXME: Linking doesn't currently work. + item = gtk_image_menu_item_new_with_mnemonic(_("_Link Here")); + gtk_menu_shell_append(GTK_MENU_SHELL(menu), item); + g_signal_connect(G_OBJECT(item), "activate", G_CALLBACK(xfdesktop_dnd_item), &action_link); + g_object_set_data(G_OBJECT(item), "manager", manager); + g_object_set_data(G_OBJECT(item), "drop_icon", drop_icon); + g_object_set_data(G_OBJECT(item), "context", context); + g_object_set_data(G_OBJECT(item), "row", temp_row); + g_object_set_data(G_OBJECT(item), "col", temp_col); + g_object_set_data(G_OBJECT(item), "time", temp_time); + gtk_widget_show (item);*/ + + item = gtk_separator_menu_item_new(); + gtk_menu_shell_append(GTK_MENU_SHELL(menu), item); + gtk_widget_show (item); + + item = gtk_image_menu_item_new_from_stock (GTK_STOCK_CANCEL, NULL); + gtk_menu_shell_append(GTK_MENU_SHELL(menu), item); + gtk_widget_show (item); + + gtk_widget_show(menu); + gtk_menu_popup(GTK_MENU(menu), NULL, NULL, NULL, NULL, 3, time_); +} + + gboolean xfdesktop_icon_view_manager_drag_drop(XfdesktopIconViewManager *manager, XfdesktopIcon *drop_icon, @@ -94,6 +197,12 @@ xfdesktop_icon_view_manager_drag_drop(XfdesktopIconViewManager *manager, g_return_val_if_fail(XFDESKTOP_IS_ICON_VIEW_MANAGER(manager), FALSE); + if(context->action == GDK_ACTION_ASK) + { + xfdesktop_dnd_menu(manager, drop_icon, context, row, col, time_); + return TRUE; + } + iface = XFDESKTOP_ICON_VIEW_MANAGER_GET_IFACE(manager); g_return_val_if_fail(iface->drag_drop, FALSE); diff --git a/src/xfdesktop-icon-view.c b/src/xfdesktop-icon-view.c index b6c7569..93e9630 100644 --- a/src/xfdesktop-icon-view.c +++ b/src/xfdesktop-icon-view.c @@ -48,6 +48,7 @@ #include "xfdesktop-icon-view.h" #include "xfdesktop-marshal.h" +#include "xfce-desktop.h" #include #include @@ -744,7 +745,7 @@ xfdesktop_icon_view_button_press(GtkWidget *widget, xfdesktop_icon_view_select_item(icon_view, icon); } - if(evt->button == 1) { + if(evt->button == 1 || evt->button == 3) { /* we might be the start of a drag */ DBG("setting stuff"); icon_view->priv->maybe_begin_drag = TRUE; @@ -752,10 +753,6 @@ xfdesktop_icon_view_button_press(GtkWidget *widget, icon_view->priv->definitely_rubber_banding = FALSE; icon_view->priv->press_start_x = evt->x; icon_view->priv->press_start_y = evt->y; - } else if(evt->button == 3) { - /* XfceDesktop will handle signalling the icon view manager - * to show the context menu */ - return FALSE; } return TRUE; @@ -810,7 +807,10 @@ xfdesktop_icon_view_button_release(GtkWidget *widget, TRACE("entering btn=%d", evt->button); - if(evt->button == 1) { + if(evt->button == 3 && !icon_view->priv->definitely_dragging && !icon_view->priv->definitely_rubber_banding) + xfce_desktop_popup_root_menu(XFCE_DESKTOP(widget), evt->button, evt->time); + + if(evt->button == 1 || evt->button == 3) { DBG("unsetting stuff"); icon_view->priv->definitely_dragging = FALSE; icon_view->priv->maybe_begin_drag = FALSE; @@ -896,10 +896,15 @@ xfdesktop_icon_view_maybe_begin_drag(XfdesktopIconView *icon_view, actions = GDK_ACTION_MOVE | (icon_view->priv->drag_source_set ? icon_view->priv->foreign_source_actions : 0); - + if(evt->state != GDK_BUTTON3_MASK) { gtk_drag_begin(GTK_WIDGET(icon_view), icon_view->priv->source_targets, actions, 1, (GdkEvent *)evt); + } else { + gtk_drag_begin(GTK_WIDGET(icon_view), + icon_view->priv->source_targets, + actions, 3, (GdkEvent *)evt); + } DBG("DRAG BEGIN!"); -- 1.7.5.4