[nautilus] dnd: rework handling of _NETSCAPE_URL dnd links



commit edd3c43beb5efbc13f55d73e8c9818966a031ad1
Author: Cosimo Cecchi <cosimoc gnome org>
Date:   Mon Apr 4 17:04:01 2011 -0400

    dnd: rework handling of _NETSCAPE_URL dnd links
    
    Previously we used to to the following:
    * default to always "ask", unless the copy was explicit
    * when dropped, we did not actually ask anything but we would trigger an
      async mimetype query_info and:
      - trigger a file asking whether to download or to link for text files
      - silently link for HTML files
      - silently download for every other mimetype
    * if the query_info was not completed within one second, we would
      download by default
    
    This is somewhat broken, as the DnD icon is not what you would expect;
    also downloading is not usually done with DnD from the browser, and it's
    also expensive, so it should never be the default, but an explicit
    choice. It also makes it impossible to create links for anything else
    than text or HTML.
    
    Change the policy to always link by default, unless the user explicitly
    requests the copy.

 libnautilus-private/nautilus-dnd.c |    4 +-
 src/nautilus-view-dnd.c            |  268 ++++++++++--------------------------
 2 files changed, 77 insertions(+), 195 deletions(-)
---
diff --git a/libnautilus-private/nautilus-dnd.c b/libnautilus-private/nautilus-dnd.c
index 630306e..9c5cc0c 100644
--- a/libnautilus-private/nautilus-dnd.c
+++ b/libnautilus-private/nautilus-dnd.c
@@ -369,10 +369,10 @@ GdkDragAction
 nautilus_drag_default_drop_action_for_netscape_url (GdkDragContext *context)
 {
 	/* Mozilla defaults to copy, but unless thats the
-	   only allowed thing (enforced by ctrl) we want to ASK */
+	   only allowed thing (enforced by ctrl) we want to LINK */
 	if (gdk_drag_context_get_suggested_action (context) == GDK_ACTION_COPY &&
 	    gdk_drag_context_get_actions (context) != GDK_ACTION_COPY) {
-		return GDK_ACTION_ASK;
+		return GDK_ACTION_LINK;
 	} else if (gdk_drag_context_get_suggested_action (context) == GDK_ACTION_MOVE) {
 		/* Don't support move */
 		return GDK_ACTION_COPY;
diff --git a/src/nautilus-view-dnd.c b/src/nautilus-view-dnd.c
index 63df2f5..ad99189 100644
--- a/src/nautilus-view-dnd.c
+++ b/src/nautilus-view-dnd.c
@@ -67,77 +67,13 @@ view_widget_to_file_operation_position_xy (NautilusView *view,
 	*y = position.y;
 }
 
-
 typedef struct {
-	NautilusView  *view;
-	GCancellable *cancellable;
-	char *encoded_url;
+	NautilusView *view;
+	char *link_name;
 	char *target_uri;
-	int x;
-	int y;
-	guint timeout;
-} NetscapeUrlDropAsk;
-
-static GdkDragAction
-ask_link_action (NautilusView *view)
-{
-	int button_pressed;
-	GdkDragAction result;
-	GtkWindow *parent_window;
-	GtkWidget *dialog;
-
-	parent_window = NULL;
-
-	/* Don't use desktop window as parent, since that means
-	   we show up an all desktops etc */
-	if (! NAUTILUS_IS_DESKTOP_ICON_VIEW (view)) {
-		parent_window = GTK_WINDOW (GET_ANCESTOR (view));
-	}
-
-	dialog = gtk_message_dialog_new (parent_window,
-					 GTK_DIALOG_DESTROY_WITH_PARENT,
-					 GTK_MESSAGE_QUESTION,
-					 GTK_BUTTONS_NONE,
-					 _("Download location?"));
-
-	gtk_message_dialog_format_secondary_text (GTK_MESSAGE_DIALOG (dialog),
-						  _("You can download it or make a link to it."));
-
-	gtk_dialog_add_button (GTK_DIALOG (dialog),
-			       _("Make a _Link"), 0);
-	gtk_dialog_add_button (GTK_DIALOG (dialog),
-			       GTK_STOCK_CANCEL, 1);
-	gtk_dialog_add_button (GTK_DIALOG (dialog),
-			       _("_Download"), 2);
-
-	gtk_window_set_title (GTK_WINDOW (dialog), ""); /* as per HIG */
-	gtk_window_set_focus_on_map (GTK_WINDOW (dialog), TRUE);
-	gtk_dialog_set_default_response (GTK_DIALOG (dialog), 2);
-
-	gtk_window_present (GTK_WINDOW (dialog));
-
-	button_pressed = gtk_dialog_run (GTK_DIALOG (dialog));
-
-	gtk_widget_destroy (dialog);
-
-	switch (button_pressed) {
-	case 0:
-		result = GDK_ACTION_LINK;
-		break;
-	case 1:
-	case GTK_RESPONSE_DELETE_EVENT:
-		result = 0;
-		break;
-	case 2:
-		result = GDK_ACTION_COPY;
-		break;
-	default:
-		g_assert_not_reached ();
-		result = 0;
-	}
-
-	return result;
-}
+	char *url;
+	GdkPoint point;
+} NetscapeUrlDropLink;
 
 static void
 revert_slashes (char *string)
@@ -151,70 +87,66 @@ revert_slashes (char *string)
 }
 
 static void
