changeset 12939:7f633dd625a9

[gaim-migrate @ 15292] SF Patch # from Levi Bard with changes by Sadrul Levi says: " This patch adds anchors to the conversation history so that you can scroll up to the last thing a person said by middle-clicking his nick in the chatter list." Sadrul added a right-click menu item. I modified the text marks to be of the form user:SCREENNAME to make sure we don't end up with any conflicts with other text marks. committer: Tailor Script <tailor@pidgin.im>
author Richard Laager <rlaager@wiktel.com>
date Thu, 19 Jan 2006 06:30:09 +0000
parents 56129c18aa2b
children b25f48c9f6d7
files ChangeLog src/gtkconv.c
diffstat 2 files changed, 53 insertions(+), 1 deletions(-) [+]
line wrap: on
line diff
--- a/ChangeLog	Thu Jan 19 05:54:11 2006 +0000
+++ b/ChangeLog	Thu Jan 19 06:30:09 2006 +0000
@@ -45,11 +45,13 @@
 	* Added tab management options to the tab right-click menu (Sadrul Habib
 	  Chowdhury)
 	* Brand new message queueing system (Casey Harkins)
+	* Ability to find the last message from a user in a chat (Levi Bard
+	  and Sadrul Habib Chowdhury)
 
 	Sounds:
 	* Beautiful new default sounds (Brad Turcotte)
 	* Use libao for playing sounds via NAS instead of accessing NAS directly
-	* A volume control in the preferences
+	* A volume control in the preferences (Casey Harkins)
 
 	Log Viewer:
 	* Log viewer aggregates logs from the same "Person"
--- a/src/gtkconv.c	Thu Jan 19 05:54:11 2006 +0000
+++ b/src/gtkconv.c	Thu Jan 19 06:30:09 2006 +0000
@@ -1526,6 +1526,32 @@
 	gtk_widget_grab_focus(GAIM_GTK_CONVERSATION(conv)->entry);
 }
 
+static GtkTextMark *
+get_mark_for_user(GaimGtkConversation *gtkconv, const char *who)
+{
+	GtkTextBuffer *buf = gtk_text_view_get_buffer(GTK_TEXT_VIEW(gtkconv->imhtml));
+	char *tmp = g_strconcat("user:", who, NULL);
+	GtkTextMark *mark = gtk_text_buffer_get_mark(buf, tmp);
+
+	g_free(tmp);
+	return mark;
+}
+
+static void
+menu_last_said_cb(GtkWidget *w, GaimGtkConversation *gtkconv)
+{
+	GtkTextMark *mark;
+	const char *who;
+
+	who = g_object_get_data(G_OBJECT(w), "user_data");
+	mark = get_mark_for_user(gtkconv, who);
+	
+	if (mark != NULL)
+		gtk_text_view_scroll_to_mark(GTK_TEXT_VIEW(gtkconv->imhtml), mark, 0.1, FALSE, 0, 0);
+	else
+		g_return_if_reached();
+}
+
 static GtkWidget *
 create_chat_menu(GaimConversation *conv, const char *who,
 				 GaimPluginProtocolInfo *prpl_info, GaimConnection *gc)
@@ -1591,6 +1617,12 @@
 		g_object_set_data_full(G_OBJECT(button), "user_data", g_strdup(who), g_free);
 	}
 
+	button = gaim_new_item_from_stock(menu, _("Last said"), GTK_STOCK_INDEX,
+						G_CALLBACK(menu_last_said_cb), GAIM_GTK_CONVERSATION(conv), 0, 0, NULL);
+	g_object_set_data_full(G_OBJECT(button), "user_data", g_strdup(who), g_free);
+	if (!get_mark_for_user(GAIM_GTK_CONVERSATION(conv), who))
+		gtk_widget_set_sensitive(button, FALSE);
+
 	return menu;
 }
 
@@ -1673,6 +1705,12 @@
 
 	if (event->button == 1 && event->type == GDK_2BUTTON_PRESS) {
 		chat_do_im(gtkconv, who);
+	} else if (event->button == 2 && event->type == GDK_BUTTON_PRESS) {
+		/* Move to user's anchor */
+		GtkTextMark *mark = get_mark_for_user(gtkconv, who);
+
+		if(mark != NULL)
+			gtk_text_view_scroll_to_mark(GTK_TEXT_VIEW(gtkconv->imhtml), mark, 0.1, FALSE, 0, 0);
 	} else if (event->button == 3 && event->type == GDK_BUTTON_PRESS) {
 		GtkWidget *menu = create_chat_menu (conv, who, prpl_info, gc);
 		gtk_menu_popup(GTK_MENU(menu), NULL, NULL, NULL, NULL,
@@ -4622,6 +4660,18 @@
 		gtk_imhtml_delete(GTK_IMHTML(gtkconv->imhtml), &start, &end);
 	}
 
+	if (type == GAIM_CONV_TYPE_CHAT)
+	{
+		/* Create anchor for user */
+		GtkTextIter iter;
+		char *tmp = g_strconcat("user:", name, NULL);
+
+		gtk_text_buffer_get_end_iter(gtk_text_view_get_buffer(GTK_TEXT_VIEW(gtkconv->imhtml)), &iter);
+		gtk_text_buffer_create_mark(gtk_text_view_get_buffer(GTK_TEXT_VIEW(gtkconv->imhtml)),
+								tmp, &iter, TRUE);
+		g_free(tmp);
+	}
+
 	if (gtk_text_buffer_get_char_count(gtk_text_view_get_buffer(GTK_TEXT_VIEW(gtkconv->imhtml))))
 		gtk_imhtml_append_text(GTK_IMHTML(gtkconv->imhtml), "<BR>", gtk_font_options_all);