summaryrefslogtreecommitdiff
path: root/src/caja-window-menus.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/caja-window-menus.c')
-rw-r--r--src/caja-window-menus.c1163
1 files changed, 1163 insertions, 0 deletions
diff --git a/src/caja-window-menus.c b/src/caja-window-menus.c
new file mode 100644
index 00000000..c11b2869
--- /dev/null
+++ b/src/caja-window-menus.c
@@ -0,0 +1,1163 @@
+/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */
+
+/*
+ * Caja
+ *
+ * Copyright (C) 2000, 2001 Eazel, Inc.
+ *
+ * Caja is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * Caja is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ *
+ * Author: John Sullivan <[email protected]>
+ */
+
+/* caja-window-menus.h - implementation of caja window menu operations,
+ * split into separate file just for convenience.
+ */
+#include <config.h>
+
+#include <locale.h>
+
+#include "caja-actions.h"
+#include "caja-application.h"
+#include "caja-connect-server-dialog.h"
+#include "caja-file-management-properties.h"
+#include "caja-property-browser.h"
+#include "caja-window-manage-views.h"
+#include "caja-window-bookmarks.h"
+#include "caja-window-private.h"
+#include "caja-desktop-window.h"
+#include "caja-search-bar.h"
+#include <gtk/gtk.h>
+#include <gio/gio.h>
+#include <glib/gi18n.h>
+#include <eel/eel-gtk-extensions.h>
+#include <eel/eel-preferences.h>
+#include <libcaja-extension/caja-menu-provider.h>
+#include <libcaja-private/caja-file-utilities.h>
+#include <libcaja-private/caja-global-preferences.h>
+#include <libcaja-private/caja-icon-names.h>
+#include <libcaja-private/caja-ui-utilities.h>
+#include <libcaja-private/caja-module.h>
+#include <libcaja-private/caja-undo-manager.h>
+#include <libcaja-private/caja-search-directory.h>
+#include <libcaja-private/caja-search-engine.h>
+#include <libcaja-private/caja-signaller.h>
+#include <libcaja-private/caja-trash-monitor.h>
+#include <string.h>
+
+#define MENU_PATH_EXTENSION_ACTIONS "/MenuBar/File/Extension Actions"
+#define POPUP_PATH_EXTENSION_ACTIONS "/background/Before Zoom Items/Extension Actions"
+
+#define NETWORK_URI "network:"
+#define COMPUTER_URI "computer:"
+#define BURN_CD_URI "burn:"
+
+/* Struct that stores all the info necessary to activate a bookmark. */
+typedef struct
+{
+ CajaBookmark *bookmark;
+ CajaWindow *window;
+ guint changed_handler_id;
+ CajaBookmarkFailedCallback failed_callback;
+} BookmarkHolder;
+
+static BookmarkHolder *
+bookmark_holder_new (CajaBookmark *bookmark,
+ CajaWindow *window,
+ GCallback refresh_callback,
+ CajaBookmarkFailedCallback failed_callback)
+{
+ BookmarkHolder *new_bookmark_holder;
+
+ new_bookmark_holder = g_new (BookmarkHolder, 1);
+ new_bookmark_holder->window = window;
+ new_bookmark_holder->bookmark = bookmark;
+ new_bookmark_holder->failed_callback = failed_callback;
+ /* Ref the bookmark because it might be unreffed away while
+ * we're holding onto it (not an issue for window).
+ */
+ g_object_ref (bookmark);
+ new_bookmark_holder->changed_handler_id =
+ g_signal_connect_object (bookmark, "appearance_changed",
+ refresh_callback,
+ window, G_CONNECT_SWAPPED);
+
+ return new_bookmark_holder;
+}
+
+static void
+bookmark_holder_free (BookmarkHolder *bookmark_holder)
+{
+ g_signal_handler_disconnect (bookmark_holder->bookmark,
+ bookmark_holder->changed_handler_id);
+ g_object_unref (bookmark_holder->bookmark);
+ g_free (bookmark_holder);
+}
+
+static void
+bookmark_holder_free_cover (gpointer callback_data, GClosure *closure)
+{
+ bookmark_holder_free (callback_data);
+}
+
+static gboolean
+should_open_in_new_tab (void)
+{
+ /* FIXME this is duplicated */
+ GdkEvent *event;
+
+ event = gtk_get_current_event ();
+
+ if (event == NULL)
+ {
+ return FALSE;
+ }
+
+ if (event->type == GDK_BUTTON_PRESS || event->type == GDK_BUTTON_RELEASE)
+ {
+ return event->button.button == 2;
+ }
+
+ gdk_event_free (event);
+
+ return FALSE;
+}
+
+static void
+activate_bookmark_in_menu_item (GtkAction *action, gpointer user_data)
+{
+ CajaWindowSlot *slot;
+ BookmarkHolder *holder;
+ GFile *location;
+
+ holder = (BookmarkHolder *)user_data;
+
+ if (caja_bookmark_uri_known_not_to_exist (holder->bookmark))
+ {
+ holder->failed_callback (holder->window, holder->bookmark);
+ }
+ else
+ {
+ location = caja_bookmark_get_location (holder->bookmark);
+ slot = caja_window_get_active_slot (holder->window);
+ caja_window_slot_go_to (slot,
+ location,
+ should_open_in_new_tab ());
+ g_object_unref (location);
+ }
+}
+
+void
+caja_menus_append_bookmark_to_menu (CajaWindow *window,
+ CajaBookmark *bookmark,
+ const char *parent_path,
+ const char *parent_id,
+ guint index_in_parent,
+ GtkActionGroup *action_group,
+ guint merge_id,
+ GCallback refresh_callback,
+ CajaBookmarkFailedCallback failed_callback)
+{
+ BookmarkHolder *bookmark_holder;
+ char action_name[128];
+ char *name;
+ char *path;
+ GdkPixbuf *pixbuf;
+ GtkAction *action;
+ GtkWidget *menuitem;
+
+ g_assert (CAJA_IS_WINDOW (window));
+ g_assert (CAJA_IS_BOOKMARK (bookmark));
+
+ bookmark_holder = bookmark_holder_new (bookmark, window, refresh_callback, failed_callback);
+ name = caja_bookmark_get_name (bookmark);
+
+ /* Create menu item with pixbuf */
+ pixbuf = caja_bookmark_get_pixbuf (bookmark, GTK_ICON_SIZE_MENU);
+
+ g_snprintf (action_name, sizeof (action_name), "%s%d", parent_id, index_in_parent);
+
+ action = gtk_action_new (action_name,
+ name,
+ _("Go to the location specified by this bookmark"),
+ NULL);
+
+ g_object_set_data_full (G_OBJECT (action), "menu-icon",
+ g_object_ref (pixbuf),
+ g_object_unref);
+
+ g_signal_connect_data (action, "activate",
+ G_CALLBACK (activate_bookmark_in_menu_item),
+ bookmark_holder,
+ bookmark_holder_free_cover, 0);
+
+ gtk_action_group_add_action (action_group,
+ GTK_ACTION (action));
+
+ g_object_unref (action);
+
+ gtk_ui_manager_add_ui (window->details->ui_manager,
+ merge_id,
+ parent_path,
+ action_name,
+ action_name,
+ GTK_UI_MANAGER_MENUITEM,
+ FALSE);
+
+ path = g_strdup_printf ("%s/%s", parent_path, action_name);
+ menuitem = gtk_ui_manager_get_widget (window->details->ui_manager,
+ path);
+ gtk_image_menu_item_set_always_show_image (GTK_IMAGE_MENU_ITEM (menuitem),
+ TRUE);
+
+ g_object_unref (pixbuf);
+ g_free (path);
+ g_free (name);
+}
+
+static void
+action_close_window_slot_callback (GtkAction *action,
+ gpointer user_data)
+{
+ CajaWindow *window;
+ CajaWindowSlot *slot;
+
+ window = CAJA_WINDOW (user_data);
+ slot = caja_window_get_active_slot (window);
+
+ caja_window_slot_close (slot);
+}
+
+static void
+action_connect_to_server_callback (GtkAction *action,
+ gpointer user_data)
+{
+ CajaWindow *window = CAJA_WINDOW (user_data);
+ CajaWindowSlot *slot;
+ GtkWidget *dialog;
+ GFile *location;
+
+ slot = caja_window_get_active_slot (window);
+ location = caja_window_slot_get_location (slot);
+ dialog = caja_connect_server_dialog_new (window, location);
+ if (location)
+ {
+ g_object_unref (location);
+ }
+
+ gtk_widget_show (dialog);
+}
+
+static void
+action_stop_callback (GtkAction *action,
+ gpointer user_data)
+{
+ CajaWindow *window;
+ CajaWindowSlot *slot;
+
+ window = CAJA_WINDOW (user_data);
+ slot = caja_window_get_active_slot (window);
+
+ caja_window_slot_stop_loading (slot);
+}
+
+static void
+action_undo_callback (GtkAction *action,
+ gpointer user_data)
+{
+ caja_undo_manager_undo
+ (CAJA_WINDOW (user_data)->application->undo_manager);
+}
+
+static void
+action_home_callback (GtkAction *action,
+ gpointer user_data)
+{
+ CajaWindow *window;
+ CajaWindowSlot *slot;
+
+ window = CAJA_WINDOW (user_data);
+ slot = caja_window_get_active_slot (window);
+
+ caja_window_slot_go_home (slot,
+ should_open_in_new_tab ());
+}
+
+static void
+action_go_to_computer_callback (GtkAction *action,
+ gpointer user_data)
+{
+ CajaWindow *window;
+ CajaWindowSlot *slot;
+ GFile *computer;
+
+ window = CAJA_WINDOW (user_data);
+ slot = caja_window_get_active_slot (window);
+
+ computer = g_file_new_for_uri (COMPUTER_URI);
+ caja_window_slot_go_to (slot,
+ computer,
+ should_open_in_new_tab ());
+ g_object_unref (computer);
+}
+
+static void
+action_go_to_network_callback (GtkAction *action,
+ gpointer user_data)
+{
+ CajaWindow *window;
+ CajaWindowSlot *slot;
+ GFile *network;
+
+ window = CAJA_WINDOW (user_data);
+ slot = caja_window_get_active_slot (window);
+
+ network = g_file_new_for_uri (NETWORK_URI);
+ caja_window_slot_go_to (slot,
+ network,
+ should_open_in_new_tab ());
+ g_object_unref (network);
+}
+
+static void
+action_go_to_templates_callback (GtkAction *action,
+ gpointer user_data)
+{
+ CajaWindow *window;
+ CajaWindowSlot *slot;
+ char *path;
+ GFile *location;
+
+ window = CAJA_WINDOW (user_data);
+ slot = caja_window_get_active_slot (window);
+
+ path = caja_get_templates_directory ();
+ location = g_file_new_for_path (path);
+ g_free (path);
+ caja_window_slot_go_to (slot,
+ location,
+ should_open_in_new_tab ());
+ g_object_unref (location);
+}
+
+static void
+action_go_to_trash_callback (GtkAction *action,
+ gpointer user_data)
+{
+ CajaWindow *window;
+ CajaWindowSlot *slot;
+ GFile *trash;
+
+ window = CAJA_WINDOW (user_data);
+ slot = caja_window_get_active_slot (window);
+
+ trash = g_file_new_for_uri ("trash:///");
+ caja_window_slot_go_to (slot,
+ trash,
+ should_open_in_new_tab ());
+ g_object_unref (trash);
+}
+
+static void
+action_reload_callback (GtkAction *action,
+ gpointer user_data)
+{
+ caja_window_reload (CAJA_WINDOW (user_data));
+}
+
+static void
+action_zoom_in_callback (GtkAction *action,
+ gpointer user_data)
+{
+ caja_window_zoom_in (CAJA_WINDOW (user_data));
+}
+
+static void
+action_zoom_out_callback (GtkAction *action,
+ gpointer user_data)
+{
+ caja_window_zoom_out (CAJA_WINDOW (user_data));
+}
+
+static void
+action_zoom_normal_callback (GtkAction *action,
+ gpointer user_data)
+{
+ caja_window_zoom_to_default (CAJA_WINDOW (user_data));
+}
+
+static void
+action_show_hidden_files_callback (GtkAction *action,
+ gpointer callback_data)
+{
+ CajaWindow *window;
+ CajaWindowShowHiddenFilesMode mode;
+
+ window = CAJA_WINDOW (callback_data);
+
+ if (gtk_toggle_action_get_active (GTK_TOGGLE_ACTION (action)))
+ {
+ mode = CAJA_WINDOW_SHOW_HIDDEN_FILES_ENABLE;
+ }
+ else
+ {
+ mode = CAJA_WINDOW_SHOW_HIDDEN_FILES_DISABLE;
+ }
+
+ caja_window_info_set_hidden_files_mode (window, mode);
+}
+
+static void
+show_hidden_files_preference_callback (gpointer callback_data)
+{
+ CajaWindow *window;
+ GtkAction *action;
+
+ window = CAJA_WINDOW (callback_data);
+
+ if (window->details->show_hidden_files_mode == CAJA_WINDOW_SHOW_HIDDEN_FILES_DEFAULT)
+ {
+ action = gtk_action_group_get_action (window->details->main_action_group, CAJA_ACTION_SHOW_HIDDEN_FILES);
+ g_assert (GTK_IS_ACTION (action));
+
+ /* update button */
+ g_signal_handlers_block_by_func (action, action_show_hidden_files_callback, window);
+ gtk_toggle_action_set_active (GTK_TOGGLE_ACTION (action),
+ eel_preferences_get_boolean (CAJA_PREFERENCES_SHOW_HIDDEN_FILES));
+ g_signal_handlers_unblock_by_func (action, action_show_hidden_files_callback, window);
+
+ /* inform views */
+ caja_window_info_set_hidden_files_mode (window, CAJA_WINDOW_SHOW_HIDDEN_FILES_DEFAULT);
+
+ }
+}
+
+static void
+preferences_respond_callback (GtkDialog *dialog,
+ gint response_id)
+{
+ if (response_id == GTK_RESPONSE_CLOSE)
+ {
+ gtk_widget_destroy (GTK_WIDGET (dialog));
+ }
+}
+
+static void
+action_preferences_callback (GtkAction *action,
+ gpointer user_data)
+{
+ GtkWindow *window;
+
+ window = GTK_WINDOW (user_data);
+
+ caja_file_management_properties_dialog_show (G_CALLBACK (preferences_respond_callback), window);
+}
+
+static void
+action_backgrounds_and_emblems_callback (GtkAction *action,
+ gpointer user_data)
+{
+ GtkWindow *window;
+
+ window = GTK_WINDOW (user_data);
+
+ caja_property_browser_show (gtk_window_get_screen (window));
+}
+
+static void
+action_about_caja_callback (GtkAction *action,
+ gpointer user_data)
+{
+ const gchar *authors[] =
+ {
+ "Alexander Larsson",
+ "Ali Abdin",
+ "Anders Carlsson",
+ "Andy Hertzfeld",
+ "Arlo Rose",
+ "Darin Adler",
+ "David Camp",
+ "Eli Goldberg",
+ "Elliot Lee",
+ "Eskil Heyn Olsen",
+ "Ettore Perazzoli",
+ "Gene Z. Ragan",
+ "George Lebl",
+ "Ian McKellar",
+ "J Shane Culpepper",
+ "James Willcox",
+ "Jan Arne Petersen",
+ "John Harper",
+ "John Sullivan",
+ "Josh Barrow",
+ "Maciej Stachowiak",
+ "Mark McLoughlin",
+ "Mathieu Lacage",
+ "Mike Engber",
+ "Mike Fleming",
+ "Pavel Cisler",
+ "Ramiro Estrugo",
+ "Raph Levien",
+ "Rebecca Schulman",
+ "Robey Pointer",
+ "Robin * Slomkowski",
+ "Seth Nickell",
+ "Susan Kare",
+ NULL
+ };
+ const gchar *documenters[] =
+ {
+ "MATE Documentation Team",
+ "Sun Microsystem",
+ NULL
+ };
+ const gchar *license[] =
+ {
+ N_("Caja is free software; you can redistribute it and/or modify "
+ "it under the terms of the GNU General Public License as published by "
+ "the Free Software Foundation; either version 2 of the License, or "
+ "(at your option) any later version."),
+ N_("Caja is distributed in the hope that it will be useful, "
+ "but WITHOUT ANY WARRANTY; without even the implied warranty of "
+ "MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the "
+ "GNU General Public License for more details."),
+ N_("You should have received a copy of the GNU General Public License "
+ "along with Caja; if not, write to the Free Software Foundation, Inc., "
+ "51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA")
+ };
+ gchar *license_trans;
+
+ license_trans = g_strjoin ("\n\n", _(license[0]), _(license[1]),
+ _(license[2]), NULL);
+
+ gtk_show_about_dialog (GTK_WINDOW (user_data),
+ "program-name", _("Caja"),
+ "version", VERSION,
+ "comments", _("Caja lets you organize "
+ "files and folders, both on "
+ "your computer and online."),
+ "copyright", _("Copyright \xC2\xA9 1999-2009 "
+ "The Caja authors"),
+ "license", license_trans,
+ "wrap-license", TRUE,
+ "authors", authors,
+ "documenters", documenters,
+ /* Translators should localize the following string
+ * which will be displayed at the bottom of the about
+ * box to give credit to the translator(s).
+ */
+ "translator-credits", _("translator-credits"),
+ "logo-icon-name", "caja",
+ "website", "https://github.com/Perberos/Mate-Desktop-Environment"
+ "/wiki/Mate-file-manager",
+ "website-label", _("Caja Web Site"),
+ NULL);
+
+ g_free (license_trans);
+
+}
+
+static void
+action_up_callback (GtkAction *action,
+ gpointer user_data)
+{
+ caja_window_go_up (CAJA_WINDOW (user_data), FALSE, should_open_in_new_tab ());
+}
+
+static void
+action_caja_manual_callback (GtkAction *action,
+ gpointer user_data)
+{
+ CajaWindow *window;
+ GError *error;
+ GtkWidget *dialog;
+
+ error = NULL;
+ window = CAJA_WINDOW (user_data);
+
+ if (CAJA_IS_DESKTOP_WINDOW (window))
+ {
+#if GTK_CHECK_VERSION(2, 24, 0)
+ gdk_spawn_command_line_on_screen(gtk_window_get_screen(GTK_WINDOW(window)), "mate-help", &error);
+#else
+
+
+
+ g_spawn_command_line_async("mate-help", &error);
+#endif
+
+ }
+ else
+ {
+ gtk_show_uri (gtk_window_get_screen (GTK_WINDOW (window)),
+ "ghelp:user-guide#goscaja-1",
+ gtk_get_current_event_time (), &error);
+ }
+
+ if (error)
+ {
+ dialog = gtk_message_dialog_new (GTK_WINDOW (window),
+ GTK_DIALOG_MODAL,
+ GTK_MESSAGE_ERROR,
+ GTK_BUTTONS_OK,
+ _("There was an error displaying help: \n%s"),
+ error->message);
+ g_signal_connect (G_OBJECT (dialog), "response",
+ G_CALLBACK (gtk_widget_destroy),
+ NULL);
+
+ gtk_window_set_resizable (GTK_WINDOW (dialog), FALSE);
+ gtk_widget_show (dialog);
+ g_error_free (error);
+ }
+}
+
+static void
+menu_item_select_cb (GtkMenuItem *proxy,
+ CajaWindow *window)
+{
+ GtkAction *action;
+ char *message;
+
+ action = gtk_activatable_get_related_action (GTK_ACTIVATABLE (proxy));
+ g_return_if_fail (action != NULL);
+
+ g_object_get (G_OBJECT (action), "tooltip", &message, NULL);
+ if (message)
+ {
+ gtk_statusbar_push (GTK_STATUSBAR (window->details->statusbar),
+ window->details->help_message_cid, message);
+ g_free (message);
+ }
+}
+
+static void
+menu_item_deselect_cb (GtkMenuItem *proxy,
+ CajaWindow *window)
+{
+ gtk_statusbar_pop (GTK_STATUSBAR (window->details->statusbar),
+ window->details->help_message_cid);
+}
+
+static GtkWidget *
+get_event_widget (GtkWidget *proxy)
+{
+ GtkWidget *widget;
+
+ /**
+ * Finding the interesting widget requires internal knowledge of
+ * the widgets in question. This can't be helped, but by keeping
+ * the sneaky code in one place, it can easily be updated.
+ */
+ if (GTK_IS_MENU_ITEM (proxy))
+ {
+ /* Menu items already forward middle clicks */
+ widget = NULL;
+ }
+ else if (GTK_IS_MENU_TOOL_BUTTON (proxy))
+ {
+ widget = eel_gtk_menu_tool_button_get_button (GTK_MENU_TOOL_BUTTON (proxy));
+ }
+ else if (GTK_IS_TOOL_BUTTON (proxy))
+ {
+ /* The tool button's button is the direct child */
+ widget = gtk_bin_get_child (GTK_BIN (proxy));
+ }
+ else if (GTK_IS_BUTTON (proxy))
+ {
+ widget = proxy;
+ }
+ else
+ {
+ /* Don't touch anything we don't know about */
+ widget = NULL;
+ }
+
+ return widget;
+}
+
+static gboolean
+proxy_button_press_event_cb (GtkButton *button,
+ GdkEventButton *event,
+ gpointer user_data)
+{
+ if (event->button == 2)
+ {
+ g_signal_emit_by_name (button, "pressed", 0);
+ }
+
+ return FALSE;
+}
+
+static gboolean
+proxy_button_release_event_cb (GtkButton *button,
+ GdkEventButton *event,
+ gpointer user_data)
+{
+ if (event->button == 2)
+ {
+ g_signal_emit_by_name (button, "released", 0);
+ }
+
+ return FALSE;
+}
+
+static void
+disconnect_proxy_cb (GtkUIManager *manager,
+ GtkAction *action,
+ GtkWidget *proxy,
+ CajaWindow *window)
+{
+ GtkWidget *widget;
+
+ if (GTK_IS_MENU_ITEM (proxy))
+ {
+ g_signal_handlers_disconnect_by_func
+ (proxy, G_CALLBACK (menu_item_select_cb), window);
+ g_signal_handlers_disconnect_by_func
+ (proxy, G_CALLBACK (menu_item_deselect_cb), window);
+ }
+
+ widget = get_event_widget (proxy);
+ if (widget)
+ {
+ g_signal_handlers_disconnect_by_func (widget,
+ G_CALLBACK (proxy_button_press_event_cb),
+ action);
+ g_signal_handlers_disconnect_by_func (widget,
+ G_CALLBACK (proxy_button_release_event_cb),
+ action);
+ }
+
+}
+
+static void
+connect_proxy_cb (GtkUIManager *manager,
+ GtkAction *action,
+ GtkWidget *proxy,
+ CajaWindow *window)
+{
+ GdkPixbuf *icon;
+ GtkWidget *widget;
+
+ if (GTK_IS_MENU_ITEM (proxy))
+ {
+ g_signal_connect (proxy, "select",
+ G_CALLBACK (menu_item_select_cb), window);
+ g_signal_connect (proxy, "deselect",
+ G_CALLBACK (menu_item_deselect_cb), window);
+
+
+ /* This is a way to easily get pixbufs into the menu items */
+ icon = g_object_get_data (G_OBJECT (action), "menu-icon");
+ if (icon != NULL)
+ {
+ gtk_image_menu_item_set_image (GTK_IMAGE_MENU_ITEM (proxy),
+ gtk_image_new_from_pixbuf (icon));
+ }
+ }
+ if (GTK_IS_TOOL_BUTTON (proxy))
+ {
+ icon = g_object_get_data (G_OBJECT (action), "toolbar-icon");
+ if (icon != NULL)
+ {
+ widget = gtk_image_new_from_pixbuf (icon);
+ gtk_widget_show (widget);
+ gtk_tool_button_set_icon_widget (GTK_TOOL_BUTTON (proxy),
+ widget);
+ }
+ }
+
+ widget = get_event_widget (proxy);
+ if (widget)
+ {
+ g_signal_connect (widget, "button-press-event",
+ G_CALLBACK (proxy_button_press_event_cb),
+ action);
+ g_signal_connect (widget, "button-release-event",
+ G_CALLBACK (proxy_button_release_event_cb),
+ action);
+ }
+}
+
+static void
+trash_state_changed_cb (CajaTrashMonitor *monitor,
+ gboolean state,
+ CajaWindow *window)
+{
+ GtkActionGroup *action_group;
+ GtkAction *action;
+ GIcon *gicon;
+
+ action_group = window->details->main_action_group;
+ action = gtk_action_group_get_action (action_group, "Go to Trash");
+
+ gicon = caja_trash_monitor_get_icon ();
+
+ if (gicon)
+ {
+ g_object_set (action, "gicon", gicon, NULL);
+ g_object_unref (gicon);
+ }
+}
+
+static void
+caja_window_initialize_trash_icon_monitor (CajaWindow *window)
+{
+ CajaTrashMonitor *monitor;
+
+ monitor = caja_trash_monitor_get ();
+
+ trash_state_changed_cb (monitor, TRUE, window);
+
+ g_signal_connect (monitor, "trash_state_changed",
+ G_CALLBACK (trash_state_changed_cb), window);
+}
+
+static const GtkActionEntry main_entries[] =
+{
+ /* name, stock id, label */ { "File", NULL, N_("_File") },
+ /* name, stock id, label */ { "Edit", NULL, N_("_Edit") },
+ /* name, stock id, label */ { "View", NULL, N_("_View") },
+ /* name, stock id, label */ { "Help", NULL, N_("_Help") },
+ /* name, stock id */ { "Close", GTK_STOCK_CLOSE,
+ /* label, accelerator */ N_("_Close"), "<control>W",
+ /* tooltip */ N_("Close this folder"),
+ G_CALLBACK (action_close_window_slot_callback)
+ },
+ {
+ "Backgrounds and Emblems", NULL,
+ N_("_Backgrounds and Emblems..."),
+ NULL, N_("Display patterns, colors, and emblems that can be used to customize appearance"),
+ G_CALLBACK (action_backgrounds_and_emblems_callback)
+ },
+ {
+ "Preferences", GTK_STOCK_PREFERENCES,
+ N_("Prefere_nces"),
+ NULL, N_("Edit Caja preferences"),
+ G_CALLBACK (action_preferences_callback)
+ },
+ /* name, stock id, label */ { "Undo", NULL, N_("_Undo"),
+ "<control>Z", N_("Undo the last text change"),
+ G_CALLBACK (action_undo_callback)
+ },
+ /* name, stock id, label */ { "Up", GTK_STOCK_GO_UP, N_("Open _Parent"),
+ "<alt>Up", N_("Open the parent folder"),
+ G_CALLBACK (action_up_callback)
+ },
+ /* name, stock id, label */ { "UpAccel", NULL, "UpAccel",
+ "", NULL,
+ G_CALLBACK (action_up_callback)
+ },
+ /* name, stock id */ { "Stop", GTK_STOCK_STOP,
+ /* label, accelerator */ N_("_Stop"), NULL,
+ /* tooltip */ N_("Stop loading the current location"),
+ G_CALLBACK (action_stop_callback)
+ },
+ /* name, stock id */ { "Reload", GTK_STOCK_REFRESH,
+ /* label, accelerator */ N_("_Reload"), "<control>R",
+ /* tooltip */ N_("Reload the current location"),
+ G_CALLBACK (action_reload_callback)
+ },
+ /* name, stock id */ { "Caja Manual", GTK_STOCK_HELP,
+ /* label, accelerator */ N_("_Contents"), "F1",
+ /* tooltip */ N_("Display Caja help"),
+ G_CALLBACK (action_caja_manual_callback)
+ },
+ /* name, stock id */ { "About Caja", GTK_STOCK_ABOUT,
+ /* label, accelerator */ N_("_About"), NULL,
+ /* tooltip */ N_("Display credits for the creators of Caja"),
+ G_CALLBACK (action_about_caja_callback)
+ },
+ /* name, stock id */ { "Zoom In", GTK_STOCK_ZOOM_IN,
+ /* label, accelerator */ N_("Zoom _In"), "<control>plus",
+ /* tooltip */ N_("Increase the view size"),
+ G_CALLBACK (action_zoom_in_callback)
+ },
+ /* name, stock id */ { "ZoomInAccel", NULL,
+ /* label, accelerator */ "ZoomInAccel", "<control>equal",
+ /* tooltip */ NULL,
+ G_CALLBACK (action_zoom_in_callback)
+ },
+ /* name, stock id */ { "ZoomInAccel2", NULL,
+ /* label, accelerator */ "ZoomInAccel2", "<control>KP_Add",
+ /* tooltip */ NULL,
+ G_CALLBACK (action_zoom_in_callback)
+ },
+ /* name, stock id */ { "Zoom Out", GTK_STOCK_ZOOM_OUT,
+ /* label, accelerator */ N_("Zoom _Out"), "<control>minus",
+ /* tooltip */ N_("Decrease the view size"),
+ G_CALLBACK (action_zoom_out_callback)
+ },
+ /* name, stock id */ { "ZoomOutAccel", NULL,
+ /* label, accelerator */ "ZoomOutAccel", "<control>KP_Subtract",
+ /* tooltip */ NULL,
+ G_CALLBACK (action_zoom_out_callback)
+ },
+ /* name, stock id */ { "Zoom Normal", GTK_STOCK_ZOOM_100,
+ /* label, accelerator */ N_("Normal Si_ze"), "<control>0",
+ /* tooltip */ N_("Use the normal view size"),
+ G_CALLBACK (action_zoom_normal_callback)
+ },
+ /* name, stock id */ { "Connect to Server", NULL,
+ /* label, accelerator */ N_("Connect to _Server..."), NULL,
+ /* tooltip */ N_("Connect to a remote computer or shared disk"),
+ G_CALLBACK (action_connect_to_server_callback)
+ },
+ /* name, stock id */ { "Home", CAJA_ICON_HOME,
+ /* label, accelerator */ N_("_Home Folder"), "<alt>Home",
+ /* tooltip */ N_("Open your personal folder"),
+ G_CALLBACK (action_home_callback)
+ },
+ /* name, stock id */ { "Go to Computer", CAJA_ICON_COMPUTER,
+ /* label, accelerator */ N_("_Computer"), NULL,
+ /* tooltip */ N_("Browse all local and remote disks and folders accessible from this computer"),
+ G_CALLBACK (action_go_to_computer_callback)
+ },
+ /* name, stock id */ { "Go to Network", CAJA_ICON_NETWORK,
+ /* label, accelerator */ N_("_Network"), NULL,
+ /* tooltip */ N_("Browse bookmarked and local network locations"),
+ G_CALLBACK (action_go_to_network_callback)
+ },
+ /* name, stock id */ { "Go to Templates", CAJA_ICON_TEMPLATE,
+ /* label, accelerator */ N_("T_emplates"), NULL,
+ /* tooltip */ N_("Open your personal templates folder"),
+ G_CALLBACK (action_go_to_templates_callback)
+ },
+ /* name, stock id */ { "Go to Trash", CAJA_ICON_TRASH,
+ /* label, accelerator */ N_("_Trash"), NULL,
+ /* tooltip */ N_("Open your personal trash folder"),
+ G_CALLBACK (action_go_to_trash_callback)
+ },
+};
+
+static const GtkToggleActionEntry main_toggle_entries[] =
+{
+ /* name, stock id */ { "Show Hidden Files", NULL,
+ /* label, accelerator */ N_("Show _Hidden Files"), "<control>H",
+ /* tooltip */ N_("Toggle the display of hidden files in the current window"),
+ G_CALLBACK (action_show_hidden_files_callback),
+ TRUE
+ },
+};
+
+/**
+ * caja_window_initialize_menus
+ *
+ * Create and install the set of menus for this window.
+ * @window: A recently-created CajaWindow.
+ */
+void
+caja_window_initialize_menus (CajaWindow *window)
+{
+ GtkActionGroup *action_group;
+ GtkUIManager *ui_manager;
+ GtkAction *action;
+ const char *ui;
+
+ action_group = gtk_action_group_new ("ShellActions");
+ gtk_action_group_set_translation_domain (action_group, GETTEXT_PACKAGE);
+ window->details->main_action_group = action_group;
+ gtk_action_group_add_actions (action_group,
+ main_entries, G_N_ELEMENTS (main_entries),
+ window);
+ gtk_action_group_add_toggle_actions (action_group,
+ main_toggle_entries, G_N_ELEMENTS (main_toggle_entries),
+ window);
+
+ action = gtk_action_group_get_action (action_group, CAJA_ACTION_UP);
+ g_object_set (action, "short_label", _("_Up"), NULL);
+
+ action = gtk_action_group_get_action (action_group, CAJA_ACTION_HOME);
+ g_object_set (action, "short_label", _("_Home"), NULL);
+
+ action = gtk_action_group_get_action (action_group, CAJA_ACTION_SHOW_HIDDEN_FILES);
+ g_signal_handlers_block_by_func (action, action_show_hidden_files_callback, window);
+ gtk_toggle_action_set_active (GTK_TOGGLE_ACTION (action),
+ eel_preferences_get_boolean (CAJA_PREFERENCES_SHOW_HIDDEN_FILES));
+ g_signal_handlers_unblock_by_func (action, action_show_hidden_files_callback, window);
+
+
+ eel_preferences_add_callback_while_alive (CAJA_PREFERENCES_SHOW_HIDDEN_FILES,
+ show_hidden_files_preference_callback,
+ window, G_OBJECT (window));
+
+ window->details->ui_manager = gtk_ui_manager_new ();
+ ui_manager = window->details->ui_manager;
+ gtk_window_add_accel_group (GTK_WINDOW (window),
+ gtk_ui_manager_get_accel_group (ui_manager));
+
+ g_signal_connect (ui_manager, "connect_proxy",
+ G_CALLBACK (connect_proxy_cb), window);
+ g_signal_connect (ui_manager, "disconnect_proxy",
+ G_CALLBACK (disconnect_proxy_cb), window);
+
+ gtk_ui_manager_insert_action_group (ui_manager, action_group, 0);
+ g_object_unref (action_group); /* owned by ui manager */
+
+ ui = caja_ui_string_get ("caja-shell-ui.xml");
+ gtk_ui_manager_add_ui_from_string (ui_manager, ui, -1, NULL);
+
+ caja_window_initialize_trash_icon_monitor (window);
+}
+
+static GList *
+get_extension_menus (CajaWindow *window)
+{
+ CajaWindowSlot *slot;
+ GList *providers;
+ GList *items;
+ GList *l;
+
+ providers = caja_module_get_extensions_for_type (CAJA_TYPE_MENU_PROVIDER);
+ items = NULL;
+
+ slot = caja_window_get_active_slot (window);
+
+ for (l = providers; l != NULL; l = l->next)
+ {
+ CajaMenuProvider *provider;
+ GList *file_items;
+
+ provider = CAJA_MENU_PROVIDER (l->data);
+ file_items = caja_menu_provider_get_background_items (provider,
+ GTK_WIDGET (window),
+ slot->viewed_file);
+ items = g_list_concat (items, file_items);
+ }
+
+ caja_module_extension_list_free (providers);
+
+ return items;
+}
+
+static void
+add_extension_menu_items (CajaWindow *window,
+ guint merge_id,
+ GtkActionGroup *action_group,
+ GList *menu_items,
+ const char *subdirectory)
+{
+ GtkUIManager *ui_manager;
+ GList *l;
+
+ ui_manager = window->details->ui_manager;
+
+ for (l = menu_items; l; l = l->next)
+ {
+ CajaMenuItem *item;
+ CajaMenu *menu;
+ GtkAction *action;
+ char *path;
+
+ item = CAJA_MENU_ITEM (l->data);
+
+ g_object_get (item, "menu", &menu, NULL);
+
+ action = caja_action_from_menu_item (item);
+ gtk_action_group_add_action_with_accel (action_group, action, NULL);
+
+ path = g_build_path ("/", POPUP_PATH_EXTENSION_ACTIONS, subdirectory, NULL);
+ gtk_ui_manager_add_ui (ui_manager,
+ merge_id,
+ path,
+ gtk_action_get_name (action),
+ gtk_action_get_name (action),
+ (menu != NULL) ? GTK_UI_MANAGER_MENU : GTK_UI_MANAGER_MENUITEM,
+ FALSE);
+ g_free (path);
+
+ path = g_build_path ("/", MENU_PATH_EXTENSION_ACTIONS, subdirectory, NULL);
+ gtk_ui_manager_add_ui (ui_manager,
+ merge_id,
+ path,
+ gtk_action_get_name (action),
+ gtk_action_get_name (action),
+ (menu != NULL) ? GTK_UI_MANAGER_MENU : GTK_UI_MANAGER_MENUITEM,
+ FALSE);
+ g_free (path);
+
+ /* recursively fill the menu */
+ if (menu != NULL)
+ {
+ char *subdir;
+ GList *children;
+
+ children = caja_menu_get_items (menu);
+
+ subdir = g_build_path ("/", subdirectory, "/", gtk_action_get_name (action), NULL);
+ add_extension_menu_items (window,
+ merge_id,
+ action_group,
+ children,
+ subdir);
+
+ caja_menu_item_list_free (children);
+ g_free (subdir);
+ }
+ }
+}
+
+void
+caja_window_load_extension_menus (CajaWindow *window)
+{
+ GtkActionGroup *action_group;
+ GList *items;
+ guint merge_id;
+
+ if (window->details->extensions_menu_merge_id != 0)
+ {
+ gtk_ui_manager_remove_ui (window->details->ui_manager,
+ window->details->extensions_menu_merge_id);
+ window->details->extensions_menu_merge_id = 0;
+ }
+
+ if (window->details->extensions_menu_action_group != NULL)
+ {
+ gtk_ui_manager_remove_action_group (window->details->ui_manager,
+ window->details->extensions_menu_action_group);
+ window->details->extensions_menu_action_group = NULL;
+ }
+
+ merge_id = gtk_ui_manager_new_merge_id (window->details->ui_manager);
+ window->details->extensions_menu_merge_id = merge_id;
+ action_group = gtk_action_group_new ("ExtensionsMenuGroup");
+ window->details->extensions_menu_action_group = action_group;
+ gtk_action_group_set_translation_domain (action_group, GETTEXT_PACKAGE);
+ gtk_ui_manager_insert_action_group (window->details->ui_manager, action_group, 0);
+ g_object_unref (action_group); /* owned by ui manager */
+
+ items = get_extension_menus (window);
+
+ if (items != NULL)
+ {
+ add_extension_menu_items (window, merge_id, action_group, items, "");
+
+ g_list_foreach (items, (GFunc) g_object_unref, NULL);
+ g_list_free (items);
+ }
+}
+
+void
+caja_window_remove_trash_monitor_callback (CajaWindow *window)
+{
+ CajaTrashMonitor *monitor;
+
+ monitor = caja_trash_monitor_get ();
+
+ g_signal_handlers_disconnect_by_func (monitor,
+ trash_state_changed_cb, window);
+}
+