diff libpurple/ft.c @ 29838:35cbe4684177

propagate from branch 'im.pidgin.pidgin' (head 1ccb1507e6594c80788043ea114c7fb942828e48) to branch 'im.pidgin.cpw.malu.ft_thumbnails' (head b439e619df4a497e9807614d87f9fb47308d648b)
author Elliott Sales de Andrade <qulogic@pidgin.im>
date Sun, 25 Apr 2010 21:40:33 +0000
parents afc9cec164e4
children ce52e101844a
line wrap: on
line diff
--- a/libpurple/ft.c	Sun Apr 25 21:40:25 2010 +0000
+++ b/libpurple/ft.c	Sun Apr 25 21:40:33 2010 +0000
@@ -60,6 +60,10 @@
 
 	/* TODO: Should really use a PurpleCircBuffer for this. */
 	GByteArray *buffer;
+
+	gpointer thumbnail_data;		/**< thumbnail image */
+	gsize thumbnail_size;
+	gchar *thumbnail_mimetype;
 } PurpleXferPrivData;
 
 static int purple_xfer_choose_file(PurpleXfer *xfer);
@@ -72,6 +76,10 @@
 	if (priv->buffer)
 		g_byte_array_free(priv->buffer, TRUE);
 
+	g_free(priv->thumbnail_data);
+
+	g_free(priv->thumbnail_mimetype);
+
 	g_free(priv);
 }
 
@@ -266,15 +274,21 @@
 	}
 }
 
-void purple_xfer_conversation_write(PurpleXfer *xfer, char *message, gboolean is_error)
+static void 
+purple_xfer_conversation_write_internal(PurpleXfer *xfer,
+	const char *message, gboolean is_error, gboolean print_thumbnail)
 {
 	PurpleConversation *conv = NULL;
 	PurpleMessageFlags flags = PURPLE_MESSAGE_SYSTEM;
 	char *escaped;
+	gconstpointer thumbnail_data;
+	gsize size;
 
 	g_return_if_fail(xfer != NULL);
 	g_return_if_fail(message != NULL);
 
+	thumbnail_data = purple_xfer_get_thumbnail(xfer, &size);
+
 	conv = purple_find_conversation_with_account(PURPLE_CONV_TYPE_IM, xfer->who,
 											   purple_xfer_get_account(xfer));
 
@@ -286,10 +300,39 @@
 	if (is_error)
 		flags |= PURPLE_MESSAGE_ERROR;
 
-	purple_conversation_write(conv, NULL, escaped, flags, time(NULL));
+	if (print_thumbnail && thumbnail_data) {
+		gchar *message_with_img;
+		gpointer data = g_memdup(thumbnail_data, size); 
+		int id = purple_imgstore_add_with_id(data, size, NULL);
+
+		message_with_img = 
+			g_strdup_printf("<img id='%d'> %s", id, escaped);
+		purple_conversation_write(conv, NULL, message_with_img, flags, 
+			time(NULL));
+		purple_imgstore_unref_by_id(id);
+		g_free(message_with_img);
+	} else {
+		purple_conversation_write(conv, NULL, escaped, flags, time(NULL));
+	}
 	g_free(escaped);
 }
 