-handle_netscape_url_drop_ask_cb (GObject *source_object,
-				 GAsyncResult *res,
-				 gpointer user_data)
+handle_netscape_url_drop_link_cb (GObject *source_object,
+				  GAsyncResult *res,
+				  gpointer user_data)
 {
-	NetscapeUrlDropAsk *data;
-	GdkDragAction action;
+	NetscapeUrlDropLink *data = user_data;
+	char *link_name = data->link_name;
+	char *link_display_name;
+	gint screen_num;
 	GFileInfo *info;
-	GFile *f;
-	const char *mime_type;
+	char *icon_name = NULL;
+	GdkScreen *screen;
 
-	data = user_data;
-	f = G_FILE (source_object);
+	info = g_file_query_info_finish (G_FILE (source_object),
+					 res, NULL);
 
-	info = g_file_query_info_finish (f, res, NULL);
-	mime_type = NULL;
+	if (info != NULL) {
+		GIcon *icon;
+		const char * const *names;
 
-	if (info) {
-		mime_type = g_file_info_get_content_type (info);
-	}
+		icon = g_file_info_get_icon (info);
 
-	if (mime_type != NULL &&
-	    (g_content_type_equals (mime_type, "text/html") ||
-	     g_content_type_equals (mime_type, "text/xml")  ||
-	     g_content_type_equals (mime_type, "application/xhtml+xml"))) {
-		action = GDK_ACTION_LINK;
-	} else if (mime_type != NULL &&
-		   g_content_type_equals (mime_type, "text/plain")) {
-		action = ask_link_action (data->view);
-	} else {
-		action = GDK_ACTION_COPY;
-	}
-	if (info) {
-		g_object_unref (info);
-	}
+		if (G_IS_THEMED_ICON (icon)) {
+			names = g_themed_icon_get_names (G_THEMED_ICON (icon));
+			icon_name = g_strdup (names[0]);
+		}
 	
-	if (action != 0) {
-		nautilus_view_handle_netscape_url_drop (data->view,
-                                                        data->encoded_url,
-                                                        data->target_uri,
-                                                        action,
-                                                        data->x, data->y);
+		g_object_unref (info);
 	}
-	
-	g_object_unref (data->view);
-	g_object_unref (data->cancellable);
-	if (data->timeout != 0) {
-		g_source_remove (data->timeout);
+
+	if (icon_name == NULL) {
+		icon_name = g_strdup ("text-html");
 	}
-	g_free (data->encoded_url);
-	g_free (data->target_uri);
-	g_free (data);
-}
 
-static gboolean
-handle_netscape_url_drop_timeout (gpointer user_data)
-{
-	NetscapeUrlDropAsk *data;
+	link_display_name = g_strdup_printf (_("Link to %s"), link_name);
 
-	data = user_data;
+	/* The filename can't contain slashes, strip em.
+	   (the basename of http://foo/ is http://foo/) */
+	revert_slashes (link_name);
 
-	g_cancellable_cancel (data->cancellable);
-	data->timeout = 0;
-	
-	return FALSE;
+	screen = gtk_widget_get_screen (GTK_WIDGET (data->view));
+	screen_num = gdk_screen_get_number (screen);
+
+	nautilus_link_local_create (data->target_uri,
+				    link_name,
+				    link_display_name,
+				    icon_name,
+				    data->url,
+				    &data->point,
+				    screen_num,
+				    TRUE);
+
+	g_free (link_display_name);
+	g_free (icon_name);
+
+	g_free (data->url);
+	g_free (data->link_name);
+	g_free (data->target_uri);
+
+	g_object_unref (data->view);
+	g_slice_free (NetscapeUrlDropLink, data);
 }
 
 void
@@ -225,36 +157,23 @@ nautilus_view_handle_netscape_url_drop (NautilusView  *view,
                                         int            x,
                                         int            y)
 {
-	GdkPoint point;
-	GdkScreen *screen;
-	int screen_num;
 	char *url, *title;
-	char *link_name, *link_display_name;
-	char *container_uri;
+	char *link_name;
 	GArray *points;
 	char **bits;
 	GList *uri_list = NULL;
 	GFile *f;
 
-	if (encoded_url == NULL) {
-		return;
-	}
+	f = g_file_new_for_uri (target_uri);
 
-	container_uri = NULL;
-	if (target_uri == NULL) {
-		container_uri = nautilus_view_get_backing_uri (view);
-		g_assert (container_uri != NULL);
-	}
-
-	f = g_file_new_for_uri (target_uri != NULL ? target_uri : container_uri);
 	if (!g_file_is_native (f)) {
 		eel_show_warning_dialog (_("Drag and drop is not supported."),
 					 _("Drag and drop is only supported on local file systems."),
                                          GET_ANCESTOR (view));
 		g_object_unref (f);
-		g_free (container_uri);
 		return;
 	}
+
 	g_object_unref (f);
 
 	/* _NETSCAPE_URL_ works like this: $URL\n$TITLE */
@@ -262,7 +181,6 @@ nautilus_view_handle_netscape_url_drop (NautilusView  *view,
 	switch (g_strv_length (bits)) {
 	case 0:
 		g_strfreev (bits);
-		g_free (container_uri);
 		return;
 	case 1:
 		url = bits[0];
@@ -273,30 +191,7 @@ nautilus_view_handle_netscape_url_drop (NautilusView  *view,
 		title = bits[1];
 	}
 
-	if (action == GDK_ACTION_ASK) {
-		NetscapeUrlDropAsk *data;
-
-		f = g_file_new_for_uri (url);
-		data = g_new0 (NetscapeUrlDropAsk, 1);
-		data->view = g_object_ref (view);
-		data->cancellable = g_cancellable_new ();
-		data->encoded_url = g_strdup (encoded_url);
-		data->target_uri = g_strdup (target_uri);
-		data->x = x;
-		data->y = y;
-		/* Ensure we wait at most 1 second for mimetype */
-		data->timeout = g_timeout_add (1000,
-					       handle_netscape_url_drop_timeout,
-					       data);
-		g_file_query_info_async (f,
-					 G_FILE_ATTRIBUTE_STANDARD_CONTENT_TYPE, 0,
-					 0, data->cancellable,
-					 handle_netscape_url_drop_ask_cb,
-					 data);
-		
-		g_free (container_uri);
-		return;
-	}
+	f = g_file_new_for_uri (url);
 
 	view_widget_to_file_operation_position_xy (view, &x, &y);
 
@@ -309,46 +204,33 @@ nautilus_view_handle_netscape_url_drop (NautilusView  *view,
 		eel_show_warning_dialog (_("Drag and drop is not supported."),
 					 _("An invalid drag type was used."),
                                          GET_ANCESTOR (view));
-		g_free (container_uri);
 		return;
 	}
 
 	if (action == GDK_ACTION_LINK) {
 		if (eel_str_is_empty (title)) {
-			GFile *f;
-
-			f = g_file_new_for_uri (url);
 			link_name = g_file_get_basename (f);
-			g_object_unref (f);
 		} else {
 			link_name = g_strdup (title);
 		}
-		
-		if (!eel_str_is_empty (link_name)) {
-			link_display_name = g_strdup_printf (_("Link to %s"), link_name);
-
-			/* The filename can't contain slashes, strip em.
-			   (the basename of http://foo/ is http://foo/) */
-			revert_slashes (link_name);
-
-			point.x = x;
-			point.y = y;
-
-			screen = gtk_widget_get_screen (GTK_WIDGET (view));
-			screen_num = gdk_screen_get_number (screen);
 
-			nautilus_link_local_create (target_uri != NULL ? target_uri : container_uri,
-						    link_name,
-						    link_display_name,
-						    "gnome-fs-bookmark",
-						    url,
-						    &point,
-						    screen_num,
-						    TRUE);
-
-			g_free (link_display_name);
+		if (!eel_str_is_empty (link_name)) {
+			NetscapeUrlDropLink *data;
+
+			data = g_slice_new0 (NetscapeUrlDropLink);
+			data->link_name = link_name;
+			data->point.x = x;
+			data->point.y = y;
+			data->view = g_object_ref (view);
+			data->target_uri = g_strdup (target_uri);
+			data->url = g_strdup (url);
+
+			g_file_query_info_async (f,
+						 G_FILE_ATTRIBUTE_STANDARD_ICON,
+						 0, 0, NULL,
+						 handle_netscape_url_drop_link_cb,
+						 data);
 		}
-		g_free (link_name);
 	} else {
 		GdkPoint tmp_point = { 0, 0 };
 
@@ -359,15 +241,15 @@ nautilus_view_handle_netscape_url_drop (NautilusView  *view,
 		uri_list = g_list_append (uri_list, url);
 
 		nautilus_view_move_copy_items (view, uri_list, points,
-                                               target_uri != NULL ? target_uri : container_uri,
+                                               target_uri,
                                                action, x, y);
 
 		g_list_free (uri_list);
 		g_array_free (points, TRUE);
 	}
 
+	g_object_unref (f);
 	g_strfreev (bits);
-	g_free (container_uri);
 }
 
 void



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