aboutsummaryrefslogtreecommitdiffstats
path: root/libempathy-gtk
diff options
context:
space:
mode:
Diffstat (limited to 'libempathy-gtk')
-rw-r--r--libempathy-gtk/empathy-chat-view.c11
-rw-r--r--libempathy-gtk/empathy-chat-view.h4
-rw-r--r--libempathy-gtk/empathy-chat.c125
-rw-r--r--libempathy-gtk/empathy-contact-widget.c159
-rw-r--r--libempathy-gtk/empathy-theme-adium.c163
5 files changed, 420 insertions, 42 deletions
diff --git a/libempathy-gtk/empathy-chat-view.c b/libempathy-gtk/empathy-chat-view.c
index 097215cfd..43d89dd78 100644
--- a/libempathy-gtk/empathy-chat-view.c
+++ b/libempathy-gtk/empathy-chat-view.c
@@ -212,3 +212,14 @@ empathy_chat_view_focus_toggled (EmpathyChatView *view,
}
}
+void
+empathy_chat_view_message_acknowledged (EmpathyChatView *view,
+ EmpathyMessage *message)
+{
+ g_return_if_fail (EMPATHY_IS_CHAT_VIEW (view));
+
+ if (EMPATHY_TYPE_CHAT_VIEW_GET_IFACE (view)->message_acknowledged) {
+ EMPATHY_TYPE_CHAT_VIEW_GET_IFACE (view)->message_acknowledged (view, message);
+ }
+}
+
diff --git a/libempathy-gtk/empathy-chat-view.h b/libempathy-gtk/empathy-chat-view.h
index 1af0721a3..73245c422 100644
--- a/libempathy-gtk/empathy-chat-view.h
+++ b/libempathy-gtk/empathy-chat-view.h
@@ -70,6 +70,8 @@ struct _EmpathyChatViewIface {
void (*copy_clipboard) (EmpathyChatView *view);
void (*focus_toggled) (EmpathyChatView *view,
gboolean has_focus);
+ void (*message_acknowledged) (EmpathyChatView *view,
+ EmpathyMessage *message);
};
GType empathy_chat_view_get_type (void) G_GNUC_CONST;
@@ -101,6 +103,8 @@ void empathy_chat_view_highlight (EmpathyChatView *view,
void empathy_chat_view_copy_clipboard (EmpathyChatView *view);
void empathy_chat_view_focus_toggled (EmpathyChatView *view,
gboolean has_focus);
+void empathy_chat_view_message_acknowledged (EmpathyChatView *view,
+ EmpathyMessage *message);
G_END_DECLS
diff --git a/libempathy-gtk/empathy-chat.c b/libempathy-gtk/empathy-chat.c
index 25203b46e..79411e74d 100644
--- a/libempathy-gtk/empathy-chat.c
+++ b/libempathy-gtk/empathy-chat.c
@@ -47,6 +47,7 @@
#include "empathy-chat.h"
#include "empathy-spell.h"
+#include "empathy-contact-dialogs.h"
#include "empathy-contact-list-store.h"
#include "empathy-contact-list-view.h"
#include "empathy-contact-menu.h"
@@ -173,6 +174,7 @@ enum {
PROP_SHOW_CONTACTS,
PROP_SMS_CHANNEL,
PROP_N_MESSAGES_SENDING,
+ PROP_NB_UNREAD_MESSAGES,
};
static guint signals[LAST_SIGNAL] = { 0 };
@@ -219,6 +221,10 @@ chat_get_property (GObject *object,
g_value_set_uint (value,
empathy_chat_get_n_messages_sending (chat));
break;
+ case PROP_NB_UNREAD_MESSAGES:
+ g_value_set_uint (value,
+ empathy_chat_get_nb_unread_messages (chat));
+ break;
default:
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, param_id, pspec);
break;
@@ -905,6 +911,84 @@ chat_command_say (EmpathyChat *chat,
g_object_unref (message);
}
+static void
+whois_got_contact_cb (TpConnection *connection,
+ guint n_contacts,
+ TpContact * const *contacts,
+ const gchar * const *requested_ids,
+ GHashTable *failed_id_errors,
+ const GError *error,
+ gpointer user_data,
+ GObject *weak_object)
+{
+ EmpathyChat *chat = EMPATHY_CHAT (weak_object);
+
+ g_return_if_fail (n_contacts <= 1);
+
+ if (n_contacts == 0) {
+ GHashTableIter iter;
+ gpointer key = NULL, value = NULL;
+ gchar *id;
+ GError *id_error;
+
+ /* tp-glib guarantees that the contacts you requested will be
+ * in failed_id_errors regardless of whether the individual
+ * contact was invalid or the whole operation failed.
+ */
+ g_hash_table_iter_init (&iter, failed_id_errors);
+ g_hash_table_iter_next (&iter, &key, &value);
+ id = key;
+ id_error = value;
+
+ DEBUG ("Error getting TpContact for '%s': %s %u %s",
+ id, g_quark_to_string (id_error->domain),
+ id_error->code, id_error->message);
+
+ if (error == NULL) {
+ /* The specific ID failed. */
+ gchar *event = g_strdup_printf (
+ _("“%s” is not a valid contact ID"), id);
+ empathy_chat_view_append_event (chat->view, event);
+ g_free (event);
+ }
+ /* Otherwise we're disconnected or something; so the window
+ * will already say ‘Disconnected’, so let's not show anything.
+ */
+ } else {
+ EmpathyContact *empathy_contact;
+ GtkWidget *window;
+
+ g_return_if_fail (contacts[0] != NULL);
+ empathy_contact = empathy_contact_dup_from_tp_contact (
+ contacts[0]);
+
+ window = gtk_widget_get_toplevel (GTK_WIDGET (chat));
+ /* If we're alive and this command is running, we'd better be
+ * in a window. */
+ g_return_if_fail (window != NULL);
+ g_return_if_fail (gtk_widget_is_toplevel (window));
+ empathy_contact_information_dialog_show (empathy_contact,
+ GTK_WINDOW (window));
+ g_object_unref (empathy_contact);
+ }
+}
+
+static void
+chat_command_whois (EmpathyChat *chat,
+ GStrv strv)
+{
+ EmpathyChatPriv *priv = GET_PRIV (chat);
+ TpConnection *conn;
+
+ conn = empathy_tp_chat_get_connection (priv->tp_chat);
+ tp_connection_get_contacts_by_id (conn,
+ /* Element 0 of 'strv' is "whois"; element 1 is the contact ID
+ * entered by the user (including spaces, if any). */
+ 1, (const gchar * const *) strv + 1,
+ 0, NULL,
+ whois_got_contact_cb, NULL, NULL, G_OBJECT (chat));
+}
+
static void chat_command_help (EmpathyChat *chat, GStrv strv);
typedef void (*ChatCommandFunc) (EmpathyChat *chat, GStrv strv);
@@ -953,6 +1037,9 @@ static ChatCommandItem commands[] = {
"This is used to send a message starting with a '/'. For example: "
"\"/say /join is used to join a new chat room\"")},
+ {"whois", 2, 2, chat_command_whois, NULL,
+ N_("/whois <contact ID>: display information about a contact")},
+
{"help", 1, 2, chat_command_help, NULL,
N_("/help [<command>]: show all supported commands. "
"If <command> is defined, show its usage.")},
@@ -1244,7 +1331,11 @@ chat_message_received (EmpathyChat *chat,
TP_CHANNEL_CHAT_STATE_ACTIVE,
chat);
- priv->unread_messages++;
+ if (empathy_message_is_incoming (message)) {
+ priv->unread_messages++;
+ g_object_notify (G_OBJECT (chat), "nb-unread-messages");
+ }
+
g_signal_emit (chat, signals[NEW_MESSAGE], 0, message, pending);
}
@@ -1257,6 +1348,20 @@ chat_message_received_cb (EmpathyTpChat *tp_chat,
}
static void
+chat_message_acknowledged_cb (EmpathyTpChat *tp_chat,
+ EmpathyMessage *message,
+ EmpathyChat *chat)
+{
+ EmpathyChatPriv *priv = GET_PRIV (chat);
+
+ empathy_chat_view_message_acknowledged (chat->view,
+ message);
+
+ priv->unread_messages--;
+ g_object_notify (G_OBJECT (chat), "nb-unread-messages");
+}
+
+static void
chat_send_error_cb (EmpathyTpChat *tp_chat,
const gchar *message_body,
TpChannelTextSendError error_code,
@@ -2845,6 +2950,8 @@ chat_finalize (GObject *object)
g_signal_handlers_disconnect_by_func (priv->tp_chat,
chat_message_received_cb, chat);
g_signal_handlers_disconnect_by_func (priv->tp_chat,
+ chat_message_acknowledged_cb, chat);
+ g_signal_handlers_disconnect_by_func (priv->tp_chat,
chat_send_error_cb, chat);
g_signal_handlers_disconnect_by_func (priv->tp_chat,
chat_state_changed_cb, chat);
@@ -2980,6 +3087,14 @@ empathy_chat_class_init (EmpathyChatClass *klass)
0, G_MAXUINT, 0,
G_PARAM_READABLE | G_PARAM_STATIC_STRINGS));
+ g_object_class_install_property (object_class,
+ PROP_NB_UNREAD_MESSAGES,
+ g_param_spec_uint ("nb-unread-messages",
+ "Num Unread Messages",
+ "The number of unread messages",
+ 0, G_MAXUINT, 0,
+ G_PARAM_READABLE | G_PARAM_STATIC_STRINGS));
+
signals[COMPOSING] =
g_signal_new ("composing",
G_OBJECT_CLASS_TYPE (object_class),
@@ -3548,6 +3663,9 @@ empathy_chat_set_tp_chat (EmpathyChat *chat,
g_signal_connect (tp_chat, "message-received",
G_CALLBACK (chat_message_received_cb),
chat);
+ g_signal_connect (tp_chat, "message_acknowledged",
+ G_CALLBACK (chat_message_acknowledged_cb),
+ chat);
g_signal_connect (tp_chat, "send-error",
G_CALLBACK (chat_send_error_cb),
chat);
@@ -3875,12 +3993,9 @@ empathy_chat_messages_read (EmpathyChat *self)
if (priv->retrieving_backlogs)
return;
- if (priv->tp_chat != NULL ) {
+ if (priv->tp_chat != NULL) {
empathy_tp_chat_acknowledge_all_messages (priv->tp_chat);
}
- priv->unread_messages = 0;
-
- empathy_chat_view_focus_toggled (self->view, TRUE);
}
/* Return TRUE if on of the contacts in this chat is composing */
diff --git a/libempathy-gtk/empathy-contact-widget.c b/libempathy-gtk/empathy-contact-widget.c
index c4e3748b4..14042bf61 100644
--- a/libempathy-gtk/empathy-contact-widget.c
+++ b/libempathy-gtk/empathy-contact-widget.c
@@ -40,6 +40,7 @@
#include <libempathy/empathy-contact-manager.h>
#include <libempathy/empathy-contact-list.h>
#include <libempathy/empathy-location.h>
+#include <libempathy/empathy-request-util.h>
#include <libempathy/empathy-time.h>
#include <libempathy/empathy-utils.h>
@@ -283,20 +284,74 @@ contact_widget_bday_changed_cb (GtkCalendar *calendar,
static void contact_widget_details_notify_cb (EmpathyContactWidget *information);
+typedef gchar * (* FieldFormatFunc) (GStrv);
+
typedef struct
{
const gchar *field_name;
const gchar *title;
- gboolean linkify;
+ FieldFormatFunc format;
} InfoFieldData;
+static gchar *
+linkify_first_value (GStrv values)
+{
+ return empathy_add_link_markup (values[0]);
+}
+
+static gchar *
+format_idle_time (GStrv values)
+{
+ const gchar *value = values[0];
+ int duration = strtol (value, NULL, 10);
+
+ if (duration <= 0)
+ return NULL;
+
+ return empathy_duration_to_string (duration);
+}
+
+static gchar *
+format_server (GStrv values)
+{
+ g_assert (values[0] != NULL);
+
+ if (values[1] == NULL)
+ return g_markup_escape_text (values[0], -1);
+ else
+ return g_markup_printf_escaped ("%s (%s)", values[0], values[1]);
+}
+
+static gchar *
+presence_hack (GStrv values)
+{
+ if (tp_str_empty (values[0]))
+ return NULL;
+
+ return g_markup_escape_text (values[0], -1);
+}
+
static InfoFieldData info_field_datas[] =
{
- { "fn", N_("Full name:"), FALSE },
- { "tel", N_("Phone number:"), FALSE },
- { "email", N_("E-mail address:"), TRUE },
- { "url", N_("Website:"), TRUE },
- { "bday", N_("Birthday:"), FALSE },
+ { "fn", N_("Full name:"), NULL },
+ { "tel", N_("Phone number:"), NULL },
+ { "email", N_("E-mail address:"), linkify_first_value },
+ { "url", N_("Website:"), linkify_first_value },
+ { "bday", N_("Birthday:"), NULL },
+
+ /* Note to translators: this is the caption for a string of the form "5
+ * minutes ago", and refers to the time since the contact last interacted
+ * with their IM client.
+ */
+ { "x-idle-time", N_("Last seen:"), format_idle_time },
+ { "x-irc-server", N_("Server:"), format_server },
+ { "x-host", N_("Connected from:"), format_server },
+
+ /* FIXME: once Idle implements SimplePresence using this information, we can
+ * and should bin this.
+ */
+ { "x-presence-status-message", N_("Away message:"), presence_hack },
+
{ NULL, NULL }
};
@@ -526,12 +581,73 @@ contact_widget_details_update_edit (EmpathyContactWidget *information)
return n_rows;
}
+static gboolean
+channel_name_activated_cb (
+ GtkLabel *label,
+ gchar *uri,
+ EmpathyContactWidget *information)
+{
+ TpAccount *account = empathy_contact_get_account (information->contact);
+
+ empathy_join_muc (account, uri, empathy_get_current_action_time ());
+ return TRUE;
+}
+
+static void
+add_channel_list (
+ EmpathyContactWidget *information,
+ GPtrArray *channels,
+ guint row)
+{
+ GtkWidget *w;
+ GString *label_markup = g_string_new ("");
+ guint i;
+
+ w = gtk_label_new (_("Channels:"));
+ gtk_table_attach (GTK_TABLE (information->table_details),
+ w, 0, 1, row, row + 1, GTK_FILL, 0, 0, 0);
+ gtk_misc_set_alignment (GTK_MISC (w), 0, 0.5);
+ gtk_widget_show (w);
+
+ for (i = 0; i < channels->len; i++)
+ {
+ const gchar *channel_name = g_ptr_array_index (channels, i);
+ /* We abuse the URI of the link to hold the channel name. It seems to
+ * be okay to just use it essentially verbatim, rather than trying to
+ * ensure it's actually a valid URI. g_string_append_uri_escaped()
+ * escapes way more than we actually need to; so we're just using
+ * g_markup_escape_text directly.
+ */
+ gchar *escaped = g_markup_escape_text (channel_name, -1);
+
+ if (i > 0)
+ g_string_append (label_markup, ", ");
+
+ g_string_append_printf (label_markup, "<a href='%s'>%s</a>",
+ escaped, channel_name);
+ g_free (escaped);
+ }
+
+ w = gtk_label_new (NULL);
+ gtk_label_set_markup (GTK_LABEL (w), label_markup->str);
+ gtk_label_set_line_wrap (GTK_LABEL (w), TRUE);
+ g_signal_connect (w, "activate-link",
+ (GCallback) channel_name_activated_cb, information);
+ gtk_table_attach_defaults (GTK_TABLE (information->table_details),
+ w, 1, 2, row, row + 1);
+ gtk_misc_set_alignment (GTK_MISC (w), 0, 0.5);
+ gtk_widget_show (w);
+
+ g_string_free (label_markup, TRUE);
+}
+
static guint
contact_widget_details_update_show (EmpathyContactWidget *information)
{
TpContact *contact;
GList *info, *l;
guint n_rows = 0;
+ GPtrArray *channels = g_ptr_array_new ();
contact = empathy_contact_get_tp_contact (information->contact);
info = tp_contact_get_contact_info (contact);
@@ -541,6 +657,7 @@ contact_widget_details_update_show (EmpathyContactWidget *information)
TpContactInfoField *field = l->data;
InfoFieldData *field_data;
const gchar *value;
+ gchar *markup = NULL;
GtkWidget *w;
if (field->field_value == NULL || field->field_value[0] == NULL)
@@ -548,6 +665,12 @@ contact_widget_details_update_show (EmpathyContactWidget *information)
value = field->field_value[0];
+ if (!tp_strdiff (field->field_name, "x-irc-channel"))
+ {
+ g_ptr_array_add (channels, (gpointer) field->field_value[0]);
+ continue;
+ }
+
field_data = find_info_field_data (field->field_name);
if (field_data == NULL)
{
@@ -555,6 +678,18 @@ contact_widget_details_update_show (EmpathyContactWidget *information)
continue;
}
+ if (field_data->format != NULL)
+ {
+ markup = field_data->format (field->field_value);
+
+ if (markup == NULL)
+ {
+ DEBUG ("Invalid value for field '%s' (first element was '%s')",
+ field->field_name, field->field_value[0]);
+ continue;
+ }
+ }
+
/* Add Title */
w = gtk_label_new (_(field_data->title));
gtk_table_attach (GTK_TABLE (information->table_details),
@@ -564,11 +699,8 @@ contact_widget_details_update_show (EmpathyContactWidget *information)
/* Add Value */
w = gtk_label_new (value);
- if (field_data->linkify)
+ if (markup != NULL)
{
- gchar *markup;
-
- markup = empathy_add_link_markup (value);
gtk_label_set_markup (GTK_LABEL (w), markup);
g_free (markup);
}
@@ -585,6 +717,13 @@ contact_widget_details_update_show (EmpathyContactWidget *information)
}
g_list_free (info);
+ if (channels->len > 0)
+ {
+ add_channel_list (information, channels, n_rows);
+ n_rows++;
+ }
+
+ g_ptr_array_unref (channels);
return n_rows;
}
diff --git a/libempathy-gtk/empathy-theme-adium.c b/libempathy-gtk/empathy-theme-adium.c
index 06410c528..b62b017c9 100644
--- a/libempathy-gtk/empathy-theme-adium.c
+++ b/libempathy-gtk/empathy-theme-adium.c
@@ -61,6 +61,9 @@ typedef struct {
guint pages_loading;
/* Queue of GValue* containing an EmpathyMessage or string */
GQueue message_queue;
+ /* Queue of owned gchar* of message token to remove unread
+ * marker for when we lose focus. */
+ GQueue acked_messages;
GtkWidget *inspector_window;
GSettings *gsettings_chat;
gboolean has_focus;
@@ -569,32 +572,10 @@ theme_adium_append_event_escaped (EmpathyChatView *view,
}
static void
-theme_adium_remove_focus_marks (EmpathyThemeAdium *theme)
+theme_adium_remove_focus_marks (EmpathyThemeAdium *theme,
+ WebKitDOMNodeList *nodes)
{
- EmpathyThemeAdiumPriv *priv = GET_PRIV (theme);
- WebKitDOMDocument *dom;
- WebKitDOMNodeList *nodes;
guint i;
- GError *error = NULL;
-
- if (!priv->has_unread_message)
- return;
-
- priv->has_unread_message = FALSE;
-
- dom = webkit_web_view_get_dom_document (WEBKIT_WEB_VIEW (theme));
- if (dom == NULL) {
- return;
- }
-
- /* Get all nodes with focus class */
- nodes = webkit_dom_document_query_selector_all (dom, ".focus", &error);
- if (nodes == NULL) {
- DEBUG ("Error getting focus nodes: %s",
- error ? error->message : "No error");
- g_clear_error (&error);
- return;
- }
/* Remove focus and firstFocus class */
for (i = 0; i < webkit_dom_node_list_get_length (nodes); i++) {
@@ -632,12 +613,43 @@ theme_adium_remove_focus_marks (EmpathyThemeAdium *theme)
}
static void
+theme_adium_remove_all_focus_marks (EmpathyThemeAdium *theme)
+{
+ EmpathyThemeAdiumPriv *priv = GET_PRIV (theme);
+ WebKitDOMDocument *dom;
+ WebKitDOMNodeList *nodes;
+ GError *error = NULL;
+
+ if (!priv->has_unread_message)
+ return;
+
+ priv->has_unread_message = FALSE;
+
+ dom = webkit_web_view_get_dom_document (WEBKIT_WEB_VIEW (theme));
+ if (dom == NULL) {
+ return;
+ }
+
+ /* Get all nodes with focus class */
+ nodes = webkit_dom_document_query_selector_all (dom, ".focus", &error);
+ if (nodes == NULL) {
+ DEBUG ("Error getting focus nodes: %s",
+ error ? error->message : "No error");
+ g_clear_error (&error);
+ return;
+ }
+
+ theme_adium_remove_focus_marks (theme, nodes);
+}
+
+static void
theme_adium_append_message (EmpathyChatView *view,
EmpathyMessage *msg)
{
EmpathyThemeAdium *theme = EMPATHY_THEME_ADIUM (view);
EmpathyThemeAdiumPriv *priv = GET_PRIV (theme);
EmpathyContact *sender;
+ TpMessage *tp_msg;
TpAccount *account;
gchar *body_escaped;
const gchar *body;
@@ -759,6 +771,20 @@ theme_adium_append_message (EmpathyChatView *view,
* %status% - See %status% in theme_adium_append_html ()
*/
+ /* This is slightly a hack, but it's the only way to add
+ * arbitrary data to messages in the HTML. We add another
+ * class called "x-empathy-message-id-*" to the message. This
+ * way, we can remove the unread marker for this specific
+ * message later. */
+ tp_msg = empathy_message_get_tp_message (msg);
+ if (tp_msg != NULL) {
+ gchar *tmp = tp_escape_as_identifier (
+ tp_message_get_token (tp_msg));
+ g_string_append_printf (message_classes,
+ " x-empathy-message-id-%s", tmp);
+ g_free (tmp);
+ }
+
/* Define javascript function to use */
if (consecutive) {
func = priv->allow_scrolling ? "appendNextMessage" : "appendNextMessageNoScroll";
@@ -777,7 +803,7 @@ theme_adium_append_message (EmpathyChatView *view,
}
/* remove all the unread marks when we are sending a message */
- theme_adium_remove_focus_marks (theme);
+ theme_adium_remove_all_focus_marks (theme);
} else {
/* in */
if (is_backlog) {
@@ -927,16 +953,93 @@ theme_adium_copy_clipboard (EmpathyChatView *view)
}
static void
+theme_adium_remove_mark_from_message (EmpathyThemeAdium *self,
+ const gchar *token)
+{
+ WebKitDOMDocument *dom;
+ WebKitDOMNodeList *nodes;
+ gchar *class, *tmp;
+ GError *error = NULL;
+
+ dom = webkit_web_view_get_dom_document (WEBKIT_WEB_VIEW (self));
+ if (dom == NULL) {
+ return;
+ }
+
+ tmp = tp_escape_as_identifier (token);
+ class = g_strdup_printf (".x-empathy-message-id-%s", tmp);
+ g_free (tmp);
+
+ /* Get all nodes with focus class */
+ nodes = webkit_dom_document_query_selector_all (dom, class, &error);
+ g_free (class);
+
+ if (nodes == NULL) {
+ DEBUG ("Error getting focus nodes: %s",
+ error ? error->message : "No error");
+ g_clear_error (&error);
+ return;
+ }
+
+ theme_adium_remove_focus_marks (self, nodes);
+}
+
+static void
+theme_adium_remove_acked_message_unread_mark_foreach (gpointer data,
+ gpointer user_data)
+{
+ EmpathyThemeAdium *self = user_data;
+ gchar *token = data;
+
+ theme_adium_remove_mark_from_message (self, token);
+ g_free (token);
+}
+
+static void
theme_adium_focus_toggled (EmpathyChatView *view,
gboolean has_focus)
{
- EmpathyThemeAdium *self = (EmpathyThemeAdium *) view;
EmpathyThemeAdiumPriv *priv = GET_PRIV (view);
priv->has_focus = has_focus;
if (!priv->has_focus) {
- theme_adium_remove_focus_marks (self);
+ /* We've lost focus, so let's make sure all the acked
+ * messages have lost their unread marker. */
+ g_queue_foreach (&priv->acked_messages,
+ theme_adium_remove_acked_message_unread_mark_foreach,
+ view);
+ g_queue_clear (&priv->acked_messages);
+
+ priv->has_unread_message = FALSE;
+ }
+}
+
+static void
+theme_adium_message_acknowledged (EmpathyChatView *view,
+ EmpathyMessage *message)
+{
+ EmpathyThemeAdium *self = (EmpathyThemeAdium *) view;
+ EmpathyThemeAdiumPriv *priv = GET_PRIV (view);
+ TpMessage *tp_msg;
+
+ tp_msg = empathy_message_get_tp_message (message);
+
+ if (tp_msg == NULL) {
+ return;
}
+
+ /* We only want to actually remove the unread marker if the
+ * view doesn't have focus. If we did it all the time we would
+ * never see the unread markers, ever! So, we'll queue these
+ * up, and when we lose focus, we'll remove the markers. */
+ if (priv->has_focus) {
+ g_queue_push_tail (&priv->acked_messages,
+ g_strdup (tp_message_get_token (tp_msg)));
+ return;
+ }
+
+ theme_adium_remove_mark_from_message (self,
+ tp_message_get_token (tp_msg));
}
static void
@@ -1059,6 +1162,7 @@ theme_adium_iface_init (EmpathyChatViewIface *iface)
iface->highlight = theme_adium_highlight;
iface->copy_clipboard = theme_adium_copy_clipboard;
iface->focus_toggled = theme_adium_focus_toggled;
+ iface->message_acknowledged = theme_adium_message_acknowledged;
}
static void
@@ -1124,6 +1228,11 @@ theme_adium_dispose (GObject *object)
priv->inspector_window = NULL;
}
+ if (priv->acked_messages.length > 0) {
+ g_queue_foreach (&priv->acked_messages, (GFunc) g_free, NULL);
+ g_queue_clear (&priv->acked_messages);
+ }
+
G_OBJECT_CLASS (empathy_theme_adium_parent_class)->dispose (object);
}