+void
+purple_xfer_conversation_write(PurpleXfer *xfer, gchar *message,
+	gboolean is_error)
+{
+	purple_xfer_conversation_write_internal(xfer, message, is_error, FALSE);
+}
+
+/* maybe this one should be exported publically? */
+static void
+purple_xfer_conversation_write_with_thumbnail(PurpleXfer *xfer,
+	const gchar *message)
+{
+	purple_xfer_conversation_write_internal(xfer, message, FALSE, TRUE);
+}
+
+
 static void purple_xfer_show_file_error(PurpleXfer *xfer, const char *filename)
 {
 	int err = errno;
@@ -448,6 +491,8 @@
 {
 	char *buf, *size_buf;
 	size_t size;
+	gconstpointer thumb;
+	gsize thumb_size;
 
 	/* If we have already accepted the request, ask the destination file
 	   name directly */
@@ -473,13 +518,19 @@
 			serv_got_im(purple_account_get_connection(xfer->account),
 								 xfer->who, xfer->message, 0, time(NULL));
 
-		purple_request_accept_cancel(xfer, NULL, buf, NULL,
-								  PURPLE_DEFAULT_ACTION_NONE,
-								  xfer->account, xfer->who, NULL,
-								  xfer,
-								  G_CALLBACK(purple_xfer_choose_file),
-								  G_CALLBACK(cancel_recv_cb));
-
+		if ((thumb = purple_xfer_get_thumbnail(xfer, &thumb_size))) {
+			purple_request_accept_cancel_with_icon(xfer, NULL, buf, NULL,
+				PURPLE_DEFAULT_ACTION_NONE, xfer->account, xfer->who, NULL,
+				thumb, thumb_size, xfer, 
+				G_CALLBACK(purple_xfer_choose_file),
+				G_CALLBACK(cancel_recv_cb));
+		} else {
+			purple_request_accept_cancel(xfer, NULL, buf, NULL,
+				PURPLE_DEFAULT_ACTION_NONE, xfer->account, xfer->who, NULL,
+				xfer, G_CALLBACK(purple_xfer_choose_file),
+				G_CALLBACK(cancel_recv_cb));
+		}
+			
 		g_free(buf);
 	} else
 		purple_xfer_choose_file(xfer);
@@ -547,10 +598,12 @@
 		{
 			gchar* message = NULL;
 			PurpleBuddy *buddy = purple_find_buddy(xfer->account, xfer->who);
+
 			message = g_strdup_printf(_("%s is offering to send file %s"),
 				buddy ? purple_buddy_get_alias(buddy) : xfer->who, purple_xfer_get_filename(xfer));
-			purple_xfer_conversation_write(xfer, message, FALSE);
+			purple_xfer_conversation_write_with_thumbnail(xfer, message);
 			g_free(message);
+
 			/* Ask for a filename to save to if it's not already given by a plugin */
 			if (xfer->local_filename == NULL)
 				purple_xfer_ask_recv(xfer);
@@ -1580,6 +1633,52 @@
 		ui_ops->update_progress(xfer, purple_xfer_get_progress(xfer));
 }
 
+gconstpointer
+purple_xfer_get_thumbnail(const PurpleXfer *xfer, gsize *len)
+{
+	PurpleXferPrivData *priv = g_hash_table_lookup(xfers_data, xfer);
+
+	if (len)
+		*len = priv->thumbnail_size;
+
+	return priv->thumbnail_data;
+}
+
+const gchar *
+purple_xfer_get_thumbnail_mimetype(const PurpleXfer *xfer)
+{
+	PurpleXferPrivData *priv = g_hash_table_lookup(xfers_data, xfer);
+
+	return priv->thumbnail_mimetype;
+}
+
+void
+purple_xfer_set_thumbnail(PurpleXfer *xfer, gconstpointer thumbnail,
+	gsize size, const gchar *mimetype)
+{
+	PurpleXferPrivData *priv = g_hash_table_lookup(xfers_data, xfer);
+
+	g_free(priv->thumbnail_data);
+	g_free(priv->thumbnail_mimetype);
+
+	if (thumbnail && size > 0) {
+		priv->thumbnail_data = g_memdup(thumbnail, size);
+		priv->thumbnail_size = size;
+		priv->thumbnail_mimetype = g_strdup(mimetype);
+	} else {
+		priv->thumbnail_data = NULL;
+		priv->thumbnail_size = 0;
+		priv->thumbnail_mimetype = NULL;
+	}
+}
+
+void
+purple_xfer_prepare_thumbnail(PurpleXfer *xfer, const gchar *formats)
+{
+	if (xfer->ui_ops->add_thumbnail) {
+		xfer->ui_ops->add_thumbnail(xfer, formats);
+	}
+}
 
 /**************************************************************************
  * File Transfer Subsystem API