diff options
-rw-r--r-- | ChangeLog | 33 | ||||
-rw-r--r-- | lib/ephy-gui.c | 2 | ||||
-rw-r--r-- | src/ephy-link-action.c | 121 | ||||
-rw-r--r-- | src/ephy-navigation-action.c | 52 | ||||
-rwxr-xr-x | src/ephy-toolbar.c | 6 |
5 files changed, 199 insertions, 15 deletions
@@ -1,3 +1,36 @@ +2005-10-16 Philip Langdale <philipl@mail.utexas.edu> + + * src/ephy-link-action.c: + (proxy_button_release_event_cb), (get_event_widget), + (ephy_link_action_connect_proxy), (ephy_link_action_disconnect_proxy), + (ephy_link_action_class_init), (ephy_link_action_get_type): + Exten the EphyLinkAction to attach a mouse-release-event handler + which turns around and calls gtk_action_activate in response to a + middle-click even on the proxy. This allows us to fully encapsulate + the extra work needed to catch middle clicks. + The GoHome action will automatically start working correctly now + that it is getting activated in this case. + + * src/ephy-navigation-action.c: + (activate_by_history_index), (activate_back_or_forward_menu_item_cb), + (ephy_navigation_action_activate), (ephy_navigation_action_class_init): + Fully enscapsulate 'activate' handling inside the action. This is more + consistent because the menus are already handled internally. Also + add support for middle-click on back/forward/up. + + * src/ephy-toolbar.c: + (ephy_toolbar_set_window): Don't attach 'activate' signal handlers + to the navigate actions because activation is now handled internally + to the action. + + I intend to make a followup change that removes the separate actions + for GoUp/Back/Forward in the menu and replace them with the main + actions already used in the toolbar. This means the menu items will + get middle-click support for free. + + * lib/ephy-gui.c: (ephy_gui_is_middle_click): + Only consider an unmodified middle-click to be a middle-click. + 2005-10-16 Christian Persch <chpe@cvs.gnome.org> * embed/ephy-favicon-cache.c: (ephy_favicon_cache_get): diff --git a/lib/ephy-gui.c b/lib/ephy-gui.c index 2e591c5e7..28dee83f3 100644 --- a/lib/ephy-gui.c +++ b/lib/ephy-gui.c @@ -434,7 +434,7 @@ ephy_gui_is_middle_click (void) /* middle-click or control-click */ if ((button == 1 && ((state & modifiers) == GDK_CONTROL_MASK)) || - (button == 2)) + (button == 2 && ((state & modifiers) == 0))) { is_middle_click = TRUE; } diff --git a/src/ephy-link-action.c b/src/ephy-link-action.c index 18af84759..5eca8a65b 100644 --- a/src/ephy-link-action.c +++ b/src/ephy-link-action.c @@ -1,5 +1,6 @@ /* * Copyright (C) 2004 Christian Persch + * Copyright (C) 2005 Philip Langdale * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -23,6 +24,124 @@ #include "ephy-link-action.h" #include "ephy-link.h" +#include "ephy-debug.h" +#include "ephy-gui.h" + +#include <gtk/gtkbutton.h> +#include <gtk/gtkmenuitem.h> +#include <gtk/gtkmenutoolbutton.h> + +static GObjectClass *parent_class = NULL; + +static gboolean +proxy_button_release_event_cb (GtkWidget *widget, + GdkEventButton *event, + GtkAction *action) +{ + /** + * We do not use ephy_gui_is_middle_click() here because + * that also catches ctrl + left_click which already + * triggers an activate event for all proxies. + */ + if (event->button == 2) + { + gtk_action_activate(action); + } + + return FALSE; +} + +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)) + { + /** + * The menu tool button's button is the first child + * of the child hbox. + */ + GtkContainer *container = + GTK_CONTAINER (gtk_bin_get_child (GTK_BIN (proxy))); + widget = GTK_WIDGET (gtk_container_get_children (container)->data); + } + 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 void +ephy_link_action_connect_proxy (GtkAction *action, GtkWidget *proxy) +{ + GtkWidget *widget; + + LOG ("Connect link action proxy"); + + widget = get_event_widget(proxy); + if (widget) + { + g_signal_connect (widget, "button-release-event", + G_CALLBACK (proxy_button_release_event_cb), + action); + } + + GTK_ACTION_CLASS (parent_class)->connect_proxy (action, proxy); +} + +static void +ephy_link_action_disconnect_proxy (GtkAction *action, GtkWidget *proxy) +{ + GtkWidget *widget; + + LOG ("Disconnect link action proxy"); + + widget = get_event_widget(proxy); + if (widget) + { + g_signal_handlers_disconnect_by_func (widget, + G_CALLBACK (proxy_button_release_event_cb), + action); + } + + GTK_ACTION_CLASS (parent_class)->disconnect_proxy (action, proxy); +} + +static void +ephy_link_action_class_init (EphyLinkActionClass *class) +{ + GtkActionClass *action_class = GTK_ACTION_CLASS (class); + + parent_class = g_type_class_peek_parent (class); + + action_class->connect_proxy = ephy_link_action_connect_proxy; + action_class->disconnect_proxy = ephy_link_action_disconnect_proxy; +} + + GType ephy_link_action_get_type (void) { @@ -35,7 +154,7 @@ ephy_link_action_get_type (void) sizeof (EphyLinkActionClass), NULL, /* base_init */ NULL, /* base_finalize */ - NULL, /* class_init */ + (GClassInitFunc) ephy_link_action_class_init, NULL, NULL, /* class_data */ sizeof (EphyLinkAction), diff --git a/src/ephy-navigation-action.c b/src/ephy-navigation-action.c index 42c39d47b..08a93a3b9 100644 --- a/src/ephy-navigation-action.c +++ b/src/ephy-navigation-action.c @@ -138,18 +138,14 @@ new_history_menu_item (const char *origtext, } static void -activate_back_or_forward_menu_item_cb (GtkWidget *menuitem, - EphyNavigationAction *action) +activate_by_history_index (EphyNavigationAction *action, + int index) { EphyEmbed *embed; - int go_nth; - char *url; embed = ephy_window_get_active_embed (action->priv->window); g_return_if_fail (embed != NULL); - go_nth = GPOINTER_TO_INT (g_object_get_data (G_OBJECT (menuitem), NTH_DATA_KEY)); - if (ephy_gui_is_middle_click ()) { EphyEmbed *dest; @@ -165,7 +161,18 @@ activate_back_or_forward_menu_item_cb (GtkWidget *menuitem, ephy_embed_shistory_copy (embed, dest, TRUE, TRUE, FALSE); embed = dest; } - ephy_embed_shistory_go_nth (embed, go_nth); + ephy_embed_shistory_go_nth (embed, index); +} + +static void +activate_back_or_forward_menu_item_cb (GtkWidget *menuitem, + EphyNavigationAction *action) +{ + int go_nth; + + go_nth = GPOINTER_TO_INT (g_object_get_data (G_OBJECT (menuitem), NTH_DATA_KEY)); + + activate_by_history_index(action, go_nth); } static void @@ -397,6 +404,36 @@ connect_proxy (GtkAction *action, GtkWidget *proxy) } static void +ephy_navigation_action_activate (GtkAction *gtk_action) +{ + EphyNavigationAction *action = EPHY_NAVIGATION_ACTION (gtk_action); + EphyWindow *window = action->priv->window; + EphyEmbed *embed; + int pos; + + embed = ephy_window_get_active_embed (window); + g_return_if_fail (embed != NULL); + + pos = ephy_embed_shistory_get_pos (embed); + + if (action->priv->direction == EPHY_NAVIGATION_DIRECTION_BACK) + { + activate_by_history_index (action, pos - 1); + } + else if (action->priv->direction == EPHY_NAVIGATION_DIRECTION_FORWARD) + { + activate_by_history_index (action, pos + 1); + } + else if (action->priv->direction == EPHY_NAVIGATION_DIRECTION_UP) + { + ephy_link_open (EPHY_LINK (action), + ephy_embed_get_go_up_list (embed)->data, + NULL, + ephy_gui_is_middle_click () ? EPHY_LINK_NEW_TAB : 0); + } +} + +static void ephy_navigation_action_init (EphyNavigationAction *action) { action->priv = EPHY_NAVIGATION_ACTION_GET_PRIVATE (action); @@ -482,6 +519,7 @@ ephy_navigation_action_class_init (EphyNavigationActionClass *class) action_class->toolbar_item_type = GTK_TYPE_MENU_TOOL_BUTTON; action_class->connect_proxy = connect_proxy; + action_class->activate = ephy_navigation_action_activate; g_object_class_install_property (object_class, PROP_ARROW_TOOLTIP, diff --git a/src/ephy-toolbar.c b/src/ephy-toolbar.c index b74f397ea..eb31c1ed3 100755 --- a/src/ephy-toolbar.c +++ b/src/ephy-toolbar.c @@ -274,8 +274,6 @@ ephy_toolbar_set_window (EphyToolbar *toolbar, "direction", EPHY_NAVIGATION_DIRECTION_BACK, "is_important", TRUE, NULL); - g_signal_connect (action, "activate", - G_CALLBACK (window_cmd_go_back), priv->window); g_signal_connect_swapped (action, "open-link", G_CALLBACK (ephy_link_open), toolbar); gtk_action_group_add_action (priv->action_group, action); @@ -294,8 +292,6 @@ ephy_toolbar_set_window (EphyToolbar *toolbar, "window", priv->window, "direction", EPHY_NAVIGATION_DIRECTION_FORWARD, NULL); - g_signal_connect (action, "activate", - G_CALLBACK (window_cmd_go_forward), priv->window); g_signal_connect_swapped (action, "open-link", G_CALLBACK (ephy_link_open), toolbar); gtk_action_group_add_action (priv->action_group, action); @@ -314,8 +310,6 @@ ephy_toolbar_set_window (EphyToolbar *toolbar, "window", priv->window, "direction", EPHY_NAVIGATION_DIRECTION_UP, NULL); - g_signal_connect (action, "activate", - G_CALLBACK (window_cmd_go_up), priv->window); g_signal_connect_swapped (action, "open-link", G_CALLBACK (ephy_link_open), toolbar); gtk_action_group_add_action (priv->action_group, action); |