]> git.0d.be Git - empathy.git/blobdiff - libempathy-gtk/empathy-chat.c
coding style fixes
[empathy.git] / libempathy-gtk / empathy-chat.c
index ea46e6b768e2c215088dc3087269a9d623bfa533..d273a3792536b161095434f2e5c31d7f4a052478 100644 (file)
@@ -73,6 +73,7 @@ struct _EmpathyChatPriv {
        gchar             *id;
        gchar             *name;
        gchar             *subject;
+       EmpathyContact    *self_contact;
        EmpathyContact    *remote_contact;
        gboolean           show_contacts;
 
@@ -155,6 +156,14 @@ struct _EmpathyChatPriv {
         * the keyboard or the mouse. We can't ask GTK for the most recent
         * event, because it will be a notify event. Instead we track it here */
        GdkEventType       most_recent_event_type;
+
+       /* A regex matching our own current nickname in the room, or %NULL if
+        * !empathy_chat_is_room (). */
+       GRegex            *highlight_regex;
+
+       /* TRUE if empathy_chat_is_room () and there are unread highlighted messages.
+        * Cleared by empathy_chat_messages_read (). */
+       gboolean           highlighted;
 };
 
 typedef struct {
@@ -368,11 +377,18 @@ static gboolean
 chat_composing_stop_timeout_cb (EmpathyChat *chat)
 {
        EmpathyChatPriv *priv;
+       gboolean send_chat_states;
 
        priv = GET_PRIV (chat);
 
        priv->composing_stop_timeout_id = 0;
-       set_chat_state (chat, TP_CHANNEL_CHAT_STATE_PAUSED);
+       send_chat_states = g_settings_get_boolean (priv->gsettings_chat,
+                                        EMPATHY_PREFS_CHAT_SEND_CHAT_STATES);
+       if (!send_chat_states) {
+               set_chat_state (chat, TP_CHANNEL_CHAT_STATE_ACTIVE);
+       } else {
+               set_chat_state (chat, TP_CHANNEL_CHAT_STATE_PAUSED);
+       }
 
        return FALSE;
 }
@@ -381,9 +397,16 @@ static void
 chat_composing_start (EmpathyChat *chat)
 {
        EmpathyChatPriv *priv;
+       gboolean send_chat_states;
 
        priv = GET_PRIV (chat);
 
+       send_chat_states = g_settings_get_boolean (priv->gsettings_chat,
+                                         EMPATHY_PREFS_CHAT_SEND_CHAT_STATES);
+       if (!send_chat_states) {
+               return;
+       }
+
        if (priv->composing_stop_timeout_id) {
                /* Just restart the timeout */
                chat_composing_remove_timeout (chat);
@@ -896,14 +919,12 @@ chat_command_me (EmpathyChat *chat,
        if (!tp_text_channel_supports_message_type (channel,
                        TP_CHANNEL_TEXT_MESSAGE_TYPE_ACTION)) {
                /* Action message are not supported, 'simulate' the action */
-               EmpathyContact *self_contact;
                gchar *tmp;
 
-               self_contact = empathy_tp_chat_get_self_contact (priv->tp_chat);
                /* The TpChat can't be ready if it doesn't have the self contact */
-               g_assert (self_contact != NULL);
+               g_assert (priv->self_contact != NULL);
 
-               tmp = g_strdup_printf ("%s %s", empathy_contact_get_alias (self_contact),
+               tmp = g_strdup_printf ("%s %s", empathy_contact_get_alias (priv->self_contact),
                        strv[1]);
                message = tp_client_message_new_text (TP_CHANNEL_TEXT_MESSAGE_TYPE_NORMAL,
                        tmp);
@@ -1408,30 +1429,44 @@ get_highlight_regex_for (const gchar *name)
        return regex;
 }
 
+/* Called when priv->self_contact changes, or priv->self_contact:alias changes.
+ * Only connected if empathy_chat_is_room() is TRUE, for obvious-ish reasons.
+ */
+static void
+chat_self_contact_alias_changed_cb (EmpathyChat *chat)
+{
+       EmpathyChatPriv *priv = GET_PRIV (chat);
+
+       tp_clear_pointer (&priv->highlight_regex, g_regex_unref);
+
+       if (priv->self_contact != NULL) {
+               const gchar *alias = empathy_contact_get_alias (priv->self_contact);
+
+               g_return_if_fail (alias != NULL);
+               priv->highlight_regex = get_highlight_regex_for (alias);
+       }
+}
+
 static gboolean
 chat_should_highlight (EmpathyChat *chat,
        EmpathyMessage *message)
 {
-       EmpathyContact *contact;
-       const gchar   *msg, *to;
-       gboolean       ret_val = FALSE;
+       EmpathyChatPriv *priv = GET_PRIV (chat);
+       const gchar   *msg;
        TpChannelTextMessageFlags flags;
-       GRegex *regex;
 
        g_return_val_if_fail (EMPATHY_IS_MESSAGE (message), FALSE);
 
-       msg = empathy_message_get_body (message);
-       if (!msg) {
+       if (!empathy_chat_is_room (chat)) {
                return FALSE;
        }
 
-       contact = empathy_tp_chat_get_self_contact (chat->priv->tp_chat);
-       if (!contact) {
+       if (!empathy_message_is_incoming (message)) {
                return FALSE;
        }
 
-       to = empathy_contact_get_alias (contact);
-       if (!to) {
+       msg = empathy_message_get_body (message);
+       if (!msg) {
                return FALSE;
        }
 
@@ -1442,13 +1477,11 @@ chat_should_highlight (EmpathyChat *chat,
                return FALSE;
        }
 
-       regex = get_highlight_regex_for (to);
-       if (regex != NULL) {
-               ret_val = g_regex_match (regex, msg, 0, NULL);
-               g_regex_unref (regex);
+       if (priv->highlight_regex == NULL) {
+               return FALSE;
        }
 
-       return ret_val;
+       return g_regex_match (priv->highlight_regex, msg, 0, NULL);
 }
 
 static void
@@ -1469,6 +1502,11 @@ chat_message_received (EmpathyChat *chat,
                empathy_chat_view_edit_message (chat->view, message);
        } else {
                gboolean should_highlight = chat_should_highlight (chat, message);
+
+               if (should_highlight) {
+                       priv->highlighted = TRUE;
+               }
+
                DEBUG ("Appending new message '%s' from %s (%d)",
                        empathy_message_get_token (message),
                        empathy_contact_get_alias (sender),
@@ -1674,15 +1712,26 @@ chat_subject_changed_cb (EmpathyChat *chat)
                        gtk_widget_show (priv->hbox_topic);
                }
                if (priv->block_events_timeout_id == 0) {
-                       gchar *str;
+                       gchar *str = NULL;
 
                        if (!EMP_STR_EMPTY (priv->subject)) {
-                               str = g_strdup_printf (_("Topic set to: %s"), priv->subject);
-                       } else {
+                               const gchar *actor = empathy_tp_chat_get_subject_actor (priv->tp_chat);
+
+                               if (tp_str_empty (actor)) {
+                                       str = g_strdup_printf (_("Topic set to: %s"), priv->subject);
+                               } else {
+                                       str = g_strdup_printf (_("Topic set by %s to: %s"),
+                                                              actor, priv->subject);
+                               }
+                       } else if (empathy_tp_chat_supports_subject (priv->tp_chat)) {
+                               /* No need to display this 'event' is no topic can be defined anyway */
                                str = g_strdup (_("No topic defined"));
                        }
-                       empathy_chat_view_append_event (EMPATHY_CHAT (chat)->view, str);
-                       g_free (str);
+
+                       if (str != NULL) {
+                               empathy_chat_view_append_event (EMPATHY_CHAT (chat)->view, str);
+                               g_free (str);
+                       }
                }
 }
 
@@ -2867,6 +2916,32 @@ empathy_chat_set_show_contacts (EmpathyChat *chat,
        g_object_notify (G_OBJECT (chat), "show-contacts");
 }
 
+static void
+chat_self_contact_changed_cb (EmpathyChat *chat)
+{
+       EmpathyChatPriv *priv = GET_PRIV (chat);
+
+       if (priv->self_contact != NULL) {
+               g_signal_handlers_disconnect_by_func (priv->self_contact,
+                                                     chat_self_contact_alias_changed_cb,
+                                                     chat);
+       }
+       g_clear_object (&priv->self_contact);
+
+       priv->self_contact = empathy_tp_chat_get_self_contact (priv->tp_chat);
+       if (priv->self_contact != NULL) {
+               g_object_ref (priv->self_contact);
+
+               if (empathy_chat_is_room (chat)) {
+                       g_signal_connect_swapped (priv->self_contact, "notify::alias",
+                                         G_CALLBACK (chat_self_contact_alias_changed_cb),
+                                         chat);
+               }
+       }
+
+       chat_self_contact_alias_changed_cb (chat);
+}
+
 static void
 chat_remote_contact_changed_cb (EmpathyChat *chat)
 {
@@ -3221,6 +3296,8 @@ chat_finalize (GObject *object)
                        chat_state_changed_cb, chat);
                g_signal_handlers_disconnect_by_func (priv->tp_chat,
                        chat_members_changed_cb, chat);
+               g_signal_handlers_disconnect_by_func (priv->tp_chat,
+                       chat_self_contact_changed_cb, chat);
                g_signal_handlers_disconnect_by_func (priv->tp_chat,
                        chat_remote_contact_changed_cb, chat);
                g_signal_handlers_disconnect_by_func (priv->tp_chat,
@@ -3233,6 +3310,12 @@ chat_finalize (GObject *object)
        if (priv->account) {
                g_object_unref (priv->account);
        }
+       if (priv->self_contact) {
+               g_signal_handlers_disconnect_by_func (priv->self_contact,
+                                                     chat_self_contact_alias_changed_cb,
+                                                     chat);
+               g_object_unref (priv->self_contact);
+       }
        if (priv->remote_contact) {
                g_object_unref (priv->remote_contact);
        }
@@ -3246,6 +3329,8 @@ chat_finalize (GObject *object)
        g_free (priv->subject);
        g_completion_free (priv->completion);
 
+       tp_clear_pointer (&priv->highlight_regex, g_regex_unref);
+
        G_OBJECT_CLASS (empathy_chat_parent_class)->finalize (object);
 }
 
@@ -3950,6 +4035,9 @@ empathy_chat_set_tp_chat (EmpathyChat   *chat,
        g_signal_connect (tp_chat, "member-renamed",
                          G_CALLBACK (chat_member_renamed_cb),
                          chat);
+       g_signal_connect_swapped (tp_chat, "notify::self-contact",
+                                 G_CALLBACK (chat_self_contact_changed_cb),
+                                 chat);
        g_signal_connect_swapped (tp_chat, "notify::remote-contact",
                                  G_CALLBACK (chat_remote_contact_changed_cb),
                                  chat);
@@ -3971,6 +4059,7 @@ empathy_chat_set_tp_chat (EmpathyChat   *chat,
 
        /* Get initial value of properties */
        chat_sms_channel_changed_cb (chat);
+       chat_self_contact_changed_cb (chat);
        chat_remote_contact_changed_cb (chat);
        chat_title_changed_cb (chat);
        chat_subject_changed_cb (chat);
@@ -4080,7 +4169,8 @@ empathy_chat_get_contact_menu (EmpathyChat *chat)
        if (contact == NULL)
                return NULL;
 
-       individual = empathy_create_individual_from_tp_contact (contact);
+       individual = empathy_ensure_individual_from_tp_contact (contact);
+
        if (individual == NULL)
                return NULL;
 
@@ -4242,6 +4332,16 @@ empathy_chat_is_room (EmpathyChat *chat)
        return (priv->handle_type == TP_HANDLE_TYPE_ROOM);
 }
 
+gboolean
+empathy_chat_is_highlighted (EmpathyChat *chat)
+{
+       EmpathyChatPriv *priv = GET_PRIV (chat);
+
+       g_return_val_if_fail (EMPATHY_IS_CHAT (chat), FALSE);
+
+       return priv->highlighted;
+}
+
 guint
 empathy_chat_get_nb_unread_messages (EmpathyChat *self)
 {
@@ -4270,6 +4370,8 @@ empathy_chat_messages_read (EmpathyChat *self)
                        TP_TEXT_CHANNEL (priv->tp_chat), NULL, NULL);
        }
 
+       priv->highlighted = FALSE;
+
        if (priv->unread_messages_when_offline > 0) {
                /* We can't ack those as the connection has gone away so just consider
                * them as read. */