diff --git a/katze/katze-arrayaction.c b/katze/katze-arrayaction.c index f0287362..cc5f45f1 100644 --- a/katze/katze-arrayaction.c +++ b/katze/katze-arrayaction.c @@ -223,22 +223,21 @@ katze_array_action_icon_cb (GdkPixbuf* icon, static void katze_array_action_menu_item_select_cb (GtkWidget* proxy, - KatzeArrayAction* array_action) + KatzeArrayAction* array_action); + +static void +katze_array_action_generate_menu (KatzeArrayAction* array_action, + KatzeArray* array, + GtkWidget* menu, + GtkWidget* proxy) { guint n, i; - GtkWidget* menu; - GtkWidget* menuitem; - GtkWidget* submenu; - KatzeArray* array; KatzeItem* item; - GdkPixbuf* pixbuf; - GtkWidget* icon; + GtkWidget* menuitem; + GdkPixbuf* icon; + GtkWidget* image; + GtkWidget* submenu; - menu = gtk_menu_item_get_submenu (GTK_MENU_ITEM (proxy)); - gtk_container_foreach (GTK_CONTAINER (menu), - (GtkCallback)(gtk_widget_destroy), NULL); - - array = g_object_get_data (G_OBJECT (proxy), "KatzeItem"); n = katze_array_get_length (array); if (n > 0) for (i = 0; i < n; i++) @@ -255,16 +254,16 @@ katze_array_action_menu_item_select_cb (GtkWidget* proxy, menuitem = katze_image_menu_item_new_ellipsized ( katze_item_get_name (item)); if (KATZE_IS_ARRAY (item)) - pixbuf = gtk_widget_render_icon (menuitem, + icon = gtk_widget_render_icon (menuitem, GTK_STOCK_DIRECTORY, GTK_ICON_SIZE_MENU, NULL); else - pixbuf = katze_net_load_icon (array_action->net, + icon = katze_net_load_icon (array_action->net, katze_item_get_uri (item), (KatzeNetIconCb)katze_array_action_icon_cb, proxy, g_object_ref (menuitem)); - icon = gtk_image_new_from_pixbuf (pixbuf); - gtk_image_menu_item_set_image (GTK_IMAGE_MENU_ITEM (menuitem), icon); - g_object_unref (pixbuf); + image = gtk_image_new_from_pixbuf (icon); + g_object_unref (icon); + gtk_image_menu_item_set_image (GTK_IMAGE_MENU_ITEM (menuitem), image); gtk_menu_shell_append (GTK_MENU_SHELL (menu), menuitem); g_object_set_data (G_OBJECT (menuitem), "KatzeItem", item); if (KATZE_IS_ARRAY (item)) @@ -288,17 +287,27 @@ katze_array_action_menu_item_select_cb (GtkWidget* proxy, } } +static void +katze_array_action_menu_item_select_cb (GtkWidget* proxy, + KatzeArrayAction* array_action) +{ + GtkWidget* menu; + KatzeArray* array; + + menu = gtk_menu_item_get_submenu (GTK_MENU_ITEM (proxy)); + gtk_container_foreach (GTK_CONTAINER (menu), + (GtkCallback)(gtk_widget_destroy), NULL); + + array = g_object_get_data (G_OBJECT (proxy), "KatzeItem"); + katze_array_action_generate_menu (array_action, array, menu, proxy); +} + static void katze_array_action_proxy_clicked_cb (GtkWidget* proxy, KatzeArrayAction* array_action) { - guint n, i; GtkWidget* menu; - GtkWidget* menuitem; - GtkWidget* submenu; - KatzeItem* item; - GdkPixbuf* pixbuf; - GtkWidget* icon; + KatzeArray* array; if (GTK_IS_MENU_ITEM (proxy)) { @@ -311,50 +320,14 @@ katze_array_action_proxy_clicked_cb (GtkWidget* proxy, menu = gtk_menu_new (); - n = katze_array_get_length (array_action->array); - if (n > 0) - for (i = 0; i < n; i++) - { - item = katze_array_get_nth_item (array_action->array, i); - /* FIXME: The menu item should reflect changes to the item */ - if (!KATZE_IS_ARRAY (item) && !katze_item_get_uri (item)) - { - menuitem = gtk_separator_menu_item_new (); - gtk_widget_show (menuitem); - gtk_menu_shell_append (GTK_MENU_SHELL (menu), menuitem); - continue; - } - menuitem = katze_image_menu_item_new_ellipsized ( - katze_item_get_name (item)); - pixbuf = gtk_widget_render_icon (menuitem, - KATZE_IS_ARRAY (item) ? GTK_STOCK_DIRECTORY : GTK_STOCK_FILE, - GTK_ICON_SIZE_MENU, NULL); - icon = gtk_image_new_from_pixbuf (pixbuf); - gtk_image_menu_item_set_image (GTK_IMAGE_MENU_ITEM (menuitem), icon); - g_object_unref (pixbuf); - gtk_widget_show (menuitem); - gtk_menu_shell_append (GTK_MENU_SHELL (menu), menuitem); - g_object_set_data (G_OBJECT (menuitem), "KatzeItem", item); - if (KATZE_IS_ARRAY (item)) - { - submenu = gtk_menu_new (); - gtk_menu_item_set_submenu (GTK_MENU_ITEM (menuitem), submenu); - g_signal_connect (menuitem, "select", - G_CALLBACK (katze_array_action_menu_item_select_cb), array_action); - } - else - g_signal_connect (menuitem, "activate", - G_CALLBACK (katze_array_action_menu_item_activate_cb), array_action); - } - else - { - menuitem = gtk_image_menu_item_new_with_label (_("Empty")); - gtk_widget_set_sensitive (menuitem, FALSE); - gtk_menu_shell_append (GTK_MENU_SHELL (menu), menuitem); - gtk_widget_show (menuitem); - } + array = (KatzeArray*)g_object_get_data (G_OBJECT (proxy), "KatzeArray"); + if (!array) + array = array_action->array; + katze_array_action_generate_menu (array_action, array, menu, proxy); - g_signal_emit (array_action, signals[POPULATE_POPUP], 0, menu); + /* populate-popup should only affect the main proxy */ + if (array == array_action->array) + g_signal_emit (array_action, signals[POPULATE_POPUP], 0, menu); katze_widget_popup (GTK_WIDGET (proxy), GTK_MENU (menu), NULL, KATZE_MENU_POSITION_LEFT); @@ -378,6 +351,106 @@ katze_array_action_create_tool_item (GtkAction* action) return toolitem; } +static void +katze_array_action_item_notify_cb (KatzeItem* item, + GParamSpec* pspec, + GtkToolItem* toolitem) +{ + KatzeArrayAction* array_action; + const gchar* property; + const gchar* title; + const gchar* desc; + GdkPixbuf* icon; + GtkWidget* image; + + if (!G_IS_PARAM_SPEC_STRING (pspec)) + return; + + array_action = (KatzeArrayAction*)g_object_get_data ( + G_OBJECT (toolitem), "KatzeArrayAction"); + property = g_param_spec_get_name (pspec); + if (!strcmp (property, "name")) + { + title = katze_item_get_name (item); + if (title) + gtk_tool_button_set_label (GTK_TOOL_BUTTON (toolitem), title); + else + gtk_tool_button_set_label (GTK_TOOL_BUTTON (toolitem), + katze_item_get_uri (item)); + } + else if (!strcmp (property, "text")) + { + desc = katze_item_get_text (item); + if (desc && *desc) + gtk_tool_item_set_tooltip_text (toolitem, desc); + else + gtk_tool_item_set_tooltip_text (toolitem, + katze_item_get_uri (item)); + } + else if (!KATZE_IS_ARRAY (item) && !strcmp (property, "uri")) + { + icon = katze_net_load_icon (array_action->net, katze_item_get_uri (item), + (KatzeNetIconCb)katze_array_action_icon_cb, + GTK_WIDGET (toolitem), g_object_ref (toolitem)); + image = gtk_image_new_from_pixbuf (icon); + g_object_unref (icon); + gtk_widget_show (image); + gtk_tool_button_set_icon_widget (GTK_TOOL_BUTTON (toolitem), image); + } +} + +GtkToolItem* +katze_array_action_create_tool_item_for (KatzeArrayAction* array_action, + KatzeItem* item) +{ + const gchar* title; + const gchar* uri; + const gchar* desc; + GtkToolItem* toolitem; + GdkPixbuf* icon; + GtkWidget* image; + + title = katze_item_get_name (item); + uri = katze_item_get_uri (item); + desc = katze_item_get_text (item); + + if (!KATZE_IS_ARRAY (item) && !uri) + return gtk_separator_tool_item_new (); + + toolitem = gtk_tool_button_new (NULL, NULL); + if (KATZE_IS_ARRAY (item)) + icon = gtk_widget_render_icon (GTK_WIDGET (toolitem), + GTK_STOCK_DIRECTORY, GTK_ICON_SIZE_MENU, NULL); + else + icon = katze_net_load_icon (array_action->net, uri, + (KatzeNetIconCb)katze_array_action_icon_cb, + GTK_WIDGET (toolitem), g_object_ref (toolitem)); + image = gtk_image_new_from_pixbuf (icon); + g_object_unref (icon); + gtk_widget_show (image); + gtk_tool_button_set_icon_widget (GTK_TOOL_BUTTON (toolitem), image); + if (title) + gtk_tool_button_set_label (GTK_TOOL_BUTTON (toolitem), title); + else + gtk_tool_button_set_label (GTK_TOOL_BUTTON (toolitem), uri); + gtk_tool_item_set_is_important (toolitem, TRUE); + if (desc && *desc) + gtk_tool_item_set_tooltip_text (toolitem, desc); + else + gtk_tool_item_set_tooltip_text (toolitem, uri); + if (KATZE_IS_ARRAY (item)) + { + g_object_set_data (G_OBJECT (toolitem), "KatzeArray", item); + g_signal_connect (toolitem, "clicked", + G_CALLBACK (katze_array_action_proxy_clicked_cb), array_action); + } + + g_object_set_data (G_OBJECT (toolitem), "KatzeArrayAction", array_action); + g_signal_connect (item, "notify", + G_CALLBACK (katze_array_action_item_notify_cb), toolitem); + return toolitem; +} + static void katze_array_action_connect_proxy (GtkAction* action, GtkWidget* proxy) diff --git a/katze/katze-arrayaction.h b/katze/katze-arrayaction.h index b4e9ee22..062ffbd0 100644 --- a/katze/katze-arrayaction.h +++ b/katze/katze-arrayaction.h @@ -14,6 +14,8 @@ #include "katze-array.h" +#include + G_BEGIN_DECLS #define KATZE_TYPE_ARRAY_ACTION \ @@ -42,6 +44,10 @@ void katze_array_action_set_array (KatzeArrayAction* array_action, KatzeArray* array); +GtkToolItem* +katze_array_action_create_tool_item_for (KatzeArrayAction* array_action, + KatzeItem* item); + G_END_DECLS #endif /* __KATZE_ARRAY_ACTION_H__ */ diff --git a/midori/midori-browser.c b/midori/midori-browser.c index 08f99fdf..0df54628 100644 --- a/midori/midori-browser.c +++ b/midori/midori-browser.c @@ -2443,46 +2443,6 @@ midori_browser_bookmarks_item_render_text_cb (GtkTreeViewColumn* column, g_object_set (renderer, "markup", _("Separator"), NULL); } -static void -_midori_browser_create_bookmark_menu (MidoriBrowser* browser, - KatzeArray* array, - GtkWidget* menu); - -static void -midori_browser_bookmark_menu_folder_activate_cb (GtkWidget* menuitem, - MidoriBrowser* browser) -{ - GtkWidget* menu; - KatzeArray* array; - - menu = gtk_menu_item_get_submenu (GTK_MENU_ITEM (menuitem)); - gtk_container_foreach (GTK_CONTAINER (menu), (GtkCallback) gtk_widget_destroy, NULL); - array = (KatzeArray*)g_object_get_data (G_OBJECT (menuitem), "KatzeArray"); - _midori_browser_create_bookmark_menu (browser, array, menu); - /* Remove all menuitems when the menu is hidden. - FIXME: We really *want* the line below, but it won't work like that - g_signal_connect_after (menu, "hide", G_CALLBACK (gtk_container_foreach), gtk_widget_destroy); */ - gtk_widget_show (menuitem); -} - -static void -midori_browser_bookmarkbar_folder_activate_cb (GtkToolItem* toolitem, - MidoriBrowser* browser) -{ - GtkWidget* menu; - KatzeArray* array; - - menu = gtk_menu_new (); - array = (KatzeArray*)g_object_get_data (G_OBJECT (toolitem), "KatzeArray"); - _midori_browser_create_bookmark_menu (browser, array, menu); - /* Remove all menuitems when the menu is hidden. - FIXME: We really *should* run the line below, but it won't work like that - g_signal_connect (menu, "hide", G_CALLBACK (gtk_container_foreach), - gtk_widget_destroy); */ - sokoke_widget_popup (GTK_WIDGET (toolitem), GTK_MENU (menu), - NULL, SOKOKE_MENU_POSITION_LEFT); -} - static void midori_browser_menu_bookmarks_item_activate_cb (GtkWidget* widget, MidoriBrowser* browser) @@ -2505,13 +2465,16 @@ midori_browser_bookmarkbar_item_button_press_event_cb (GtkWidget* toolitem, if (event->button == 2) { - g_object_get (browser->settings, "open-tabs-in-the-background", - &open_in_background, NULL); item = (KatzeItem*)g_object_get_data (G_OBJECT (toolitem), "KatzeItem"); - n = midori_browser_add_uri (browser, katze_item_get_uri (item)); - if (!open_in_background) - midori_browser_set_current_page (browser, n); - return TRUE; + if (katze_item_get_uri (item)) + { + g_object_get (browser->settings, "open-tabs-in-the-background", + &open_in_background, NULL); + n = midori_browser_add_uri (browser, katze_item_get_uri (item)); + if (!open_in_background) + midori_browser_set_current_page (browser, n); + return TRUE; + } } else if (event->button == 3) { @@ -2522,64 +2485,6 @@ midori_browser_bookmarkbar_item_button_press_event_cb (GtkWidget* toolitem, return FALSE; } -static void -_midori_browser_create_bookmark_menu (MidoriBrowser* browser, - KatzeArray* array, - GtkWidget* menu) -{ - guint i, n; - KatzeItem* item; - const gchar* title; - GtkWidget* menuitem; - GtkWidget* submenu; - GtkWidget* image; - GdkPixbuf* icon; - - n = katze_array_get_length (array); - for (i = 0; i < n; i++) - { - item = katze_array_get_nth_item (array, i); - title = katze_item_get_name (item); - - if (KATZE_IS_ARRAY (item)) - { - /* FIXME: what about the "folded" status */ - menuitem = sokoke_image_menu_item_new_ellipsized (title); - gtk_image_menu_item_set_image (GTK_IMAGE_MENU_ITEM (menuitem), - gtk_image_new_from_stock (GTK_STOCK_DIRECTORY, - GTK_ICON_SIZE_MENU)); - submenu = gtk_menu_new (); - gtk_menu_item_set_submenu (GTK_MENU_ITEM (menuitem), submenu); - g_signal_connect (menuitem, "activate", - G_CALLBACK (midori_browser_bookmark_menu_folder_activate_cb), - browser); - g_object_set_data (G_OBJECT (menuitem), "KatzeArray", item); - } - else if (katze_item_get_uri (item)) - { - menuitem = sokoke_image_menu_item_new_ellipsized (title); - image = gtk_image_new (); - /* FIXME: Implement icon_cb */ - icon = katze_net_load_icon (browser->net, - katze_item_get_uri (item), - NULL /*(KatzeNetIconCb)midori_browser_bookmark_icon_cb*/, - GTK_WIDGET (browser), NULL /*g_object_ref (image)*/); - gtk_image_set_from_pixbuf (GTK_IMAGE (image), icon); - g_object_unref (icon); - gtk_widget_show (image); - gtk_image_menu_item_set_image (GTK_IMAGE_MENU_ITEM (menuitem), image); - g_signal_connect (menuitem, "activate", - G_CALLBACK (midori_browser_menu_bookmarks_item_activate_cb), - browser); - g_object_set_data (G_OBJECT (menuitem), "KatzeItem", item); - } - else - menuitem = gtk_separator_menu_item_new (); - gtk_menu_shell_append (GTK_MENU_SHELL (menu), menuitem); - gtk_widget_show (menuitem); - } -} - static void _action_bookmark_add_activate (GtkAction* action, MidoriBrowser* browser) @@ -4193,20 +4098,61 @@ midori_browser_settings_notify (MidoriWebSettings* web_settings, g_value_unset (&value); } +static void +browser_bookmarks_add_item_cb (KatzeArray* array, + KatzeItem* item, + MidoriBrowser* browser) +{ + GtkToolItem* toolitem; + + toolitem = katze_array_action_create_tool_item_for ( + KATZE_ARRAY_ACTION (_action_by_name (browser, "Bookmarks")), item); + + g_object_set_data (G_OBJECT (toolitem), "KatzeItem", item); + if (!KATZE_IS_ARRAY (item) && katze_item_get_uri (item)) + g_signal_connect (toolitem, "clicked", + G_CALLBACK (midori_browser_menu_bookmarks_item_activate_cb), + browser); + if (KATZE_IS_ARRAY (item) || katze_item_get_uri (item)) + { + g_signal_connect (gtk_bin_get_child (GTK_BIN (toolitem)), + "button-press-event", + G_CALLBACK (midori_browser_bookmarkbar_item_button_press_event_cb), + browser); + g_object_set_data (G_OBJECT (gtk_bin_get_child (GTK_BIN (toolitem))), + "KatzeItem", item); + } + gtk_widget_show (GTK_WIDGET (toolitem)); + gtk_toolbar_insert (GTK_TOOLBAR (browser->bookmarkbar), toolitem, -1); +} + +static void +browser_bookmarks_remove_item_cb (KatzeArray* array, + KatzeItem* removed_item, + MidoriBrowser* browser) +{ + GList* children; + GtkWidget* toolitem; + KatzeItem* item; + + children = gtk_container_get_children (GTK_CONTAINER (browser->bookmarkbar)); + while (children != NULL) + { + toolitem = GTK_WIDGET (children->data); + item = (KatzeItem*)g_object_get_data (G_OBJECT (toolitem), "KatzeItem"); + if (item == removed_item) + gtk_widget_destroy (toolitem); + children = g_list_next (children); + } +} + static void midori_browser_load_bookmarks (MidoriBrowser* browser) { guint i, n; KatzeItem* item; - const gchar* title; - const gchar* desc; - GtkWidget* image; - GdkPixbuf* icon; - GtkToolItem* toolitem; GtkTreeModel* treestore; - // FIXME: Clear bookmarks menu - // FIXME: Clear bookmarkbar // FIXME: Clear bookmark panel _action_set_sensitive (browser, "BookmarkAdd", FALSE); @@ -4218,51 +4164,12 @@ midori_browser_load_bookmarks (MidoriBrowser* browser) for (i = 0; i < n; i++) { item = katze_array_get_nth_item (browser->bookmarks, i); - title = katze_item_get_name (item); - desc = katze_item_get_text (item); - - if (KATZE_IS_ARRAY (item)) - { - toolitem = gtk_tool_button_new_from_stock (GTK_STOCK_DIRECTORY); - gtk_tool_button_set_label (GTK_TOOL_BUTTON (toolitem), title); - gtk_tool_item_set_is_important (toolitem, TRUE); - g_signal_connect (toolitem, "clicked", - G_CALLBACK (midori_browser_bookmarkbar_folder_activate_cb), - browser); - if (desc && *desc) - gtk_tool_item_set_tooltip_text (toolitem, desc); - g_object_set_data (G_OBJECT (toolitem), "KatzeArray", item); - } - else if (katze_item_get_uri (item)) - { - image = gtk_image_new (); - /* FIXME: Implement icon_cb */ - icon = katze_net_load_icon (browser->net, - katze_item_get_uri (item), - NULL /*(KatzeNetIconCb)midori_browser_bookmark_icon_cb*/, - GTK_WIDGET (browser), NULL /*g_object_ref (image)*/); - gtk_image_set_from_pixbuf (GTK_IMAGE (image), icon); - g_object_unref (icon); - toolitem = gtk_tool_button_new (image, title); - gtk_tool_item_set_is_important (toolitem, TRUE); - g_signal_connect (toolitem, "clicked", - G_CALLBACK (midori_browser_menu_bookmarks_item_activate_cb), - browser); - g_signal_connect (gtk_bin_get_child (GTK_BIN (toolitem)), - "button-press-event", - G_CALLBACK (midori_browser_bookmarkbar_item_button_press_event_cb), - browser); - if (desc && *desc) - gtk_tool_item_set_tooltip_text (toolitem, desc); - g_object_set_data (G_OBJECT (toolitem), "KatzeItem", item); - g_object_set_data (G_OBJECT (gtk_bin_get_child (GTK_BIN (toolitem))), - "KatzeItem", item); - } - else - toolitem = gtk_separator_tool_item_new (); - gtk_toolbar_insert (GTK_TOOLBAR (browser->bookmarkbar), toolitem, -1); + browser_bookmarks_add_item_cb (browser->bookmarks, item, browser); } - sokoke_container_show_children (GTK_CONTAINER (browser->bookmarkbar)); + g_signal_connect (browser->bookmarks, "add-item", + G_CALLBACK (browser_bookmarks_add_item_cb), browser); + g_signal_connect (browser->bookmarks, "remove-item", + G_CALLBACK (browser_bookmarks_remove_item_cb), browser); treestore = gtk_tree_view_get_model (GTK_TREE_VIEW (browser->panel_bookmarks)); _tree_store_insert_folder (GTK_TREE_STORE (treestore),