changeset 14616:f1f1dcb26d89

[gaim-migrate @ 17344] Add a barebone menu in the buddylist for account actions. (Press Ctrl+o) committer: Tailor Script <tailor@pidgin.im>
author Sadrul Habib Chowdhury <imadil@gmail.com>
date Sun, 24 Sep 2006 17:07:38 +0000
parents bddedf8e4653
children 3df4aadebc20
files console/gntblist.c console/libgnt/gntmenu.c console/libgnt/gntmenuitem.c console/libgnt/gntmenuitem.h console/libgnt/gnttree.c console/libgnt/gnttree.h console/libgnt/gntwindow.c console/libgnt/test/menu.c
diffstat 8 files changed, 128 insertions(+), 12 deletions(-) [+]
line wrap: on
line diff
--- a/console/gntblist.c	Sun Sep 24 16:35:31 2006 +0000
+++ b/console/gntblist.c	Sun Sep 24 17:07:38 2006 +0000
@@ -39,6 +39,7 @@
 #include "gntlabel.h"
 #include "gntline.h"
 #include "gnttree.h"
+#include "gntwindow.h"
 
 #include "gntblist.h"
 #include "gntconv.h"
@@ -483,6 +484,8 @@
 				gnt_tree_create_row(GNT_TREE(ggblist->tree), get_display_name(node)),
 				group, NULL);
 
+	/* XXX: This causes problem because you can close a chat window, hide the buddylist.
+	 * When you show the buddylist, you automatically join the chat again. */
 	if (gaim_blist_node_get_bool((GaimBlistNode*)chat, "gnt-autojoin"))
 		serv_join_chat(gaim_account_get_connection(chat->account), chat->components);
 }
@@ -1608,6 +1611,75 @@
 	return FALSE;
 }
 
