Implement Save As for arbitrary links
This commit is contained in:
parent
7c63a0b480
commit
38c6ad5dad
2 changed files with 130 additions and 87 deletions
|
@ -218,7 +218,7 @@ _midori_browser_update_interface (MidoriBrowser* browser)
|
||||||
midori_view_can_go_forward (MIDORI_VIEW (view)));
|
midori_view_can_go_forward (MIDORI_VIEW (view)));
|
||||||
|
|
||||||
/* Currently views that don't support source, don't support
|
/* Currently views that don't support source, don't support
|
||||||
saving either. If that changes, we need to thinkof something. */
|
saving either. If that changes, we need to think of something. */
|
||||||
_action_set_sensitive (browser, "SaveAs",
|
_action_set_sensitive (browser, "SaveAs",
|
||||||
midori_view_can_view_source (MIDORI_VIEW (view)));
|
midori_view_can_view_source (MIDORI_VIEW (view)));
|
||||||
_action_set_sensitive (browser, "Print",
|
_action_set_sensitive (browser, "Print",
|
||||||
|
@ -630,6 +630,103 @@ midori_view_add_bookmark_cb (GtkWidget* menuitem,
|
||||||
midori_browser_edit_bookmark_dialog_new (browser, item, FALSE);
|
midori_browser_edit_bookmark_dialog_new (browser, item, FALSE);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
midori_browser_save_transfer_cb (KatzeNetRequest* request,
|
||||||
|
gchar* filename)
|
||||||
|
{
|
||||||
|
FILE* fp;
|
||||||
|
|
||||||
|
if (request->data)
|
||||||
|
{
|
||||||
|
/* FIXME: Show an error message if the file cannot be saved */
|
||||||
|
if ((fp = fopen (filename, "wb")))
|
||||||
|
{
|
||||||
|
fwrite (request->data, 1, request->length, fp);
|
||||||
|
fclose (fp);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
g_free (filename);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
midori_browser_save_uri (MidoriBrowser* browser,
|
||||||
|
const gchar* uri)
|
||||||
|
{
|
||||||
|
static gchar* last_dir = NULL;
|
||||||
|
gboolean folder_set = FALSE;
|
||||||
|
GtkWidget* dialog;
|
||||||
|
gchar* filename;
|
||||||
|
gchar* dirname;
|
||||||
|
gchar* last_slash;
|
||||||
|
gchar* folder;
|
||||||
|
|
||||||
|
dialog = gtk_file_chooser_dialog_new (
|
||||||
|
_("Save file as"), GTK_WINDOW (browser),
|
||||||
|
GTK_FILE_CHOOSER_ACTION_SAVE,
|
||||||
|
GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL,
|
||||||
|
GTK_STOCK_SAVE, GTK_RESPONSE_ACCEPT,
|
||||||
|
NULL);
|
||||||
|
gtk_window_set_icon_name (GTK_WINDOW (dialog), GTK_STOCK_SAVE);
|
||||||
|
gtk_window_set_transient_for (GTK_WINDOW (dialog), GTK_WINDOW (browser));
|
||||||
|
|
||||||
|
if (uri)
|
||||||
|
{
|
||||||
|
/* Base the start folder on the current view's uri if it is local */
|
||||||
|
filename = g_filename_from_uri (uri, NULL, NULL);
|
||||||
|
if (filename)
|
||||||
|
{
|
||||||
|
dirname = g_path_get_dirname (filename);
|
||||||
|
if (dirname && g_file_test (dirname, G_FILE_TEST_IS_DIR))
|
||||||
|
{
|
||||||
|
gtk_file_chooser_set_current_folder (GTK_FILE_CHOOSER (dialog), dirname);
|
||||||
|
folder_set = TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
g_free (dirname);
|
||||||
|
g_free (filename);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Try to provide a good default filename */
|
||||||
|
filename = g_filename_from_uri (uri, NULL, NULL);
|
||||||
|
if (!filename && (last_slash = g_strrstr (uri, "/")))
|
||||||
|
{
|
||||||
|
if (last_slash[0] == '/')
|
||||||
|
last_slash++;
|
||||||
|
filename = g_strdup (last_slash);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
filename = g_strdup (uri);
|
||||||
|
gtk_file_chooser_set_current_name (GTK_FILE_CHOOSER (dialog), filename);
|
||||||
|
g_free (filename);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!folder_set && last_dir && *last_dir)
|
||||||
|
gtk_file_chooser_set_current_folder (GTK_FILE_CHOOSER (dialog), last_dir);
|
||||||
|
|
||||||
|
if (gtk_dialog_run (GTK_DIALOG (dialog)) == GTK_RESPONSE_ACCEPT)
|
||||||
|
{
|
||||||
|
filename = gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (dialog));
|
||||||
|
folder = gtk_file_chooser_get_current_folder (GTK_FILE_CHOOSER (dialog));
|
||||||
|
katze_net_load_uri (browser->net, uri, NULL,
|
||||||
|
(KatzeNetTransferCb)midori_browser_save_transfer_cb, filename);
|
||||||
|
|
||||||
|
g_free (last_dir);
|
||||||
|
last_dir = folder;
|
||||||
|
}
|
||||||
|
gtk_widget_destroy (dialog);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
midori_view_save_as_cb (GtkWidget* menuitem,
|
||||||
|
const gchar* uri,
|
||||||
|
GtkWidget* view)
|
||||||
|
{
|
||||||
|
MidoriBrowser* browser;
|
||||||
|
|
||||||
|
browser = (MidoriBrowser*)gtk_widget_get_toplevel (menuitem);
|
||||||
|
midori_browser_save_uri (browser, uri);
|
||||||
|
}
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
midori_browser_tab_leave_notify_event_cb (GtkWidget* widget,
|
midori_browser_tab_leave_notify_event_cb (GtkWidget* widget,
|
||||||
GdkEventCrossing* event,
|
GdkEventCrossing* event,
|
||||||
|
@ -798,6 +895,8 @@ _midori_browser_add_tab (MidoriBrowser* browser,
|
||||||
midori_view_search_text_cb, browser,
|
midori_view_search_text_cb, browser,
|
||||||
"signal::add-bookmark",
|
"signal::add-bookmark",
|
||||||
midori_view_add_bookmark_cb, browser,
|
midori_view_add_bookmark_cb, browser,
|
||||||
|
"signal::save-as",
|
||||||
|
midori_view_save_as_cb, browser,
|
||||||
NULL);
|
NULL);
|
||||||
|
|
||||||
g_signal_connect (view, "leave-notify-event",
|
g_signal_connect (view, "leave-notify-event",
|
||||||
|
@ -1187,94 +1286,11 @@ _action_open_activate (GtkAction* action,
|
||||||
gtk_widget_destroy (dialog);
|
gtk_widget_destroy (dialog);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
|
||||||
midori_browser_save_transfer_cb (KatzeNetRequest* request,
|
|
||||||
gchar* filename)
|
|
||||||
{
|
|
||||||
FILE* fp;
|
|
||||||
|
|
||||||
if (request->data)
|
|
||||||
{
|
|
||||||
/* FIXME: Show an error message if the file cannot be saved */
|
|
||||||
if ((fp = fopen (filename, "wb")))
|
|
||||||
{
|
|
||||||
fwrite (request->data, 1, request->length, fp);
|
|
||||||
fclose (fp);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
g_free (filename);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
_action_save_as_activate (GtkAction* action,
|
_action_save_as_activate (GtkAction* action,
|
||||||
MidoriBrowser* browser)
|
MidoriBrowser* browser)
|
||||||
{
|
{
|
||||||
static gchar* last_dir = NULL;
|
midori_browser_save_uri (browser, midori_browser_get_current_uri (browser));
|
||||||
gchar* uri = NULL;
|
|
||||||
gboolean folder_set = FALSE;
|
|
||||||
GtkWidget* dialog;
|
|
||||||
GtkWidget* view;
|
|
||||||
gchar* filename;
|
|
||||||
gchar* dirname;
|
|
||||||
gchar* last_slash;
|
|
||||||
gchar* folder;
|
|
||||||
|
|
||||||
dialog = gtk_file_chooser_dialog_new (
|
|
||||||
_("Save file as"), GTK_WINDOW (browser),
|
|
||||||
GTK_FILE_CHOOSER_ACTION_SAVE,
|
|
||||||
GTK_STOCK_CANCEL, GTK_RESPONSE_CANCEL,
|
|
||||||
GTK_STOCK_SAVE, GTK_RESPONSE_ACCEPT,
|
|
||||||
NULL);
|
|
||||||
gtk_window_set_icon_name (GTK_WINDOW (dialog), GTK_STOCK_SAVE);
|
|
||||||
gtk_window_set_transient_for (GTK_WINDOW (dialog), GTK_WINDOW (browser));
|
|
||||||
|
|
||||||
view = midori_browser_get_current_tab (browser);
|
|
||||||
if ((uri = (gchar*)midori_view_get_display_uri (MIDORI_VIEW (view))))
|
|
||||||
{
|
|
||||||
/* Base the start folder on the current view's uri if it is local */
|
|
||||||
filename = g_filename_from_uri (uri, NULL, NULL);
|
|
||||||
if (filename)
|
|
||||||
{
|
|
||||||
dirname = g_path_get_dirname (filename);
|
|
||||||
if (dirname && g_file_test (dirname, G_FILE_TEST_IS_DIR))
|
|
||||||
{
|
|
||||||
gtk_file_chooser_set_current_folder (GTK_FILE_CHOOSER (dialog), dirname);
|
|
||||||
folder_set = TRUE;
|
|
||||||
}
|
|
||||||
|
|
||||||
g_free (dirname);
|
|
||||||
g_free (filename);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Try to provide a good default filename */
|
|
||||||
filename = g_filename_from_uri (uri, NULL, NULL);
|
|
||||||
if (!filename && (last_slash = g_strrstr (uri, "/")))
|
|
||||||
{
|
|
||||||
if (last_slash[0] == '/')
|
|
||||||
last_slash++;
|
|
||||||
filename = g_strdup (last_slash);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
filename = g_strdup (uri);
|
|
||||||
gtk_file_chooser_set_current_name (GTK_FILE_CHOOSER (dialog), filename);
|
|
||||||
g_free (filename);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!folder_set && last_dir && *last_dir)
|
|
||||||
gtk_file_chooser_set_current_folder (GTK_FILE_CHOOSER (dialog), last_dir);
|
|
||||||
|
|
||||||
if (gtk_dialog_run (GTK_DIALOG (dialog)) == GTK_RESPONSE_ACCEPT)
|
|
||||||
{
|
|
||||||
filename = gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (dialog));
|
|
||||||
folder = gtk_file_chooser_get_current_folder (GTK_FILE_CHOOSER (dialog));
|
|
||||||
katze_net_load_uri (browser->net, uri, NULL,
|
|
||||||
(KatzeNetTransferCb)midori_browser_save_transfer_cb, filename);
|
|
||||||
|
|
||||||
g_free (last_dir);
|
|
||||||
last_dir = folder;
|
|
||||||
g_free (uri);
|
|
||||||
}
|
|
||||||
gtk_widget_destroy (dialog);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
|
|
|
@ -112,6 +112,7 @@ enum {
|
||||||
NEW_WINDOW,
|
NEW_WINDOW,
|
||||||
SEARCH_TEXT,
|
SEARCH_TEXT,
|
||||||
ADD_BOOKMARK,
|
ADD_BOOKMARK,
|
||||||
|
SAVE_AS,
|
||||||
|
|
||||||
LAST_SIGNAL
|
LAST_SIGNAL
|
||||||
};
|
};
|
||||||
|
@ -350,6 +351,17 @@ midori_view_class_init (MidoriViewClass* class)
|
||||||
G_TYPE_NONE, 1,
|
G_TYPE_NONE, 1,
|
||||||
G_TYPE_STRING);
|
G_TYPE_STRING);
|
||||||
|
|
||||||
|
signals[SAVE_AS] = g_signal_new (
|
||||||
|
"save-as",
|
||||||
|
G_TYPE_FROM_CLASS (class),
|
||||||
|
(GSignalFlags)(G_SIGNAL_RUN_LAST | G_SIGNAL_ACTION),
|
||||||
|
0,
|
||||||
|
0,
|
||||||
|
NULL,
|
||||||
|
g_cclosure_marshal_VOID__STRING,
|
||||||
|
G_TYPE_NONE, 1,
|
||||||
|
G_TYPE_STRING);
|
||||||
|
|
||||||
gobject_class = G_OBJECT_CLASS (class);
|
gobject_class = G_OBJECT_CLASS (class);
|
||||||
gobject_class->finalize = midori_view_finalize;
|
gobject_class->finalize = midori_view_finalize;
|
||||||
gobject_class->set_property = midori_view_set_property;
|
gobject_class->set_property = midori_view_set_property;
|
||||||
|
@ -783,6 +795,13 @@ midori_web_view_menu_new_window_activate_cb (GtkWidget* widget,
|
||||||
g_signal_emit (view, signals[NEW_WINDOW], 0, view->link_uri);
|
g_signal_emit (view, signals[NEW_WINDOW], 0, view->link_uri);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
midori_web_view_menu_save_as_activate_cb (GtkWidget* widget,
|
||||||
|
MidoriView* view)
|
||||||
|
{
|
||||||
|
g_signal_emit (view, signals[SAVE_AS], 0, view->link_uri);
|
||||||
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
midori_web_view_menu_download_activate_cb (GtkWidget* widget,
|
midori_web_view_menu_download_activate_cb (GtkWidget* widget,
|
||||||
MidoriView* view)
|
MidoriView* view)
|
||||||
|
@ -859,6 +878,12 @@ webkit_web_view_populate_popup_cb (WebKitWebView* web_view,
|
||||||
/* hack to disable non-functional Download File
|
/* hack to disable non-functional Download File
|
||||||
FIXME: Make sure this really is the right menu item */
|
FIXME: Make sure this really is the right menu item */
|
||||||
gtk_widget_hide (menuitem);
|
gtk_widget_hide (menuitem);
|
||||||
|
menuitem = gtk_image_menu_item_new_with_mnemonic (
|
||||||
|
_("_Save Link destination"));
|
||||||
|
gtk_menu_shell_insert (GTK_MENU_SHELL (menu), menuitem, 3);
|
||||||
|
g_signal_connect (menuitem, "activate",
|
||||||
|
G_CALLBACK (midori_web_view_menu_save_as_activate_cb), view);
|
||||||
|
gtk_widget_show (menuitem);
|
||||||
if (view->download_manager && *view->download_manager)
|
if (view->download_manager && *view->download_manager)
|
||||||
{
|
{
|
||||||
menuitem = gtk_image_menu_item_new_with_mnemonic (
|
menuitem = gtk_image_menu_item_new_with_mnemonic (
|
||||||
|
@ -923,8 +948,10 @@ webkit_web_view_populate_popup_cb (WebKitWebView* web_view,
|
||||||
g_signal_connect (menuitem, "activate",
|
g_signal_connect (menuitem, "activate",
|
||||||
G_CALLBACK (midori_web_view_menu_action_activate_cb), view);
|
G_CALLBACK (midori_web_view_menu_action_activate_cb), view);
|
||||||
gtk_widget_show (menuitem);
|
gtk_widget_show (menuitem);
|
||||||
/* FIXME: Make this sensitive once it's implemented */
|
/* Currently views that don't support source, don't support
|
||||||
gtk_widget_set_sensitive (menuitem, FALSE);
|
saving either. If that changes, we need to think of something. */
|
||||||
|
if (!midori_view_can_view_source (view))
|
||||||
|
gtk_widget_set_sensitive (menuitem, FALSE);
|
||||||
menuitem = gtk_image_menu_item_new_with_mnemonic (_("View _Source"));
|
menuitem = gtk_image_menu_item_new_with_mnemonic (_("View _Source"));
|
||||||
gtk_menu_shell_append (GTK_MENU_SHELL (menu), menuitem);
|
gtk_menu_shell_append (GTK_MENU_SHELL (menu), menuitem);
|
||||||
g_object_set_data (G_OBJECT (menuitem), "action", "SourceView");
|
g_object_set_data (G_OBJECT (menuitem), "action", "SourceView");
|
||||||
|
|
Loading…
Reference in a new issue