[polari] chatView: Track contacts associated with nicks and base status on them
- From: Florian Müllner <fmuellner src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [polari] chatView: Track contacts associated with nicks and base status on them
- Date: Fri, 10 Jun 2016 20:06:43 +0000 (UTC)
commit e697d2d3727f08b724fecb0896eaffbf84ecaf18
Author: raresv <rares visalom gmail com>
Date: Sun Jun 5 23:59:47 2016 +0300
chatView: Track contacts associated with nicks and base status on them
Until now, the status of a nickname was updated each time a status
change was observed (join, left, rename, etc.). Due to the fact that
the 'basenick' is used to identify a user tag, multiple users sharing
the same 'basenick' also share the same tag, therefore if one of
the users leaves, then both of them would be marked as offline.
To fix, keep track of the actual contacts corresponding to each
'basenick'. Users are marked as online if there is at least one
contact associated with their 'basenick', and are marked offline
otherwise.
https://bugzilla.gnome.org/show_bug.cgi?id=763868
src/chatView.js | 82 ++++++++++++++++++++++++++++++++++---------------------
1 files changed, 51 insertions(+), 31 deletions(-)
---
diff --git a/src/chatView.js b/src/chatView.js
index f9cc7b0..4be3765 100644
--- a/src/chatView.js
+++ b/src/chatView.js
@@ -376,6 +376,11 @@ const ChatView = new Lang.Class({
});
},
+ _resetNickTag: function(nickTag) {
+ nickTag._contacts = [];
+ this._updateTagStatus(nickTag);
+ },
+
_onStyleUpdated: function() {
let context = this.get_style_context();
context.save();
@@ -430,10 +435,9 @@ const ChatView = new Lang.Class({
}
});
- let offset = NICKTAG_PREFIX.length;
tagTable.foreach(Lang.bind(this, function(tag) {
- if (tag._status)
- this._setNickStatus(tag.name.substring(offset), tag._status);
+ if (tag._contacts)
+ this._updateTagStatus(tag);
}));
},
@@ -489,7 +493,6 @@ const ChatView = new Lang.Class({
messageType: pending[i].get_message_type(),
shouldHighlight: false };
this._insertMessage(iter, message, state);
- this._setNickStatus(message.nick, Tp.ConnectionPresenceType.OFFLINE);
if (!iter.is_end() || i < pending.length - 1)
this._view.buffer.insert(iter, '\n', -1);
@@ -501,13 +504,10 @@ const ChatView = new Lang.Class({
if (this._room.type == Tp.HandleType.ROOM) {
let members = this._channel.group_dup_members_contacts();
for (let j = 0; j < members.length; j++)
- this._setNickStatus(members[j].get_alias(),
- Tp.ConnectionPresenceType.AVAILABLE);
+ this._trackContact(members[j]);
} else {
- this._setNickStatus(this._channel.connection.self_contact.get_alias(),
- Tp.ConnectionPresenceType.AVAILABLE);
- this._setNickStatus(this._channel.target_contact.get_alias(),
- Tp.ConnectionPresenceType.AVAILABLE);
+ this._trackContact(this._channel.connection.self_contact);
+ this._trackContact(this._channel.target_contact);
}
},
@@ -772,17 +772,38 @@ const ChatView = new Lang.Class({
return NICKTAG_PREFIX + Polari.util_get_basenick(nick);
},
- _setNickStatus: function(nick, status) {
- let nickTag = this._lookupTag(this._getNickTagName(nick));
+ _trackContact: function(contact) {
+ let nickTag = this._lookupTag(this._getNickTagName(contact.alias));
if (!nickTag)
return;
- if (status == Tp.ConnectionPresenceType.AVAILABLE)
- nickTag.foreground_rgba = this._activeNickColor;
- else
- nickTag.foreground_rgba = this._inactiveNickColor;
+ let alreadyTracked = nickTag._contacts.some(c => c.alias == contact.alias);
+
+ if (!alreadyTracked)
+ nickTag._contacts.push(contact);
+
+ this._updateTagStatus(nickTag);
+ },
+
+ _untrackContact: function(contact) {
+ let nickTag = this._lookupTag(this._getNickTagName(contact.alias));
+ if (!nickTag)
+ return;
+
+ let indexToDelete = nickTag._contacts.map(c => c.alias).indexOf(contact.alias);
+
+ if (indexToDelete > -1) {
+ nickTag._contacts.splice(indexToDelete, 1);
+
+ this._updateTagStatus(nickTag);
+ }
+ },
- nickTag._status = status;
+ _updateTagStatus: function(tag) {
+ if (tag._contacts.length == 0)
+ tag.foreground_rgba = this._inactiveNickColor;
+ else
+ tag.foreground_rgba = this._activeNickColor;
},
_onChannelChanged: function() {
@@ -827,21 +848,18 @@ const ChatView = new Lang.Class({
if (this._room.type == Tp.HandleType.ROOM) {
let members = this._channel.group_dup_members_contacts();
for (let j = 0; j < members.length; j++)
- this._setNickStatus(members[j].get_alias(),
- Tp.ConnectionPresenceType.AVAILABLE);
+ this._trackContact(members[j]);
} else {
- this._setNickStatus(this._channel.connection.self_contact.get_alias(),
- Tp.ConnectionPresenceType.AVAILABLE);
- this._setNickStatus(this._channel.target_contact.get_alias(),
- Tp.ConnectionPresenceType.AVAILABLE);
+ this._trackContact(this._channel.connection.self_contact);
+ this._trackContact(this._channel.target_contact);
}
},
_onMemberRenamed: function(room, oldMember, newMember) {
let text = _("%s is now known as %s").format(oldMember.alias, newMember.alias);
this._insertStatus(text, oldMember.alias, 'renamed');
- this._setNickStatus(oldMember.alias, Tp.ConnectionPresenceType.OFFLINE);
- this._setNickStatus(newMember.alias, Tp.ConnectionPresenceType.AVAILABLE);
+ this._untrackContact(oldMember);
+ this._trackContact(newMember);
},
_onMemberDisconnected: function(room, member, message) {
@@ -849,7 +867,7 @@ const ChatView = new Lang.Class({
if (message)
text += ' (%s)'.format(message);
this._insertStatus(text, member.alias, 'left');
- this._setNickStatus(member.alias, Tp.ConnectionPresenceType.OFFLINE);
+ this._untrackContact(member);
},
_onMemberKicked: function(room, member, actor) {
@@ -858,7 +876,7 @@ const ChatView = new Lang.Class({
actor.alias)
: _("%s has been kicked").format(member.alias);
this._insertStatus(message, member.alias, 'left');
- this._setNickStatus(member.alias, Tp.ConnectionPresenceType.OFFLINE);
+ this._untrackContact(member);
},
_onMemberBanned: function(room, member, actor) {
@@ -867,13 +885,13 @@ const ChatView = new Lang.Class({
actor.alias)
: _("%s has been banned").format(member.alias)
this._insertStatus(message, member.alias, 'left');
- this._setNickStatus(member.alias, Tp.ConnectionPresenceType.OFFLINE);
+ this._untrackContact(member);
},
_onMemberJoined: function(room, member) {
let text = _("%s joined").format(member.alias);
this._insertStatus(text, member.alias, 'joined');
- this._setNickStatus(member.alias, Tp.ConnectionPresenceType.AVAILABLE);
+ this._trackContact(member);
},
_onMemberLeft: function(room, member, message) {
@@ -883,7 +901,7 @@ const ChatView = new Lang.Class({
text += ' (%s)'.format(message);
this._insertStatus(text, member.alias, 'left');
- this._setNickStatus(member.alias, Tp.ConnectionPresenceType.OFFLINE);
+ this._untrackContact(member);
},
_onMessageReceived: function(room, tpMessage) {
@@ -1117,7 +1135,7 @@ const ChatView = new Lang.Class({
let iter = this._view.buffer.get_end_iter();
this._insertMessage(iter, message, this._state);
- this._setNickStatus(message.nick, Tp.ConnectionPresenceType.AVAILABLE);
+ this._trackContact(tpMessage.sender);
let [id, valid] = tpMessage.get_pending_message_id();
@@ -1203,6 +1221,8 @@ const ChatView = new Lang.Class({
if (!nickTag) {
nickTag = new Gtk.TextTag({ name: nickTagName });
this._view.get_buffer().get_tag_table().add(nickTag);
+
+ this._resetNickTag(nickTag);
}
tags.push(nickTag);
if (needsGap)
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]