[yelp] [libyelp/yelp-view] Handle the right-click popup menu



commit faca2ee96c70f6376ee3f4ee93db7d138e445965
Author: Shaun McCance <shaunm gnome org>
Date:   Tue May 18 09:30:36 2010 -0500

    [libyelp/yelp-view] Handle the right-click popup menu

 libyelp/yelp-view.c    |  109 +++++++++++++++++++++++++++++++++++++++++++++++-
 src/yelp-application.c |   18 +++++---
 src/yelp-application.h |   24 ++++++-----
 src/yelp-window.c      |   13 ++++++
 4 files changed, 145 insertions(+), 19 deletions(-)
---
diff --git a/libyelp/yelp-view.c b/libyelp/yelp-view.c
index 7d5ab99..89eb36b 100644
--- a/libyelp/yelp-view.c
+++ b/libyelp/yelp-view.c
@@ -60,6 +60,13 @@ static void        view_scroll_adjustments        (YelpView           *view,
                                                    GtkAdjustment      *hadj,
                                                    GtkAdjustment      *vadj,
                                                    gpointer            data);
+static void        popup_open_link                (GtkMenuItem        *item,
+                                                   YelpView           *view);
+static void        popup_open_link_new            (GtkMenuItem        *item,
+                                                   YelpView           *view);
+static void        view_populate_popup            (YelpView           *view,
+                                                   GtkMenu            *menu,
+                                                   gpointer            data);
 static gboolean    view_navigation_requested      (WebKitWebView             *view,
                                                    WebKitWebFrame            *frame,
                                                    WebKitNetworkRequest      *request,
@@ -178,6 +185,8 @@ struct _YelpViewPrivate {
     gdouble        vadjust;
     gdouble        hadjust;
 
+    gchar         *popup_link_uri;
+
     YelpViewState  state;
 
     gchar         *page_id;
@@ -218,6 +227,8 @@ yelp_view_init (YelpView *view)
                       G_CALLBACK (view_resource_request), NULL);
     g_signal_connect (view, "set-scroll-adjustments",
                       G_CALLBACK (view_scroll_adjustments), NULL);
+    g_signal_connect (view, "populate-popup",
+                      G_CALLBACK (view_populate_popup), NULL);
 
     priv->action_group = gtk_action_group_new ("YelpView");
     gtk_action_group_set_translation_domain (priv->action_group, GETTEXT_PACKAGE);
@@ -265,6 +276,8 @@ yelp_view_finalize (GObject *object)
 {
     YelpViewPrivate *priv = GET_PRIV (object);
 
+    g_free (priv->popup_link_uri);
+
     g_free (priv->page_id);
     g_free (priv->root_title);
     g_free (priv->page_title);
@@ -304,8 +317,8 @@ yelp_view_class_init (YelpViewClass *klass)
 		      G_TYPE_FROM_CLASS (klass),
 		      G_SIGNAL_RUN_LAST,
                       0, NULL, NULL,
-		      g_cclosure_marshal_VOID__STRING,
-		      G_TYPE_NONE, 1, G_TYPE_STRING);
+		      g_cclosure_marshal_VOID__OBJECT,
+		      G_TYPE_NONE, 1, YELP_TYPE_URI);
 
     signals[EXTERNAL_URI] =
 	g_signal_new ("external-uri",
@@ -601,6 +614,98 @@ view_scroll_adjustments (YelpView      *view,
     }
 }
 