+static void
+plugin_action(GntMenuItem *item, gpointer data)
+{
+	GaimPluginAction *action = data;
+	if (action && action->callback)
+		action->callback(action);
+}
+
+static void
+reconstruct_accounts_menu()
+{
+	GntWidget *menu, *sub;
+	GntMenuItem *item;
+	GntWindow *window;
+	GList *iter;
+
+	if (!ggblist)
+		return;
+
+	window  = GNT_WINDOW(ggblist->window);
+
+	menu = gnt_menu_new(GNT_MENU_TOPLEVEL);
+	gnt_window_set_menu(window, GNT_MENU(menu));
+
+	item = gnt_menuitem_new(_("Accounts"));
+	gnt_menu_add_item(GNT_MENU(menu), item);
+
+	sub = gnt_menu_new(GNT_MENU_POPUP);
+	gnt_menuitem_set_submenu(item, GNT_MENU(sub));
+
+	for (iter = gaim_accounts_get_all_active(); iter;
+			iter = g_list_delete_link(iter, iter)) {
+		GaimAccount *account = iter->data;
+		GaimConnection *gc = gaim_account_get_connection(account);
+		GaimPlugin *prpl;
+		
+		if (!GAIM_CONNECTION_IS_CONNECTED(gc))
+			continue;
+		prpl = gc->prpl;
+
+		if (GAIM_PLUGIN_HAS_ACTIONS(prpl)) {
+			GList *acts;
+			GntWidget *s;
+
+			item = gnt_menuitem_new(gaim_account_get_username(account));
+			s = gnt_menu_new(GNT_MENU_POPUP);
+			gnt_menuitem_set_submenu(item, GNT_MENU(s));
+			gnt_menu_add_item(GNT_MENU(sub), item);
+
+			for (acts = GAIM_PLUGIN_ACTIONS(prpl, gc); acts;
+					acts = g_list_delete_link(acts, acts)) {
+				GaimPluginAction *action = acts->data;
+				if (!action)
+					continue;
+
+				action->plugin = prpl;
+				action->context = gc;
+
+				item = gnt_menuitem_new(action->label);
+				gnt_menuitem_set_callback(item, plugin_action, action);
+				/* This is to make sure the action is freed when the menu is destroyed */
+				g_object_set_data_full(G_OBJECT(item), "plugin_action", action,
+					(GDestroyNotify)gaim_plugin_action_free);
+				gnt_menu_add_item(GNT_MENU(s), item);
+			}
+		}
+	}
+}
+
 void gg_blist_show()
 {
 	if (ggblist)
@@ -1617,7 +1689,7 @@
 
 	gaim_get_blist()->ui_data = ggblist;
 
-	ggblist->window = gnt_vbox_new(FALSE);
+	ggblist->window = gnt_vwindow_new(FALSE);
 	gnt_widget_set_name(ggblist->window, "buddylist");
 	gnt_box_set_toplevel(GNT_BOX(ggblist->window), TRUE);
 	gnt_box_set_title(GNT_BOX(ggblist->window), _("Buddy List"));
@@ -1641,6 +1713,10 @@
 
 	gnt_widget_show(ggblist->window);
 
+	gaim_signal_connect(gaim_connections_get_handle(), "signed-on", gg_blist_get_handle(),
+				GAIM_CALLBACK(reconstruct_accounts_menu), NULL);
+	gaim_signal_connect(gaim_connections_get_handle(), "signed-off", gg_blist_get_handle(),
+				GAIM_CALLBACK(reconstruct_accounts_menu), NULL);
 	gaim_signal_connect(gaim_blist_get_handle(), "buddy-status-changed", gg_blist_get_handle(),
 				GAIM_CALLBACK(buddy_status_changed), ggblist);
 	gaim_signal_connect(gaim_blist_get_handle(), "buddy-idle-changed", gg_blist_get_handle(),
@@ -1682,6 +1758,8 @@
 	g_signal_connect(G_OBJECT(ggblist->statustext), "key_pressed",
 				G_CALLBACK(status_text_changed), NULL);
 
+	reconstruct_accounts_menu(ggblist);
+
 	populate_buddylist();
 
 	savedstatus_changed(gaim_savedstatus_get_current(), NULL);
--- a/console/libgnt/gntmenu.c	Sun Sep 24 16:35:31 2006 +0000
+++ b/console/libgnt/gntmenu.c	Sun Sep 24 17:07:38 2006 +0000
@@ -10,10 +10,10 @@
 static GntTreeClass *parent_class = NULL;
 static guint signals[SIGS] = { 0 };
 
-void (*org_draw)(GntWidget *wid);
-void (*org_destroy)(GntWidget *wid);
-void (*org_map)(GntWidget *wid);
-gboolean (*org_key_pressed)(GntWidget *w, const char *t);
+static void (*org_draw)(GntWidget *wid);
+static void (*org_destroy)(GntWidget *wid);
+static void (*org_map)(GntWidget *wid);
+static gboolean (*org_key_pressed)(GntWidget *w, const char *t);
 
 static void
 gnt_menu_draw(GntWidget *widget)
@@ -89,6 +89,7 @@
 			menu_tree_add(menu, item, NULL);
 		}
 		org_map(widget);
+		gnt_tree_adjust_columns(GNT_TREE(widget));
 	}
 	GNTDEBUG;
 }
@@ -267,7 +268,7 @@
 	GntWidget *widget = g_object_new(GNT_TYPE_MENU, NULL);
 	GntMenu *menu = GNT_MENU(widget);
 	menu->list = NULL;
-	menu->selected = -1;
+	menu->selected = 0;
 	menu->type = type;
 
 	if (type == GNT_MENU_TOPLEVEL) {
--- a/console/libgnt/gntmenuitem.c	Sun Sep 24 16:35:31 2006 +0000
+++ b/console/libgnt/gntmenuitem.c	Sun Sep 24 17:07:38 2006 +0000
@@ -56,14 +56,14 @@
 	return type;
 }
 
-GObject *gnt_menuitem_new(const char *text)
+GntMenuItem *gnt_menuitem_new(const char *text)
 {
 	GObject *item = g_object_new(GNT_TYPE_MENUITEM, NULL);
 	GntMenuItem *menuitem = GNT_MENUITEM(item);
 
 	menuitem->text = g_strdup(text);
 
-	return item;
+	return menuitem;
 }
 
 void gnt_menuitem_set_callback(GntMenuItem *item, GntMenuItemCallback callback, gpointer data)
--- a/console/libgnt/gntmenuitem.h	Sun Sep 24 16:35:31 2006 +0000
+++ b/console/libgnt/gntmenuitem.h	Sun Sep 24 17:07:38 2006 +0000
@@ -58,7 +58,7 @@
 
 GType gnt_menuitem_get_gtype(void);
 
