diff options
author | Matthew Barnes <mbarnes@redhat.com> | 2009-11-13 10:27:40 +0800 |
---|---|---|
committer | Matthew Barnes <mbarnes@redhat.com> | 2009-11-14 00:26:43 +0800 |
commit | c5e04ca04066ae2d92d3999626ef91d5d0606cab (patch) | |
tree | 4c4cc28faa947d29d9f6e575680549daf95ae753 | |
parent | ba89f0b2c4993c562a1bdb0f5ce90b654c3b68b5 (diff) | |
download | gsoc2013-evolution-c5e04ca04066ae2d92d3999626ef91d5d0606cab.tar gsoc2013-evolution-c5e04ca04066ae2d92d3999626ef91d5d0606cab.tar.gz gsoc2013-evolution-c5e04ca04066ae2d92d3999626ef91d5d0606cab.tar.bz2 gsoc2013-evolution-c5e04ca04066ae2d92d3999626ef91d5d0606cab.tar.lz gsoc2013-evolution-c5e04ca04066ae2d92d3999626ef91d5d0606cab.tar.xz gsoc2013-evolution-c5e04ca04066ae2d92d3999626ef91d5d0606cab.tar.zst gsoc2013-evolution-c5e04ca04066ae2d92d3999626ef91d5d0606cab.zip |
EWebView popup menu enhancements.
Bumps the GtkHtml dependency to 3.29.2 for gtk_html_unselect_all().
-rw-r--r-- | configure.ac | 2 | ||||
-rw-r--r-- | modules/addressbook/e-book-shell-content.c | 30 | ||||
-rw-r--r-- | modules/addressbook/e-book-shell-content.h | 3 | ||||
-rw-r--r-- | modules/addressbook/e-book-shell-view-actions.c | 57 | ||||
-rw-r--r-- | modules/calendar/e-memo-shell-content.c | 10 | ||||
-rw-r--r-- | modules/calendar/e-memo-shell-view-actions.c | 57 | ||||
-rw-r--r-- | modules/calendar/e-task-shell-content.c | 10 | ||||
-rw-r--r-- | modules/calendar/e-task-shell-view-actions.c | 57 | ||||
-rw-r--r-- | plugins/mark-all-read/mark-all-read.c | 26 | ||||
-rw-r--r-- | shell/e-shell-utils.c | 29 | ||||
-rw-r--r-- | shell/e-shell-utils.h | 4 | ||||
-rw-r--r-- | ui/evolution-contacts.ui | 3 | ||||
-rw-r--r-- | widgets/misc/e-popup-action.c | 344 | ||||
-rw-r--r-- | widgets/misc/e-popup-action.h | 15 | ||||
-rw-r--r-- | widgets/misc/e-web-view.c | 454 | ||||
-rw-r--r-- | widgets/misc/e-web-view.h | 21 |
16 files changed, 926 insertions, 196 deletions
diff --git a/configure.ac b/configure.ac index 40a426a580..0f38234dac 100644 --- a/configure.ac +++ b/configure.ac @@ -46,7 +46,7 @@ m4_define([gtk_minimum_version], [2.16.0]) m4_define([eds_minimum_version], [evo_version]) m4_define([gnome_icon_theme_minimum_version], [2.19.91]) m4_define([gnome_desktop_minimum_version], [2.26.0]) -m4_define([libgtkhtml_minimum_version], [3.29.1]) +m4_define([libgtkhtml_minimum_version], [3.29.2]) m4_define([gconf_minimum_version], [2.0.0]) dnl XXX Just a Guess m4_define([libglade_minimum_version], [2.0.0]) dnl XXX Just a Guess m4_define([libgnomecanvas_minimum_version], [2.0.0]) dnl XXX Just a Guess diff --git a/modules/addressbook/e-book-shell-content.c b/modules/addressbook/e-book-shell-content.c index 4eccc971df..1c121adc61 100644 --- a/modules/addressbook/e-book-shell-content.c +++ b/modules/addressbook/e-book-shell-content.c @@ -26,6 +26,7 @@ #include "e-util/e-binding.h" #include "e-util/e-selection.h" #include "e-util/gconf-bridge.h" +#include "shell/e-shell-utils.h" #include "widgets/misc/e-paned.h" #define E_BOOK_SHELL_CONTENT_GET_PRIVATE(obj) \ @@ -182,6 +183,10 @@ static void book_shell_content_constructed (GObject *object) { EBookShellContentPrivate *priv; + EShell *shell; + EShellView *shell_view; + EShellWindow *shell_window; + EShellContent *shell_content; GConfBridge *bridge; GtkWidget *container; GtkWidget *widget; @@ -192,6 +197,11 @@ book_shell_content_constructed (GObject *object) /* Chain up to parent's constructed() method. */ G_OBJECT_CLASS (parent_class)->constructed (object); + shell_content = E_SHELL_CONTENT (object); + shell_view = e_shell_content_get_shell_view (shell_content); + shell_window = e_shell_view_get_shell_window (shell_view); + shell = e_shell_window_get_shell (shell_window); + container = GTK_WIDGET (object); widget = e_paned_new (GTK_ORIENTATION_VERTICAL); @@ -199,9 +209,7 @@ book_shell_content_constructed (GObject *object) priv->paned = g_object_ref (widget); gtk_widget_show (widget); - e_binding_new ( - object, "orientation", - widget, "orientation"); + e_binding_new (object, "orientation", widget, "orientation"); container = widget; @@ -221,9 +229,7 @@ book_shell_content_constructed (GObject *object) gtk_paned_pack2 (GTK_PANED (container), widget, FALSE, FALSE); gtk_widget_show (widget); - e_binding_new ( - object, "preview-visible", - widget, "visible"); + e_binding_new (object, "preview-visible", widget, "visible"); container = widget; @@ -231,12 +237,13 @@ book_shell_content_constructed (GObject *object) eab_contact_display_set_mode ( EAB_CONTACT_DISPLAY (widget), EAB_CONTACT_DISPLAY_RENDER_NORMAL); + e_shell_configure_web_view (shell, E_WEB_VIEW (widget)); gtk_container_add (GTK_CONTAINER (container), widget); priv->preview = g_object_ref (widget); gtk_widget_show (widget); g_signal_connect_swapped ( - priv->preview, "send-message", + widget, "send-message", G_CALLBACK (book_shell_content_send_message_cb), object); /* Bind GObject properties to GConf keys. */ @@ -474,6 +481,15 @@ e_book_shell_content_set_current_view (EBookShellContent *book_shell_content, g_object_notify (G_OBJECT (book_shell_content), "current-view"); } +EABContactDisplay * +e_book_shell_content_get_preview (EBookShellContent *book_shell_content) +{ + g_return_val_if_fail ( + E_IS_BOOK_SHELL_CONTENT (book_shell_content), NULL); + + return EAB_CONTACT_DISPLAY (book_shell_content->priv->preview); +} + EContact * e_book_shell_content_get_preview_contact (EBookShellContent *book_shell_content) { diff --git a/modules/addressbook/e-book-shell-content.h b/modules/addressbook/e-book-shell-content.h index 31f8c35838..138b60d175 100644 --- a/modules/addressbook/e-book-shell-content.h +++ b/modules/addressbook/e-book-shell-content.h @@ -93,6 +93,9 @@ EAddressbookView * void e_book_shell_content_set_current_view (EBookShellContent *book_shell_content, EAddressbookView *addressbook_view); +EABContactDisplay * + e_book_shell_content_get_preview + (EBookShellContent *book_shell_content); EContact * e_book_shell_content_get_preview_contact (EBookShellContent *book_shell_content); void e_book_shell_content_set_preview_contact diff --git a/modules/addressbook/e-book-shell-view-actions.c b/modules/addressbook/e-book-shell-view-actions.c index 0ec4eac2e6..495aed6f1d 100644 --- a/modules/addressbook/e-book-shell-view-actions.c +++ b/modules/addressbook/e-book-shell-view-actions.c @@ -830,18 +830,11 @@ static GtkActionEntry contact_entries[] = { { "contact-open", NULL, - N_("_Open"), + N_("_Open Contact"), "<Control>o", N_("View the current contact"), G_CALLBACK (action_contact_open_cb) }, - { "contact-save-as", - GTK_STOCK_SAVE_AS, - N_("Save as vCard..."), - NULL, - N_("Save selected contacts as a vCard"), - G_CALLBACK (action_contact_save_as_cb) }, - { "contact-select-all", GTK_STOCK_SELECT_ALL, NULL, @@ -923,10 +916,6 @@ static EPopupActionEntry contact_popup_entries[] = { NULL, "contact-open" }, - { "contact-popup-save-as", - NULL, - "contact-save-as" }, - { "contact-popup-send-message", NULL, "contact-send-message" }, @@ -1035,11 +1024,30 @@ static EPopupActionEntry lockdown_printing_popup_entries[] = { "contact-print" } }; +static GtkActionEntry lockdown_save_to_disk_entries[] = { + + { "contact-save-as", + GTK_STOCK_SAVE_AS, + N_("Save as vCard..."), + NULL, + N_("Save selected contacts as a vCard"), + G_CALLBACK (action_contact_save_as_cb) } +}; + +static EPopupActionEntry lockdown_save_to_disk_popup_entries[] = { + + { "contact-popup-save-as", + NULL, + "contact-save-as" } +}; + void e_book_shell_view_actions_init (EBookShellView *book_shell_view) { EShellView *shell_view; EShellWindow *shell_window; + EBookShellContent *book_shell_content; + EABContactDisplay *contact_preview; GtkActionGroup *action_group; GConfBridge *bridge; GtkAction *action; @@ -1049,6 +1057,9 @@ e_book_shell_view_actions_init (EBookShellView *book_shell_view) shell_view = E_SHELL_VIEW (book_shell_view); shell_window = e_shell_view_get_shell_window (shell_view); + book_shell_content = book_shell_view->priv->book_shell_content; + contact_preview = e_book_shell_content_get_preview (book_shell_content); + /* Contact Actions */ action_group = ACTION_GROUP (CONTACTS); gtk_action_group_add_actions ( @@ -1074,11 +1085,22 @@ e_book_shell_view_actions_init (EBookShellView *book_shell_view) action_group = ACTION_GROUP (LOCKDOWN_PRINTING); gtk_action_group_add_actions ( action_group, lockdown_printing_entries, - G_N_ELEMENTS (lockdown_printing_entries), book_shell_view); + G_N_ELEMENTS (lockdown_printing_entries), + book_shell_view); e_action_group_add_popup_actions ( action_group, lockdown_printing_popup_entries, G_N_ELEMENTS (lockdown_printing_popup_entries)); + /* Lockdown Save-to-Disk Actions */ + action_group = ACTION_GROUP (LOCKDOWN_SAVE_TO_DISK); + gtk_action_group_add_actions ( + action_group, lockdown_save_to_disk_entries, + G_N_ELEMENTS (lockdown_save_to_disk_entries), + book_shell_view); + e_action_group_add_popup_actions ( + action_group, lockdown_save_to_disk_popup_entries, + G_N_ELEMENTS (lockdown_save_to_disk_popup_entries)); + /* Bind GObject properties to GConf keys. */ bridge = gconf_bridge_get (); @@ -1107,6 +1129,15 @@ e_book_shell_view_actions_init (EBookShellView *book_shell_view) e_binding_new ( ACTION (CONTACT_PREVIEW), "active", ACTION (CONTACT_VIEW_VERTICAL), "sensitive"); + + e_web_view_set_open_proxy ( + E_WEB_VIEW (contact_preview), ACTION (CONTACT_OPEN)); + + e_web_view_set_print_proxy ( + E_WEB_VIEW (contact_preview), ACTION (CONTACT_PRINT)); + + e_web_view_set_save_as_proxy ( + E_WEB_VIEW (contact_preview), ACTION (CONTACT_SAVE_AS)); } void diff --git a/modules/calendar/e-memo-shell-content.c b/modules/calendar/e-memo-shell-content.c index 0e8d73bbe5..b877efc546 100644 --- a/modules/calendar/e-memo-shell-content.c +++ b/modules/calendar/e-memo-shell-content.c @@ -25,6 +25,7 @@ #include "e-util/e-binding.h" #include "e-util/gconf-bridge.h" +#include "shell/e-shell-utils.h" #include "widgets/menus/gal-view-etable.h" #include "widgets/misc/e-paned.h" @@ -427,9 +428,7 @@ memo_shell_content_constructed (GObject *object) priv->paned = g_object_ref (widget); gtk_widget_show (widget); - e_binding_new ( - object, "orientation", - widget, "orientation"); + e_binding_new (object, "orientation", widget, "orientation"); container = widget; @@ -447,15 +446,14 @@ memo_shell_content_constructed (GObject *object) gtk_paned_pack2 (GTK_PANED (container), widget, FALSE, FALSE); gtk_widget_show (widget); - e_binding_new ( - object, "preview-visible", - widget, "visible"); + e_binding_new (object, "preview-visible", widget, "visible"); container = widget; widget = e_cal_component_preview_new (); e_cal_component_preview_set_default_timezone ( E_CAL_COMPONENT_PREVIEW (widget), timezone); + e_shell_configure_web_view (shell, E_WEB_VIEW (widget)); gtk_container_add (GTK_CONTAINER (container), widget); priv->memo_preview = g_object_ref (widget); gtk_widget_show (widget); diff --git a/modules/calendar/e-memo-shell-view-actions.c b/modules/calendar/e-memo-shell-view-actions.c index 4ffaa519e7..80ebca237d 100644 --- a/modules/calendar/e-memo-shell-view-actions.c +++ b/modules/calendar/e-memo-shell-view-actions.c @@ -682,13 +682,6 @@ static GtkActionEntry memo_entries[] = { NULL, /* XXX Add a tooltip! */ G_CALLBACK (action_memo_open_url_cb) }, - { "memo-save-as", - GTK_STOCK_SAVE_AS, - N_("_Save as iCalendar..."), - NULL, - NULL, /* XXX Add a tooltip! */ - G_CALLBACK (action_memo_save_as_cb) }, - /*** Menus ***/ { "memo-preview-menu", @@ -747,11 +740,7 @@ static EPopupActionEntry memo_popup_entries[] = { { "memo-popup-open-url", NULL, - "memo-open-url" }, - - { "memo-popup-save-as", - NULL, - "memo-save-as" } + "memo-open-url" } }; static GtkToggleActionEntry memo_toggle_entries[] = { @@ -864,11 +853,30 @@ static EPopupActionEntry lockdown_printing_popup_entries[] = { "memo-print" } }; +static GtkActionEntry lockdown_save_to_disk_entries[] = { + + { "memo-save-as", + GTK_STOCK_SAVE_AS, + N_("_Save as iCalendar..."), + NULL, + NULL, /* XXX Add a tooltip! */ + G_CALLBACK (action_memo_save_as_cb) }, +}; + +static EPopupActionEntry lockdown_save_to_disk_popup_entries[] = { + + { "memo-popup-save-as", + NULL, + "memo-save-as" } +}; + void e_memo_shell_view_actions_init (EMemoShellView *memo_shell_view) { EShellView *shell_view; EShellWindow *shell_window; + EMemoShellContent *memo_shell_content; + ECalComponentPreview *memo_preview; GtkActionGroup *action_group; GConfBridge *bridge; GtkAction *action; @@ -878,6 +886,9 @@ e_memo_shell_view_actions_init (EMemoShellView *memo_shell_view) shell_view = E_SHELL_VIEW (memo_shell_view); shell_window = e_shell_view_get_shell_window (shell_view); + memo_shell_content = memo_shell_view->priv->memo_shell_content; + memo_preview = e_memo_shell_content_get_memo_preview (memo_shell_content); + /* Memo Actions */ action_group = ACTION_GROUP (MEMOS); gtk_action_group_add_actions ( @@ -903,11 +914,22 @@ e_memo_shell_view_actions_init (EMemoShellView *memo_shell_view) action_group = ACTION_GROUP (LOCKDOWN_PRINTING); gtk_action_group_add_actions ( action_group, lockdown_printing_entries, - G_N_ELEMENTS (lockdown_printing_entries), memo_shell_view); + G_N_ELEMENTS (lockdown_printing_entries), + memo_shell_view); e_action_group_add_popup_actions ( action_group, lockdown_printing_popup_entries, G_N_ELEMENTS (lockdown_printing_popup_entries)); + /* Lockdown Save-to-Disk Actions */ + action_group = ACTION_GROUP (LOCKDOWN_SAVE_TO_DISK); + gtk_action_group_add_actions ( + action_group, lockdown_save_to_disk_entries, + G_N_ELEMENTS (lockdown_save_to_disk_entries), + memo_shell_view); + e_action_group_add_popup_actions ( + action_group, lockdown_save_to_disk_popup_entries, + G_N_ELEMENTS (lockdown_save_to_disk_popup_entries)); + /* Bind GObject properties to GConf keys. */ bridge = gconf_bridge_get (); @@ -936,6 +958,15 @@ e_memo_shell_view_actions_init (EMemoShellView *memo_shell_view) e_binding_new ( ACTION (MEMO_PREVIEW), "active", ACTION (MEMO_VIEW_VERTICAL), "sensitive"); + + e_web_view_set_open_proxy ( + E_WEB_VIEW (memo_preview), ACTION (MEMO_OPEN)); + + e_web_view_set_print_proxy ( + E_WEB_VIEW (memo_preview), ACTION (MEMO_PRINT)); + + e_web_view_set_save_as_proxy ( + E_WEB_VIEW (memo_preview), ACTION (MEMO_SAVE_AS)); } void diff --git a/modules/calendar/e-task-shell-content.c b/modules/calendar/e-task-shell-content.c index 8dea4b840b..9dfdd91e8e 100644 --- a/modules/calendar/e-task-shell-content.c +++ b/modules/calendar/e-task-shell-content.c @@ -25,6 +25,7 @@ #include "e-util/e-binding.h" #include "e-util/gconf-bridge.h" +#include "shell/e-shell-utils.h" #include "widgets/menus/gal-view-etable.h" #include "widgets/misc/e-paned.h" @@ -425,9 +426,7 @@ task_shell_content_constructed (GObject *object) priv->paned = g_object_ref (widget); gtk_widget_show (widget); - e_binding_new ( - object, "orientation", - widget, "orientation"); + e_binding_new (object, "orientation", widget, "orientation"); container = widget; @@ -445,15 +444,14 @@ task_shell_content_constructed (GObject *object) gtk_paned_pack2 (GTK_PANED (container), widget, FALSE, FALSE); gtk_widget_show (widget); - e_binding_new ( - object, "preview-visible", - widget, "visible"); + e_binding_new (object, "preview-visible", widget, "visible"); container = widget; widget = e_cal_component_preview_new (); e_cal_component_preview_set_default_timezone ( E_CAL_COMPONENT_PREVIEW (widget), timezone); + e_shell_configure_web_view (shell, E_WEB_VIEW (widget)); gtk_container_add (GTK_CONTAINER (container), widget); priv->task_preview = g_object_ref (widget); gtk_widget_show (widget); diff --git a/modules/calendar/e-task-shell-view-actions.c b/modules/calendar/e-task-shell-view-actions.c index 07558bfa90..e5063c1d85 100644 --- a/modules/calendar/e-task-shell-view-actions.c +++ b/modules/calendar/e-task-shell-view-actions.c @@ -829,13 +829,6 @@ static GtkActionEntry task_entries[] = { N_("Delete completed tasks"), G_CALLBACK (action_task_purge_cb) }, - { "task-save-as", - GTK_STOCK_SAVE_AS, - N_("_Save as iCalendar..."), - NULL, - NULL, /* XXX Add a tooltip! */ - G_CALLBACK (action_task_save_as_cb) }, - /*** Menus ***/ { "task-actions-menu", @@ -913,11 +906,7 @@ static EPopupActionEntry task_popup_entries[] = { { "task-popup-open-url", NULL, - "task-open-url" }, - - { "task-popup-save-as", - NULL, - "task-save-as" }, + "task-open-url" } }; static GtkToggleActionEntry task_toggle_entries[] = { @@ -1065,11 +1054,30 @@ static EPopupActionEntry lockdown_printing_popup_entries[] = { "task-print" } }; +static GtkActionEntry lockdown_save_to_disk_entries[] = { + + { "task-save-as", + GTK_STOCK_SAVE_AS, + N_("_Save as iCalendar..."), + NULL, + NULL, /* XXX Add a tooltip! */ + G_CALLBACK (action_task_save_as_cb) } +}; + +static EPopupActionEntry lockdown_save_to_disk_popup_entries[] = { + + { "task-popup-save-as", + NULL, + "task-save-as" }, +}; + void e_task_shell_view_actions_init (ETaskShellView *task_shell_view) { EShellView *shell_view; EShellWindow *shell_window; + ETaskShellContent *task_shell_content; + ECalComponentPreview *task_preview; GtkActionGroup *action_group; GConfBridge *bridge; GtkAction *action; @@ -1079,6 +1087,9 @@ e_task_shell_view_actions_init (ETaskShellView *task_shell_view) shell_view = E_SHELL_VIEW (task_shell_view); shell_window = e_shell_view_get_shell_window (shell_view); + task_shell_content = task_shell_view->priv->task_shell_content; + task_preview = e_task_shell_content_get_task_preview (task_shell_content); + /* Task Actions */ action_group = ACTION_GROUP (TASKS); gtk_action_group_add_actions ( @@ -1104,11 +1115,22 @@ e_task_shell_view_actions_init (ETaskShellView *task_shell_view) action_group = ACTION_GROUP (LOCKDOWN_PRINTING); gtk_action_group_add_actions ( action_group, lockdown_printing_entries, - G_N_ELEMENTS (lockdown_printing_entries), task_shell_view); + G_N_ELEMENTS (lockdown_printing_entries), + task_shell_view); e_action_group_add_popup_actions ( action_group, lockdown_printing_popup_entries, G_N_ELEMENTS (lockdown_printing_popup_entries)); + /* Lockdown Save-to-Disk Actions */ + action_group = ACTION_GROUP (LOCKDOWN_SAVE_TO_DISK); + gtk_action_group_add_actions ( + action_group, lockdown_save_to_disk_entries, + G_N_ELEMENTS (lockdown_save_to_disk_entries), + task_shell_view); + e_action_group_add_popup_actions ( + action_group, lockdown_save_to_disk_popup_entries, + G_N_ELEMENTS (lockdown_save_to_disk_popup_entries)); + /* Bind GObject properties to GConf keys. */ bridge = gconf_bridge_get (); @@ -1137,6 +1159,15 @@ e_task_shell_view_actions_init (ETaskShellView *task_shell_view) e_binding_new ( ACTION (TASK_PREVIEW), "active", ACTION (TASK_VIEW_VERTICAL), "sensitive"); + + e_web_view_set_open_proxy ( + E_WEB_VIEW (task_preview), ACTION (TASK_OPEN)); + + e_web_view_set_print_proxy ( + E_WEB_VIEW (task_preview), ACTION (TASK_PRINT)); + + e_web_view_set_save_as_proxy ( + E_WEB_VIEW (task_preview), ACTION (TASK_SAVE_AS)); } void diff --git a/plugins/mark-all-read/mark-all-read.c b/plugins/mark-all-read/mark-all-read.c index 008cc5a78d..cb36dc01a2 100644 --- a/plugins/mark-all-read/mark-all-read.c +++ b/plugins/mark-all-read/mark-all-read.c @@ -355,7 +355,9 @@ update_actions_cb (EShellView *shell_view, gpointer user_data) EShellSidebar *shell_sidebar; EMFolderTree *folder_tree; gchar *folder_uri; - gboolean has_unread = FALSE, applicable = FALSE; + gboolean has_unread = FALSE; + gboolean applicable = FALSE; + gboolean visible; g_return_if_fail (E_IS_SHELL_VIEW (shell_view)); @@ -368,13 +370,20 @@ update_actions_cb (EShellView *shell_view, gpointer user_data) model = em_folder_tree_model_get_default (); if (model) { - GtkTreeRowReference *reference = em_folder_tree_model_lookup_uri (model, folder_uri); + GtkTreeRowReference *reference; + + reference = em_folder_tree_model_lookup_uri ( + model, folder_uri); if (reference != NULL) { - GtkTreePath *path = gtk_tree_row_reference_get_path (reference); + GtkTreePath *path; GtkTreeIter iter; - gtk_tree_model_get_iter (GTK_TREE_MODEL (model), &iter, path); - has_unread_mail (GTK_TREE_MODEL (model), &iter, TRUE, &has_unread, &applicable); + path = gtk_tree_row_reference_get_path (reference); + gtk_tree_model_get_iter ( + GTK_TREE_MODEL (model), &iter, path); + has_unread_mail ( + GTK_TREE_MODEL (model), &iter, + TRUE, &has_unread, &applicable); gtk_tree_path_free (path); } } @@ -386,7 +395,8 @@ update_actions_cb (EShellView *shell_view, gpointer user_data) action = gtk_action_group_get_action (action_group, entries[0].name); g_return_if_fail (action != NULL); - gtk_action_set_sensitive (action, has_unread && applicable); + visible = has_unread && applicable; + gtk_action_set_visible (action, visible); g_free (folder_uri); g_object_unref (folder_tree); @@ -407,7 +417,9 @@ e_plugin_ui_init (GtkUIManager *ui_manager, action_group, entries, G_N_ELEMENTS (entries), shell_view); - g_signal_connect (shell_view, "update-actions", G_CALLBACK (update_actions_cb), NULL); + g_signal_connect ( + shell_view, "update-actions", + G_CALLBACK (update_actions_cb), NULL); return TRUE; } diff --git a/shell/e-shell-utils.c b/shell/e-shell-utils.c index 570f15bddd..c9c887c97a 100644 --- a/shell/e-shell-utils.c +++ b/shell/e-shell-utils.c @@ -23,9 +23,38 @@ #include <glib/gi18n-lib.h> +#include "e-util/e-binding.h" #include "widgets/misc/e-import-assistant.h" /** + * e_shell_configure_web_view: + * @shell: an #EShell + * @web_view: an #EWebView + * + * Adds shell integration to @web_view. In particular, it configures + * @web_view to honor the printing and save-to-disk lockdown options. + **/ +void +e_shell_configure_web_view (EShell *shell, + EWebView *web_view) +{ + EShellSettings *shell_settings; + + g_return_if_fail (E_IS_SHELL (shell)); + g_return_if_fail (E_IS_WEB_VIEW (web_view)); + + shell_settings = e_shell_get_shell_settings (shell); + + e_binding_new ( + shell_settings, "disable-printing", + web_view, "disable-printing"); + + e_binding_new ( + shell_settings, "disable-save-to-disk", + web_view, "disable-save-to-disk"); +} + +/** * e_shell_run_open_dialog: * @shell: an #EShell * @title: file chooser dialog title diff --git a/shell/e-shell-utils.h b/shell/e-shell-utils.h index 24b44a9622..6e26256155 100644 --- a/shell/e-shell-utils.h +++ b/shell/e-shell-utils.h @@ -29,9 +29,13 @@ #define E_SHELL_UTILS_H #include <shell/e-shell.h> +#include <misc/e-web-view.h> G_BEGIN_DECLS +void e_shell_configure_web_view (EShell *shell, + EWebView *web_view); + GFile * e_shell_run_open_dialog (EShell *shell, const gchar *title, GtkCallback customize_func, diff --git a/ui/evolution-contacts.ui b/ui/evolution-contacts.ui index 6fb31b4b55..2b95d86fc4 100644 --- a/ui/evolution-contacts.ui +++ b/ui/evolution-contacts.ui @@ -65,11 +65,10 @@ <menuitem action='address-book-popup-properties'/> </popup> <popup name='contact-popup'> - <menuitem action='contact-popup-open'/> - <separator/> <menuitem action='contact-new'/> <menuitem action='contact-new-list'/> <separator/> + <menuitem action='contact-popup-open'/> <menuitem action='contact-popup-save-as'/> <menuitem action='contact-popup-forward'/> <menuitem action='contact-popup-send-message'/> diff --git a/widgets/misc/e-popup-action.c b/widgets/misc/e-popup-action.c index e856a1fc24..5f060a45cd 100644 --- a/widgets/misc/e-popup-action.c +++ b/widgets/misc/e-popup-action.c @@ -30,23 +30,110 @@ enum { PROP_0, - PROP_SOURCE + PROP_RELATED_ACTION, + PROP_USE_ACTION_APPEARANCE }; struct _EPopupActionPrivate { - GtkAction *source; + GtkAction *related_action; + gboolean use_action_appearance; + gulong activate_handler_id; + gulong notify_handler_id; }; static gpointer parent_class; static void -popup_action_set_source (EPopupAction *popup_action, - GtkAction *source) +popup_action_notify_cb (GtkAction *action, + GParamSpec *pspec, + GtkActivatable *activatable) { - g_return_if_fail (popup_action->priv->source == NULL); - g_return_if_fail (GTK_IS_ACTION (source)); + GtkActivatableIface *iface; - popup_action->priv->source = g_object_ref (source); + iface = GTK_ACTIVATABLE_GET_IFACE (activatable); + g_return_if_fail (iface->update != NULL); + + iface->update (activatable, action, pspec->name); +} + +static GtkAction * +popup_action_get_related_action (EPopupAction *popup_action) +{ + return popup_action->priv->related_action; +} + +static void +popup_action_set_related_action (EPopupAction *popup_action, + GtkAction *related_action) +{ + GtkActivatable *activatable; + + /* Do not call gtk_activatable_do_set_related_action() because + * it assumes the activatable object is a widget and tries to add + * it to the related actions's proxy list. Instead we'll just do + * the relevant steps manually. */ + + activatable = GTK_ACTIVATABLE (popup_action); + + if (related_action == popup_action->priv->related_action) + return; + + if (related_action != NULL) + g_object_ref (related_action); + + if (popup_action->priv->related_action != NULL) { + g_signal_handler_disconnect ( + popup_action, + popup_action->priv->activate_handler_id); + g_signal_handler_disconnect ( + popup_action->priv->related_action, + popup_action->priv->notify_handler_id); + popup_action->priv->activate_handler_id = 0; + popup_action->priv->notify_handler_id = 0; + g_object_unref (popup_action->priv->related_action); + } + + popup_action->priv->related_action = related_action; + + if (related_action != NULL) { + popup_action->priv->activate_handler_id = + g_signal_connect_swapped ( + popup_action, "activate", + G_CALLBACK (gtk_action_activate), + related_action); + popup_action->priv->notify_handler_id = + g_signal_connect ( + related_action, "notify", + G_CALLBACK (popup_action_notify_cb), + popup_action); + gtk_activatable_sync_action_properties ( + activatable, related_action); + } else + gtk_action_set_visible (GTK_ACTION (popup_action), FALSE); + + g_object_notify (G_OBJECT (popup_action), "related-action"); +} + +static gboolean +popup_action_get_use_action_appearance (EPopupAction *popup_action) +{ + return popup_action->priv->use_action_appearance; +} + +static void +popup_action_set_use_action_appearance (EPopupAction *popup_action, + gboolean use_action_appearance) +{ + GtkActivatable *activatable; + GtkAction *related_action; + + popup_action->priv->use_action_appearance = use_action_appearance; + + g_object_notify (G_OBJECT (popup_action), "use-action-appearance"); + + activatable = GTK_ACTIVATABLE (popup_action); + related_action = popup_action_get_related_action (popup_action); + gtk_activatable_sync_action_properties (activatable, related_action); } static void @@ -56,11 +143,17 @@ popup_action_set_property (GObject *object, GParamSpec *pspec) { switch (property_id) { - case PROP_SOURCE: - popup_action_set_source ( + case PROP_RELATED_ACTION: + popup_action_set_related_action ( E_POPUP_ACTION (object), g_value_get_object (value)); return; + + case PROP_USE_ACTION_APPEARANCE: + popup_action_set_use_action_appearance ( + E_POPUP_ACTION (object), + g_value_get_boolean (value)); + return; } G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec); @@ -73,9 +166,17 @@ popup_action_get_property (GObject *object, GParamSpec *pspec) { switch (property_id) { - case PROP_SOURCE: + case PROP_RELATED_ACTION: g_value_set_object ( - value, e_popup_action_get_source ( + value, + popup_action_get_related_action ( + E_POPUP_ACTION (object))); + return; + + case PROP_USE_ACTION_APPEARANCE: + g_value_set_boolean ( + value, + popup_action_get_use_action_appearance ( E_POPUP_ACTION (object))); return; } @@ -90,9 +191,15 @@ popup_action_dispose (GObject *object) priv = E_POPUP_ACTION_GET_PRIVATE (object); - if (priv->source != NULL) { - g_object_unref (priv->source); - priv->source = NULL; + if (priv->related_action != NULL) { + g_signal_handler_disconnect ( + object, + priv->activate_handler_id); + g_signal_handler_disconnect ( + priv->related_action, + priv->notify_handler_id); + g_object_unref (priv->related_action); + priv->related_action = NULL; } /* Chain up to parent's dispose() method. */ @@ -100,56 +207,97 @@ popup_action_dispose (GObject *object) } static void -popup_action_constructed (GObject *object) +popup_action_update (GtkActivatable *activatable, + GtkAction *action, + const gchar *property_name) { - EPopupActionPrivate *priv; - GObject *source; - gchar *icon_name; - gchar *label; - gchar *stock_id; - gchar *tooltip; + GObjectClass *class; + GParamSpec *pspec; + GValue *value; - priv = E_POPUP_ACTION_GET_PRIVATE (object); + /* Ignore "action-group" changes" */ + if (strcmp (property_name, "action-group") == 0) + return; - source = G_OBJECT (priv->source); + /* Ignore "visible" changes. */ + if (strcmp (property_name, "visible") == 0) + return; - g_object_get ( - object, "icon-name", &icon_name, "label", &label, - "stock-id", &stock_id, "tooltip", &tooltip, NULL); + value = g_slice_new0 (GValue); + class = G_OBJECT_GET_CLASS (action); + pspec = g_object_class_find_property (class, property_name); + g_value_init (value, pspec->value_type); - if (label == NULL) - e_binding_new (source, "label", object, "label"); + g_object_get_property (G_OBJECT (action), property_name, value); - if (tooltip == NULL) - e_binding_new (source, "tooltip", object, "tooltip"); + if (strcmp (property_name, "sensitive") == 0) + property_name = "visible"; + else if (!gtk_activatable_get_use_action_appearance (activatable)) + goto exit; - if (icon_name == NULL && stock_id == NULL) { - g_free (icon_name); - g_free (stock_id); + g_object_set_property (G_OBJECT (activatable), property_name, value); - g_object_get ( - source, "icon-name", &icon_name, - "stock-id", &stock_id, NULL); +exit: + g_value_unset (value); + g_slice_free (GValue, value); +} - if (icon_name == NULL) { - e_binding_new ( - source, "icon-name", object, "icon-name"); - e_binding_new ( - source, "stock-id", object, "stock-id"); - } else { - e_binding_new ( - source, "stock-id", object, "stock-id"); - e_binding_new ( - source, "icon-name", object, "icon-name"); - } - } +static void +popup_action_sync_action_properties (GtkActivatable *activatable, + GtkAction *action) +{ + if (action == NULL) + return; + + /* XXX GTK+ 2.18 is still missing accessor functions for + * "hide-if-empty" and "visible-overflown" properties. + * These are rarely used so we'll skip them for now. */ + + /* A popup action is never shown as insensitive. */ + gtk_action_set_sensitive (GTK_ACTION (activatable), TRUE); + + gtk_action_set_visible ( + GTK_ACTION (activatable), + gtk_action_get_sensitive (action)); + + gtk_action_set_visible_horizontal ( + GTK_ACTION (activatable), + gtk_action_get_visible_horizontal (action)); + + gtk_action_set_visible_vertical ( + GTK_ACTION (activatable), + gtk_action_get_visible_vertical (action)); + + gtk_action_set_is_important ( + GTK_ACTION (activatable), + gtk_action_get_is_important (action)); - e_binding_new (source, "sensitive", object, "visible"); + if (!gtk_activatable_get_use_action_appearance (activatable)) + return; - g_free (icon_name); - g_free (label); - g_free (stock_id); - g_free (tooltip); + gtk_action_set_label ( + GTK_ACTION (activatable), + gtk_action_get_label (action)); + + gtk_action_set_short_label ( + GTK_ACTION (activatable), + gtk_action_get_short_label (action)); + + gtk_action_set_tooltip ( + GTK_ACTION (activatable), + gtk_action_get_tooltip (action)); + + gtk_action_set_stock_id ( + GTK_ACTION (activatable), + gtk_action_get_stock_id (action)); + + gtk_action_set_gicon ( + GTK_ACTION (activatable), + gtk_action_get_gicon (action)); + + gtk_action_set_icon_name ( + GTK_ACTION (activatable), + gtk_action_get_icon_name (action)); } static void @@ -165,22 +313,32 @@ popup_action_class_init (EPopupActionClass *class) object_class->get_property = popup_action_get_property; object_class->dispose = popup_action_dispose; - g_object_class_install_property ( + g_object_class_override_property ( + object_class, + PROP_RELATED_ACTION, + "related-action"); + + g_object_class_override_property ( object_class, - PROP_SOURCE, - g_param_spec_object ( - "source", - _("Source Action"), - _("The source action to proxy"), - GTK_TYPE_ACTION, - G_PARAM_READWRITE | - G_PARAM_CONSTRUCT_ONLY)); + PROP_USE_ACTION_APPEARANCE, + "use-action-appearance"); +} + +static void +popup_action_iface_init (GtkActivatableIface *iface) +{ + iface->update = popup_action_update; + iface->sync_action_properties = popup_action_sync_action_properties; } static void popup_action_init (EPopupAction *popup_action) { popup_action->priv = E_POPUP_ACTION_GET_PRIVATE (popup_action); + popup_action->priv->use_action_appearance = TRUE; + + /* Remain invisible until we have a related action. */ + gtk_action_set_visible (GTK_ACTION (popup_action), FALSE); } GType @@ -202,43 +360,28 @@ e_popup_action_get_type (void) NULL /* value_table */ }; + static const GInterfaceInfo iface_info = { + (GInterfaceInitFunc) popup_action_iface_init, + (GInterfaceFinalizeFunc) NULL, + NULL /* interface_data */ + }; + type = g_type_register_static ( GTK_TYPE_ACTION, "EPopupAction", &type_info, 0); + + g_type_add_interface_static ( + type, GTK_TYPE_ACTIVATABLE, &iface_info); } return type; } EPopupAction * -e_popup_action_new (const gchar *name, - const gchar *label, - GtkAction *source) +e_popup_action_new (const gchar *name) { - EPopupAction *popup_action; - g_return_val_if_fail (name != NULL, NULL); - g_return_val_if_fail (GTK_IS_ACTION (source), NULL); - popup_action = g_object_new ( - E_TYPE_POPUP_ACTION, "name", name, - "label", label, "source", source, NULL); - - /* XXX This is a hack to work around the fact that GtkAction's - * "label" and "tooltip" properties are not constructor - * properties, even though they're supplied upfront. - * - * See: http://bugzilla.gnome.org/show_bug.cgi?id=568334 */ - popup_action_constructed (G_OBJECT (popup_action)); - - return popup_action; -} - -GtkAction * -e_popup_action_get_source (EPopupAction *popup_action) -{ - g_return_val_if_fail (E_IS_POPUP_ACTION (popup_action), NULL); - - return popup_action->priv->source; + return g_object_new (E_TYPE_POPUP_ACTION, "name", name, NULL); } void @@ -252,30 +395,31 @@ e_action_group_add_popup_actions (GtkActionGroup *action_group, for (ii = 0; ii < n_entries; ii++) { EPopupAction *popup_action; - GtkAction *source; + GtkAction *related_action; const gchar *label; label = gtk_action_group_translate_string ( action_group, entries[ii].label); - source = gtk_action_group_get_action ( - action_group, entries[ii].source); + related_action = gtk_action_group_get_action ( + action_group, entries[ii].related); - if (source == NULL) { + if (related_action == NULL) { g_warning ( - "Source action '%s' not found in " - "action group '%s'", entries[ii].source, + "Related action '%s' not found in " + "action group '%s'", entries[ii].related, gtk_action_group_get_name (action_group)); continue; } - popup_action = e_popup_action_new ( - entries[ii].name, label, source); + popup_action = e_popup_action_new (entries[ii].name); + + gtk_activatable_set_related_action ( + GTK_ACTIVATABLE (popup_action), related_action); - g_signal_connect_swapped ( - popup_action, "activate", - G_CALLBACK (gtk_action_activate), - popup_action->priv->source); + if (label != NULL && *label != '\0') + gtk_action_set_label ( + GTK_ACTION (popup_action), label); gtk_action_group_add_action ( action_group, GTK_ACTION (popup_action)); diff --git a/widgets/misc/e-popup-action.h b/widgets/misc/e-popup-action.h index d19971f303..02469375d5 100644 --- a/widgets/misc/e-popup-action.h +++ b/widgets/misc/e-popup-action.h @@ -28,9 +28,9 @@ * To use: * * Create an array of EPopupActionEntry structs. Add the main menu actions - * that serve as "sources" for the popup actions to an action group first. - * Then pass the same action group and the EPopupActionEntry array to - * e_action_group_add_popup_actions() to add popup actions. + * that serve as related actions for the popup actions to an action group + * first. Then pass the same action group and the EPopupActionEntry array + * to e_action_group_add_popup_actions() to add popup actions. */ #ifndef E_POPUP_ACTION_H @@ -75,15 +75,12 @@ struct _EPopupActionClass { struct _EPopupActionEntry { const gchar *name; - const gchar *label; /* optional: overrides the source action */ - const gchar *source; /* name of the source action */ + const gchar *label; /* optional: overrides the related action */ + const gchar *related; /* name of the related action */ }; GType e_popup_action_get_type (void); -EPopupAction * e_popup_action_new (const gchar *name, - const gchar *label, - GtkAction *source); -GtkAction * e_popup_action_get_source (EPopupAction *popup_action); +EPopupAction * e_popup_action_new (const gchar *name); void e_action_group_add_popup_actions (GtkActionGroup *action_group, diff --git a/widgets/misc/e-web-view.c b/widgets/misc/e-web-view.c index 3a3e62b13b..5d56735e5e 100644 --- a/widgets/misc/e-web-view.c +++ b/widgets/misc/e-web-view.c @@ -29,8 +29,11 @@ #include <camel/camel-url.h> #include "e-util/e-util.h" +#include "e-util/e-binding.h" #include "e-util/e-plugin-ui.h" +#include "e-popup-action.h" + #define E_WEB_VIEW_GET_PRIVATE(obj) \ (G_TYPE_INSTANCE_GET_PRIVATE \ ((obj), E_TYPE_WEB_VIEW, EWebViewPrivate)) @@ -41,6 +44,14 @@ struct _EWebViewPrivate { GList *requests; GtkUIManager *ui_manager; gchar *selected_uri; + + GtkAction *open_proxy; + GtkAction *print_proxy; + GtkAction *save_as_proxy; + + /* Lockdown Options */ + guint disable_printing : 1; + guint disable_save_to_disk : 1; }; struct _EWebViewRequest { @@ -56,6 +67,11 @@ enum { PROP_0, PROP_ANIMATE, PROP_CARET_MODE, + PROP_DISABLE_PRINTING, + PROP_DISABLE_SAVE_TO_DISK, + PROP_OPEN_PROXY, + PROP_PRINT_PROXY, + PROP_SAVE_AS_PROXY, PROP_SELECTED_URI }; @@ -73,15 +89,22 @@ static guint signals[LAST_SIGNAL]; static const gchar *ui = "<ui>" " <popup name='context'>" +" <menuitem action='clipboard-copy'/>" +" <separator/>" " <placeholder name='custom-actions-1'>" +" <menuitem action='open'/>" +" <menuitem action='save-as'/>" " <menuitem action='http-open'/>" " <menuitem action='send-message'/>" +" <menuitem action='print'/>" " </placeholder>" " <placeholder name='custom-actions-2'>" " <menuitem action='uri-copy'/>" " <menuitem action='mailto-copy'/>" " </placeholder>" " <placeholder name='custom-actions-3'/>" +" <separator/>" +" <menuitem action='select-all'/>" " </popup>" "</ui>"; @@ -217,6 +240,13 @@ web_view_request_read_cb (GFile *file, } static void +action_clipboard_copy_cb (GtkAction *action, + EWebView *web_view) +{ + e_web_view_clipboard_copy (web_view); +} + +static void action_http_open_cb (GtkAction *action, EWebView *web_view) { @@ -266,6 +296,13 @@ action_mailto_copy_cb (GtkAction *action, } static void +action_select_all_cb (GtkAction *action, + EWebView *web_view) +{ + e_web_view_select_all (web_view); +} + +static void action_send_message_cb (GtkAction *action, EWebView *web_view) { @@ -333,6 +370,26 @@ static GtkActionEntry mailto_entries[] = { G_CALLBACK (action_send_message_cb) } }; +static GtkActionEntry selection_entries[] = { + + { "clipboard-copy", + GTK_STOCK_COPY, + NULL, + NULL, + N_("Copy the selection to the clipboard"), + G_CALLBACK (action_clipboard_copy_cb) }, +}; + +static GtkActionEntry standard_entries[] = { + + { "select-all", + GTK_STOCK_SELECT_ALL, + NULL, + NULL, + N_("Select all text and images"), + G_CALLBACK (action_select_all_cb) } +}; + static gboolean web_view_button_press_event_cb (EWebView *web_view, GdkEventButton *event, @@ -420,6 +477,36 @@ web_view_set_property (GObject *object, g_value_get_boolean (value)); return; + case PROP_DISABLE_PRINTING: + e_web_view_set_disable_printing ( + E_WEB_VIEW (object), + g_value_get_boolean (value)); + return; + + case PROP_DISABLE_SAVE_TO_DISK: + e_web_view_set_disable_save_to_disk ( + E_WEB_VIEW (object), + g_value_get_boolean (value)); + return; + + case PROP_OPEN_PROXY: + e_web_view_set_open_proxy ( + E_WEB_VIEW (object), + g_value_get_object (value)); + return; + + case PROP_PRINT_PROXY: + e_web_view_set_print_proxy ( + E_WEB_VIEW (object), + g_value_get_object (value)); + return; + + case PROP_SAVE_AS_PROXY: + e_web_view_set_save_as_proxy ( + E_WEB_VIEW (object), + g_value_get_object (value)); + return; + case PROP_SELECTED_URI: e_web_view_set_selected_uri ( E_WEB_VIEW (object), @@ -449,6 +536,36 @@ web_view_get_property (GObject *object, E_WEB_VIEW (object))); return; + case PROP_DISABLE_PRINTING: + g_value_set_boolean ( + value, e_web_view_get_disable_printing ( + E_WEB_VIEW (object))); + return; + + case PROP_DISABLE_SAVE_TO_DISK: + g_value_set_boolean ( + value, e_web_view_get_disable_save_to_disk ( + E_WEB_VIEW (object))); + return; + + case PROP_OPEN_PROXY: + g_value_set_object ( + value, e_web_view_get_open_proxy ( + E_WEB_VIEW (object))); + return; + + case PROP_PRINT_PROXY: + g_value_set_object ( + value, e_web_view_get_print_proxy ( + E_WEB_VIEW (object))); + return; + + case PROP_SAVE_AS_PROXY: + g_value_set_object ( + value, e_web_view_get_save_as_proxy ( + E_WEB_VIEW (object))); + return; + case PROP_SELECTED_URI: g_value_set_string ( value, e_web_view_get_selected_uri ( @@ -471,6 +588,21 @@ web_view_dispose (GObject *object) priv->ui_manager = NULL; } + if (priv->open_proxy != NULL) { + g_object_unref (priv->open_proxy); + priv->open_proxy = NULL; + } + + if (priv->print_proxy != NULL) { + g_object_unref (priv->print_proxy); + priv->print_proxy = NULL; + } + + if (priv->save_as_proxy != NULL) { + g_object_unref (priv->save_as_proxy); + priv->save_as_proxy = NULL; + } + /* Chain up to parent's dispose() method. */ G_OBJECT_CLASS (parent_class)->dispose (object); } @@ -639,8 +771,8 @@ web_view_popup_event (EWebView *web_view, GdkEventButton *event, const gchar *uri) { - if (uri == NULL) - return FALSE; + if (uri != NULL) + e_web_view_unselect_all (web_view); e_web_view_set_selected_uri (web_view, uri); e_web_view_show_popup_menu (web_view, event, NULL, NULL); @@ -661,40 +793,68 @@ web_view_stop_loading (EWebView *web_view) static void web_view_update_actions (EWebView *web_view) { - CamelURL *curl; GtkActionGroup *action_group; - gboolean scheme_is_http; - gboolean scheme_is_mailto; - gboolean uri_is_valid; + gboolean have_selection; + gboolean scheme_is_http = FALSE; + gboolean scheme_is_mailto = FALSE; + gboolean uri_is_valid = FALSE; gboolean visible; + const gchar *group_name; const gchar *uri; uri = e_web_view_get_selected_uri (web_view); - g_return_if_fail (uri != NULL); + have_selection = e_web_view_is_selection_active (web_view); /* Parse the URI early so we know if the actions will work. */ - curl = camel_url_new (uri, NULL); - uri_is_valid = (curl != NULL); - camel_url_free (curl); + if (uri != NULL) { + CamelURL *curl; + + curl = camel_url_new (uri, NULL); + uri_is_valid = (curl != NULL); + camel_url_free (curl); - scheme_is_http = - (g_ascii_strncasecmp (uri, "http:", 5) == 0) || - (g_ascii_strncasecmp (uri, "https:", 6) == 0); + scheme_is_http = + (g_ascii_strncasecmp (uri, "http:", 5) == 0) || + (g_ascii_strncasecmp (uri, "https:", 6) == 0); - scheme_is_mailto = - (g_ascii_strncasecmp (uri, "mailto:", 7) == 0); + scheme_is_mailto = + (g_ascii_strncasecmp (uri, "mailto:", 7) == 0); + } /* Allow copying the URI even if it's malformed. */ - visible = !scheme_is_mailto; - action_group = e_web_view_get_action_group (web_view, "uri"); + group_name = "uri"; + visible = (uri != NULL) && !scheme_is_mailto; + action_group = e_web_view_get_action_group (web_view, group_name); gtk_action_group_set_visible (action_group, visible); + group_name = "http"; visible = uri_is_valid && scheme_is_http; - action_group = e_web_view_get_action_group (web_view, "http"); + action_group = e_web_view_get_action_group (web_view, group_name); gtk_action_group_set_visible (action_group, visible); + group_name = "mailto"; visible = uri_is_valid && scheme_is_mailto; - action_group = e_web_view_get_action_group (web_view, "mailto"); + action_group = e_web_view_get_action_group (web_view, group_name); + gtk_action_group_set_visible (action_group, visible); + + group_name = "selection"; + visible = have_selection; + action_group = e_web_view_get_action_group (web_view, group_name); + gtk_action_group_set_visible (action_group, visible); + + group_name = "standard"; + visible = (uri == NULL); + action_group = e_web_view_get_action_group (web_view, group_name); + gtk_action_group_set_visible (action_group, visible); + + group_name = "lockdown-printing"; + visible = (uri == NULL) && !web_view->priv->disable_printing; + action_group = e_web_view_get_action_group (web_view, group_name); + gtk_action_group_set_visible (action_group, visible); + + group_name = "lockdown-save-to-disk"; + visible = (uri == NULL) && !web_view->priv->disable_save_to_disk; + action_group = e_web_view_get_action_group (web_view, group_name); gtk_action_group_set_visible (action_group, visible); } @@ -751,6 +911,56 @@ web_view_class_init (EWebViewClass *class) g_object_class_install_property ( object_class, + PROP_DISABLE_PRINTING, + g_param_spec_boolean ( + "disable-printing", + "Disable Printing", + NULL, + FALSE, + G_PARAM_READWRITE)); + + g_object_class_install_property ( + object_class, + PROP_DISABLE_SAVE_TO_DISK, + g_param_spec_boolean ( + "disable-save-to-disk", + "Disable Save-to-Disk", + NULL, + FALSE, + G_PARAM_READWRITE)); + + g_object_class_install_property ( + object_class, + PROP_OPEN_PROXY, + g_param_spec_object ( + "open-proxy", + "Open Proxy", + NULL, + GTK_TYPE_ACTION, + G_PARAM_READWRITE)); + + g_object_class_install_property ( + object_class, + PROP_PRINT_PROXY, + g_param_spec_object ( + "print-proxy", + "Print Proxy", + NULL, + GTK_TYPE_ACTION, + G_PARAM_READWRITE)); + + g_object_class_install_property ( + object_class, + PROP_SAVE_AS_PROXY, + g_param_spec_object ( + "save-as-proxy", + "Save As Proxy", + NULL, + GTK_TYPE_ACTION, + G_PARAM_READWRITE)); + + g_object_class_install_property ( + object_class, PROP_SELECTED_URI, g_param_spec_string ( "selected-uri", @@ -804,6 +1014,7 @@ web_view_init (EWebView *web_view) { GtkUIManager *ui_manager; GtkActionGroup *action_group; + EPopupAction *popup_action; const gchar *domain = GETTEXT_PACKAGE; const gchar *id; GError *error = NULL; @@ -844,6 +1055,60 @@ web_view_init (EWebView *web_view) action_group, mailto_entries, G_N_ELEMENTS (mailto_entries), web_view); + action_group = gtk_action_group_new ("selection"); + gtk_action_group_set_translation_domain (action_group, domain); + gtk_ui_manager_insert_action_group (ui_manager, action_group, 0); + g_object_unref (action_group); + + gtk_action_group_add_actions ( + action_group, selection_entries, + G_N_ELEMENTS (selection_entries), web_view); + + action_group = gtk_action_group_new ("standard"); + gtk_action_group_set_translation_domain (action_group, domain); + gtk_ui_manager_insert_action_group (ui_manager, action_group, 0); + g_object_unref (action_group); + + gtk_action_group_add_actions ( + action_group, standard_entries, + G_N_ELEMENTS (standard_entries), web_view); + + popup_action = e_popup_action_new ("open"); + gtk_action_group_add_action (action_group, GTK_ACTION (popup_action)); + g_object_unref (popup_action); + + e_mutual_binding_new ( + web_view, "open-proxy", + popup_action, "related-action"); + + /* Support lockdown. */ + + action_group = gtk_action_group_new ("lockdown-printing"); + gtk_action_group_set_translation_domain (action_group, domain); + gtk_ui_manager_insert_action_group (ui_manager, action_group, 0); + g_object_unref (action_group); + + popup_action = e_popup_action_new ("print"); + gtk_action_group_add_action (action_group, GTK_ACTION (popup_action)); + g_object_unref (popup_action); + + e_mutual_binding_new ( + web_view, "print-proxy", + popup_action, "related-action"); + + action_group = gtk_action_group_new ("lockdown-save-to-disk"); + gtk_action_group_set_translation_domain (action_group, domain); + gtk_ui_manager_insert_action_group (ui_manager, action_group, 0); + g_object_unref (action_group); + + popup_action = e_popup_action_new ("save-as"); + gtk_action_group_add_action (action_group, GTK_ACTION (popup_action)); + g_object_unref (popup_action); + + e_mutual_binding_new ( + web_view, "save-as-proxy", + popup_action, "related-action"); + /* Because we are loading from a hard-coded string, there is * no chance of I/O errors. Failure here implies a malformed * UI definition. Full stop. */ @@ -960,6 +1225,44 @@ e_web_view_set_caret_mode (EWebView *web_view, g_object_notify (G_OBJECT (web_view), "caret-mode"); } +gboolean +e_web_view_get_disable_printing (EWebView *web_view) +{ + g_return_val_if_fail (E_IS_WEB_VIEW (web_view), FALSE); + + return web_view->priv->disable_printing; +} + +void +e_web_view_set_disable_printing (EWebView *web_view, + gboolean disable_printing) +{ + g_return_if_fail (E_IS_WEB_VIEW (web_view)); + + web_view->priv->disable_printing = disable_printing; + + g_object_notify (G_OBJECT (web_view), "disable-printing"); +} + +gboolean +e_web_view_get_disable_save_to_disk (EWebView *web_view) +{ + g_return_val_if_fail (E_IS_WEB_VIEW (web_view), FALSE); + + return web_view->priv->disable_save_to_disk; +} + +void +e_web_view_set_disable_save_to_disk (EWebView *web_view, + gboolean disable_save_to_disk) +{ + g_return_if_fail (E_IS_WEB_VIEW (web_view)); + + web_view->priv->disable_save_to_disk = disable_save_to_disk; + + g_object_notify (G_OBJECT (web_view), "disable-save-to-disk"); +} + const gchar * e_web_view_get_selected_uri (EWebView *web_view) { @@ -981,6 +1284,87 @@ e_web_view_set_selected_uri (EWebView *web_view, } GtkAction * +e_web_view_get_open_proxy (EWebView *web_view) +{ + g_return_val_if_fail (E_IS_WEB_VIEW (web_view), FALSE); + + return web_view->priv->open_proxy; +} + +void +e_web_view_set_open_proxy (EWebView *web_view, + GtkAction *open_proxy) +{ + g_return_if_fail (E_IS_WEB_VIEW (web_view)); + + if (open_proxy != NULL) { + g_return_if_fail (GTK_IS_ACTION (open_proxy)); + g_object_ref (open_proxy); + } + + if (web_view->priv->open_proxy != NULL) + g_object_unref (web_view->priv->open_proxy); + + web_view->priv->open_proxy = open_proxy; + + g_object_notify (G_OBJECT (web_view), "open-proxy"); +} + +GtkAction * +e_web_view_get_print_proxy (EWebView *web_view) +{ + g_return_val_if_fail (E_IS_WEB_VIEW (web_view), FALSE); + + return web_view->priv->print_proxy; +} + +void +e_web_view_set_print_proxy (EWebView *web_view, + GtkAction *print_proxy) +{ + g_return_if_fail (E_IS_WEB_VIEW (web_view)); + + if (print_proxy != NULL) { + g_return_if_fail (GTK_IS_ACTION (print_proxy)); + g_object_ref (print_proxy); + } + + if (web_view->priv->print_proxy != NULL) + g_object_unref (web_view->priv->print_proxy); + + web_view->priv->print_proxy = print_proxy; + + g_object_notify (G_OBJECT (web_view), "print-proxy"); +} + +GtkAction * +e_web_view_get_save_as_proxy (EWebView *web_view) +{ + g_return_val_if_fail (E_IS_WEB_VIEW (web_view), FALSE); + + return web_view->priv->save_as_proxy; +} + +void +e_web_view_set_save_as_proxy (EWebView *web_view, + GtkAction *save_as_proxy) +{ + g_return_if_fail (E_IS_WEB_VIEW (web_view)); + + if (save_as_proxy != NULL) { + g_return_if_fail (GTK_IS_ACTION (save_as_proxy)); + g_object_ref (save_as_proxy); + } + + if (web_view->priv->save_as_proxy != NULL) + g_object_unref (web_view->priv->save_as_proxy); + + web_view->priv->save_as_proxy = save_as_proxy; + + g_object_notify (G_OBJECT (web_view), "save-as-proxy"); +} + +GtkAction * e_web_view_get_action (EWebView *web_view, const gchar *action_name) { @@ -1026,6 +1410,22 @@ e_web_view_extract_uri (EWebView *web_view, return class->extract_uri (web_view, event, frame); } +void +e_web_view_clipboard_copy (EWebView *web_view) +{ + g_return_if_fail (E_IS_WEB_VIEW (web_view)); + + gtk_html_command (GTK_HTML (web_view), "copy"); +} + +gboolean +e_web_view_is_selection_active (EWebView *web_view) +{ + g_return_val_if_fail (E_IS_WEB_VIEW (web_view), FALSE); + + return gtk_html_command (GTK_HTML (web_view), "is-selection-active"); +} + gboolean e_web_view_scroll_forward (EWebView *web_view) { @@ -1042,6 +1442,22 @@ e_web_view_scroll_backward (EWebView *web_view) return gtk_html_command (GTK_HTML (web_view), "scroll-backward"); } +void +e_web_view_select_all (EWebView *web_view) +{ + g_return_if_fail (E_IS_WEB_VIEW (web_view)); + + gtk_html_command (GTK_HTML (web_view), "select-all"); +} + +void +e_web_view_unselect_all (EWebView *web_view) +{ + g_return_if_fail (E_IS_WEB_VIEW (web_view)); + + gtk_html_command (GTK_HTML (web_view), "unselect-all"); +} + GtkUIManager * e_web_view_get_ui_manager (EWebView *web_view) { diff --git a/widgets/misc/e-web-view.h b/widgets/misc/e-web-view.h index 3bce2b4887..37c289a877 100644 --- a/widgets/misc/e-web-view.h +++ b/widgets/misc/e-web-view.h @@ -91,9 +91,26 @@ void e_web_view_set_animate (EWebView *web_view, gboolean e_web_view_get_caret_mode (EWebView *web_view); void e_web_view_set_caret_mode (EWebView *web_view, gboolean caret_mode); +gboolean e_web_view_get_disable_printing (EWebView *web_view); +void e_web_view_set_disable_printing (EWebView *web_view, + gboolean disable_printing); +gboolean e_web_view_get_disable_save_to_disk + (EWebView *web_view); +void e_web_view_set_disable_save_to_disk + (EWebView *web_view, + gboolean disable_save_to_disk); const gchar * e_web_view_get_selected_uri (EWebView *web_view); void e_web_view_set_selected_uri (EWebView *web_view, const gchar *selected_uri); +GtkAction * e_web_view_get_open_proxy (EWebView *web_view); +void e_web_view_set_open_proxy (EWebView *web_view, + GtkAction *open_proxy); +GtkAction * e_web_view_get_print_proxy (EWebView *web_view); +void e_web_view_set_print_proxy (EWebView *web_view, + GtkAction *print_proxy); +GtkAction * e_web_view_get_save_as_proxy (EWebView *web_view); +void e_web_view_set_save_as_proxy (EWebView *web_view, + GtkAction *save_as_proxy); GtkAction * e_web_view_get_action (EWebView *web_view, const gchar *action_name); GtkActionGroup *e_web_view_get_action_group (EWebView *web_view, @@ -101,8 +118,12 @@ GtkActionGroup *e_web_view_get_action_group (EWebView *web_view, gchar * e_web_view_extract_uri (EWebView *web_view, GdkEventButton *event, GtkHTML *frame); +void e_web_view_clipboard_copy (EWebView *web_view); +gboolean e_web_view_is_selection_active (EWebView *web_view); gboolean e_web_view_scroll_forward (EWebView *web_view); gboolean e_web_view_scroll_backward (EWebView *web_view); +void e_web_view_select_all (EWebView *web_view); +void e_web_view_unselect_all (EWebView *web_view); GtkUIManager * e_web_view_get_ui_manager (EWebView *web_view); GtkWidget * e_web_view_get_popup_menu (EWebView *web_view); void e_web_view_show_popup_menu (EWebView *web_view, |