+static void
+popup_open_link (GtkMenuItem *item,
+                 YelpView    *view)
+{
+    YelpViewPrivate *priv = GET_PRIV (view);
+    YelpUri *uri;
+
+    if (g_str_has_prefix (priv->popup_link_uri, BOGUS_URI))
+        uri = yelp_uri_new_relative (priv->uri, priv->popup_link_uri + BOGUS_URI_LEN);
+    else
+        uri = yelp_uri_new_relative (priv->uri, priv->popup_link_uri);
+
+    yelp_view_load_uri (view, uri);
+
+    g_free (priv->popup_link_uri);
+    priv->popup_link_uri = NULL;
+}
+
+static void
+popup_open_link_new (GtkMenuItem *item,
+                     YelpView    *view)
+{
+    YelpViewPrivate *priv = GET_PRIV (view);
+    YelpUri *uri;
+
+    if (g_str_has_prefix (priv->popup_link_uri, BOGUS_URI))
+        uri = yelp_uri_new_relative (priv->uri, priv->popup_link_uri + BOGUS_URI_LEN);
+    else
+        uri = yelp_uri_new_relative (priv->uri, priv->popup_link_uri);
+
+    g_free (priv->popup_link_uri);
+    priv->popup_link_uri = NULL;
+
+    g_signal_emit (view, signals[NEW_VIEW_REQUESTED], 0, uri);
+    g_object_unref (uri);
+}
+
+static void
+view_populate_popup (YelpView *view,
+                     GtkMenu  *menu,
+                     gpointer  data)
+{
+    WebKitHitTestResult *result;
+    WebKitHitTestResultContext context;
+    GdkEvent *event;
+    YelpViewPrivate *priv = GET_PRIV (view);
+    GList *children;
+    GtkWidget *item;
+
+    children = gtk_container_get_children (GTK_CONTAINER (menu));
+    while (children) {
+        gtk_container_remove (GTK_CONTAINER (menu),
+                              GTK_WIDGET (children->data));
+        children = children->next;
+    }
+    g_list_free (children);
+
+    event = gtk_get_current_event ();
+
+    result = webkit_web_view_get_hit_test_result (WEBKIT_WEB_VIEW (view), (GdkEventButton *) event);
+    g_object_get (result, "context", &context, NULL);
+
+    if (context & WEBKIT_HIT_TEST_RESULT_CONTEXT_LINK) {
+        gchar *uri;
+        g_object_get (result, "link-uri", &uri, NULL);
+        g_free (priv->popup_link_uri);
+        priv->popup_link_uri = uri;
+
+        item = gtk_menu_item_new_with_mnemonic ("_Open Link");
+        g_signal_connect (item, "activate",
+                          G_CALLBACK (popup_open_link), view);
+        gtk_menu_shell_append (GTK_MENU_SHELL (menu), item);
+
+        item = gtk_menu_item_new_with_mnemonic ("Open Link in New _Window");
+        g_signal_connect (item, "activate",
+                          G_CALLBACK (popup_open_link_new), view);
+        gtk_menu_shell_append (GTK_MENU_SHELL (menu), item);
+    }
+    else {
+        item = gtk_action_create_menu_item (gtk_action_group_get_action (priv->action_group,
+                                                                         "YelpViewGoBack"));
+        gtk_menu_shell_append (GTK_MENU_SHELL (menu), item);
+        item = gtk_action_create_menu_item (gtk_action_group_get_action (priv->action_group,
+                                                                         "YelpViewGoForward"));
+        gtk_menu_shell_append (GTK_MENU_SHELL (menu), item);
+    }
+
+    g_object_unref (result);
+    gdk_event_free (event);
+    gtk_widget_show_all (GTK_WIDGET (menu));
+}
+
 static gboolean
 view_navigation_requested (WebKitWebView             *view,
                            WebKitWebFrame            *frame,
diff --git a/src/yelp-application.c b/src/yelp-application.c
index 8f4573d..155742a 100644
--- a/src/yelp-application.c
+++ b/src/yelp-application.c
@@ -407,19 +407,25 @@ void
 yelp_application_new_window (YelpApplication  *app,
                              const gchar      *uri)
 {
-    YelpApplicationLoad *data;
     YelpUri *yuri;
 
+    yuri = yelp_uri_new (uri ? uri : DEFAULT_URI);
+
+    yelp_application_new_window_uri (app, yuri);
+}
+
+void
+yelp_application_new_window_uri (YelpApplication  *app,
+                                 YelpUri          *uri)
+{
+    YelpApplicationLoad *data;
     data = g_new (YelpApplicationLoad, 1);
     data->app = app;
     data->new = TRUE;
-
-    yuri = yelp_uri_new (uri ? uri : DEFAULT_URI);
-
-    g_signal_connect (yuri, "resolved",
+    g_signal_connect (uri, "resolved",
                       G_CALLBACK (application_uri_resolved),
                       data);
-    yelp_uri_resolve (yuri);
+    yelp_uri_resolve (uri);
 }
 
 static void
diff --git a/src/yelp-application.h b/src/yelp-application.h
index 5a3726c..bf664a9 100644
--- a/src/yelp-application.h
+++ b/src/yelp-application.h
@@ -46,17 +46,19 @@ struct _YelpApplicationClass
     GObjectClass  parent_class;
 };
 
-GType             yelp_application_get_type    (void);
-YelpApplication*  yelp_application_new         (void);
-gint              yelp_application_run         (YelpApplication  *app,
-                                                gint              argc,
-                                                gchar           **argv);
-gboolean          yelp_application_load_uri    (YelpApplication  *app,
-                                                const gchar      *uri,
-                                                guint             timestamp,
-                                                GError          **error);
-void              yelp_application_new_window  (YelpApplication  *app,
-                                                const gchar      *uri);
+GType             yelp_application_get_type       (void);
+YelpApplication*  yelp_application_new            (void);
+gint              yelp_application_run            (YelpApplication  *app,
+                                                   gint              argc,
+                                                   gchar           **argv);
+gboolean          yelp_application_load_uri       (YelpApplication  *app,
+                                                   const gchar      *uri,
+                                                   guint             timestamp,
+                                                   GError          **error);
+void              yelp_application_new_window     (YelpApplication  *app,
+                                                   const gchar      *uri);
+void              yelp_application_new_window_uri (YelpApplication  *app,
+                                                   YelpUri          *uri);
 GtkActionGroup *  yelp_application_get_action_group     (YelpApplication   *app);
 void              yelp_application_add_bookmark         (YelpApplication   *app,
                                                          const gchar       *doc_uri,
diff --git a/src/yelp-window.c b/src/yelp-window.c
index 8885d73..d59a33f 100644
--- a/src/yelp-window.c
+++ b/src/yelp-window.c
@@ -111,6 +111,9 @@ static gboolean      entry_focus_out              (YelpLocationEntry  *entry,
 static void          view_external_uri            (YelpView           *view,
                                                    YelpUri            *uri,
                                                    YelpWindow         *window);
+static void          view_new_window              (YelpView           *view,
+                                                   YelpUri            *uri,
+                                                   YelpWindow         *window);
 static void          view_loaded                  (YelpView           *view,
                                                    YelpWindow         *window);
 static void          view_uri_selected            (YelpView           *view,
@@ -560,6 +563,7 @@ window_construct (YelpWindow *window)
     gtk_box_pack_start (GTK_BOX (priv->find_bar), priv->find_label, FALSE, FALSE, 0);
 
     g_signal_connect (priv->view, "external-uri", G_CALLBACK (view_external_uri), window);
+    g_signal_connect (priv->view, "new-view-requested", G_CALLBACK (view_new_window), window);
     g_signal_connect (priv->view, "loaded", G_CALLBACK (view_loaded), window);
     g_signal_connect (priv->view, "notify::yelp-uri", G_CALLBACK (view_uri_selected), window);
     g_signal_connect_swapped (priv->view, "notify::page-id",
@@ -1322,6 +1326,15 @@ view_external_uri (YelpView   *view,
 }
 
 static void
+view_new_window (YelpView   *view,
+                 YelpUri    *uri,
+                 YelpWindow *window)
+{
+    YelpWindowPrivate *priv = GET_PRIV (window);
+    yelp_application_new_window_uri (priv->application, uri);
+}
+
+static void
 view_loaded (YelpView   *view,
              YelpWindow *window)
 {



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