-GObject *gnt_menuitem_new(const char *text);
+GntMenuItem *gnt_menuitem_new(const char *text);
 
 void gnt_menuitem_set_callback(GntMenuItem *item, GntMenuItemCallback callback, gpointer data);
 
--- a/console/libgnt/gnttree.c	Sun Sep 24 16:35:31 2006 +0000
+++ b/console/libgnt/gnttree.c	Sun Sep 24 17:07:38 2006 +0000
@@ -1,5 +1,6 @@
 #include "gnttree.h"
 #include "gntmarshal.h"
+#include "gntutils.h"
 
 #include <string.h>
 #include <ctype.h>
@@ -1140,6 +1141,7 @@
 	{
 		tree->columns[col].width = 15;
 	}
+	tree->list = NULL;
 	tree->show_title = FALSE;
 }
 
@@ -1241,3 +1243,33 @@
 	tree->show_separator = set;
 }
 
+void gnt_tree_adjust_columns(GntTree *tree)
+{
+	GntTreeRow *row = tree->root;
+	int *widths, i, twidth, height;
+
+	widths = g_new0(int, tree->ncol);
+	while (row) {
+		GList *iter;
+		for (i = 0, iter = row->columns; iter; iter = iter->next, i++) {
+			GntTreeCol *col = iter->data;
+			int w = gnt_util_onscreen_width(col->text, NULL);
+			if (widths[i] < w)
+				widths[i] = w;
+		}
+		row = row->next;
+	}
+
+	twidth = 1 + 2 * (!GNT_WIDGET_IS_FLAG_SET(GNT_WIDGET(tree), GNT_WIDGET_NO_BORDER));
+	for (i = 0; i < tree->ncol; i++) {
+		gnt_tree_set_col_width(tree, i, widths[i]);
+		twidth += widths[i] + (tree->show_separator ? 1 : 0) + 1;
+		fprintf(stderr, "column width for col %d: %d\n", i, widths[i]);
+	}
+	g_free(widths);
+
+	fprintf(stderr, "tree width: %d\n", twidth);
+	gnt_widget_get_size(GNT_WIDGET(tree), NULL, &height);
+	gnt_widget_set_size(GNT_WIDGET(tree), twidth, height);
+}
+
--- a/console/libgnt/gnttree.h	Sun Sep 24 16:35:31 2006 +0000
+++ b/console/libgnt/gnttree.h	Sun Sep 24 17:07:38 2006 +0000
@@ -123,6 +123,9 @@
 
 void gnt_tree_set_show_separator(GntTree *tree, gboolean set);
 
+/* This will try to automatically adjust the width of the columns in the tree */
+void gnt_tree_adjust_columns(GntTree *tree);
+
 G_END_DECLS
 
 /* The following functions should NOT be used by applications. */
--- a/console/libgnt/gntwindow.c	Sun Sep 24 16:35:31 2006 +0000
+++ b/console/libgnt/gntwindow.c	Sun Sep 24 17:07:38 2006 +0000
@@ -10,8 +10,8 @@
 static GntBoxClass *parent_class = NULL;
 static guint signals[SIGS] = { 0 };
 
-gboolean (*org_keypress)(GntWidget *widget, const char *text);
-void (*org_destroy)(GntWidget *widget);
+static gboolean (*org_keypress)(GntWidget *widget, const char *text);
+static void (*org_destroy)(GntWidget *widget);
 
 static gboolean
 gnt_window_key_pressed(GntWidget *widget, const char *text)
@@ -108,6 +108,9 @@
 
 void gnt_window_set_menu(GntWindow *window, GntMenu *menu)
 {
+	/* If a menu already existed, then destroy that first. */
+	if (window->menu)
+		gnt_widget_destroy(GNT_WIDGET(window->menu));
 	window->menu = menu;
 }
 
--- a/console/libgnt/test/menu.c	Sun Sep 24 16:35:31 2006 +0000
+++ b/console/libgnt/test/menu.c	Sun Sep 24 17:07:38 2006 +0000
@@ -48,7 +48,6 @@
 
 	gnt_screen_menu_show(menu);
 
-
 	GntWidget *win = gnt_window_new();
 	gnt_box_add_widget(GNT_BOX(win),
 		gnt_label_new("..."));