diff options
author | Danny van Heumen <danny@dannyvanheumen.nl> | 2014-12-18 00:28:46 +0100 |
---|---|---|
committer | Danny van Heumen <danny@dannyvanheumen.nl> | 2015-01-12 22:47:08 +0100 |
commit | db41fa2525d504ee927c203b5c2a203872a3b7cf (patch) | |
tree | e5ecde44d22a1f51900cd48be6c92b28055962b8 /src/net/java | |
parent | 1d57442c0cdf5609f96912c000ac0f4e2799e1b8 (diff) | |
download | jitsi-db41fa2525d504ee927c203b5c2a203872a3b7cf.zip jitsi-db41fa2525d504ee927c203b5c2a203872a3b7cf.tar.gz jitsi-db41fa2525d504ee927c203b5c2a203872a3b7cf.tar.bz2 |
Work-in-progress on MUC member presence.
Diffstat (limited to 'src/net/java')
11 files changed, 216 insertions, 25 deletions
diff --git a/src/net/java/sip/communicator/impl/gui/main/chat/ChatPanel.java b/src/net/java/sip/communicator/impl/gui/main/chat/ChatPanel.java index 77718d8..3d08edf 100644 --- a/src/net/java/sip/communicator/impl/gui/main/chat/ChatPanel.java +++ b/src/net/java/sip/communicator/impl/gui/main/chat/ChatPanel.java @@ -3059,17 +3059,20 @@ public class ChatPanel */ public void chatRoomPropertyChanged(ChatRoomMemberPropertyChangeEvent event) { - String message = GuiActivator.getResources().getI18NString( - "service.gui.CHAT_NICKNAME_CHANGE", - new String[]{ - (String) event.getOldValue(), - (String) event.getNewValue() - }); - this.conversationPanel - .appendMessageToEnd( + if (ChatRoomMemberPropertyChangeEvent.MEMBER_NICKNAME.equals(event + .getPropertyName())) + { + String message = + GuiActivator.getResources().getI18NString( + "service.gui.CHAT_NICKNAME_CHANGE", + new String[] + { (String) event.getOldValue(), + (String) event.getNewValue() }); + this.conversationPanel.appendMessageToEnd( "<DIV identifier=\"message\" style=\"color:#707070;\">" - + StringEscapeUtils.escapeHtml4(message) + "</DIV>", + + StringEscapeUtils.escapeHtml4(message) + "</DIV>", ChatHtmlUtils.HTML_CONTENT_TYPE); + } } /** diff --git a/src/net/java/sip/communicator/impl/gui/main/chat/conference/ChatContactCellRenderer.java b/src/net/java/sip/communicator/impl/gui/main/chat/conference/ChatContactCellRenderer.java index 936c05e..7264b6b 100644 --- a/src/net/java/sip/communicator/impl/gui/main/chat/conference/ChatContactCellRenderer.java +++ b/src/net/java/sip/communicator/impl/gui/main/chat/conference/ChatContactCellRenderer.java @@ -91,9 +91,18 @@ public class ChatContactCellRenderer if(memberRole != null) this.nameLabel.setIcon( ChatContactRoleIcon.getRoleIcon(memberRole)); - } - if (contactForegroundColor != null) + // FIXME Make solution more generic by querying color from presence + // status instance. + final int presenceStatus = member.getPresenceStatus().getStatus(); + if (presenceStatus >= PresenceStatus.AVAILABLE_THRESHOLD) { + this.nameLabel.setForeground(Color.BLACK); + } + else if (presenceStatus >= PresenceStatus.AWAY_THRESHOLD) { + this.nameLabel.setForeground(Color.GRAY); + } + } + else if (contactForegroundColor != null) this.nameLabel.setForeground(contactForegroundColor); this.setBorder(BorderFactory.createEmptyBorder(1, 5, 1, 1)); diff --git a/src/net/java/sip/communicator/impl/gui/main/contactlist/DefaultContactList.java b/src/net/java/sip/communicator/impl/gui/main/contactlist/DefaultContactList.java index 41d858b..98a0a93 100644 --- a/src/net/java/sip/communicator/impl/gui/main/contactlist/DefaultContactList.java +++ b/src/net/java/sip/communicator/impl/gui/main/contactlist/DefaultContactList.java @@ -197,6 +197,9 @@ public class DefaultContactList tip.addLine(ChatContactRoleIcon.getRoleIcon(member.getRole()), roleName); + // FIXME Needs i18n status name + PresenceStatus status = member.getPresenceStatus(); + tip.addLine(null, status.getStatusName()); } } diff --git a/src/net/java/sip/communicator/impl/msghistory/MessageHistoryServiceImpl.java b/src/net/java/sip/communicator/impl/msghistory/MessageHistoryServiceImpl.java index 1b73547..605b5db 100644 --- a/src/net/java/sip/communicator/impl/msghistory/MessageHistoryServiceImpl.java +++ b/src/net/java/sip/communicator/impl/msghistory/MessageHistoryServiceImpl.java @@ -6,8 +6,7 @@ */ package net.java.sip.communicator.impl.msghistory; -import static - net.java.sip.communicator.service.history.HistoryService.DATE_FORMAT; +import static net.java.sip.communicator.service.history.HistoryService.*; import java.beans.*; import java.io.*; @@ -24,9 +23,10 @@ import net.java.sip.communicator.service.msghistory.*; import net.java.sip.communicator.service.msghistory.event.*; import net.java.sip.communicator.service.protocol.*; import net.java.sip.communicator.service.protocol.event.*; +import net.java.sip.communicator.service.protocol.globalstatus.*; import net.java.sip.communicator.util.*; - import net.java.sip.communicator.util.account.*; + import org.jitsi.service.configuration.*; import org.osgi.framework.*; @@ -2720,6 +2720,13 @@ public class MessageHistoryServiceImpl { return; } + + @Override + public PresenceStatus getPresenceStatus() + { + // FIXME is this correct response? + return GlobalStatusEnum.ONLINE; + } } /** diff --git a/src/net/java/sip/communicator/impl/protocol/irc/ChannelManager.java b/src/net/java/sip/communicator/impl/protocol/irc/ChannelManager.java index 8ca0374..168b92c 100644 --- a/src/net/java/sip/communicator/impl/protocol/irc/ChannelManager.java +++ b/src/net/java/sip/communicator/impl/protocol/irc/ChannelManager.java @@ -451,7 +451,7 @@ public class ChannelManager final ChatRoomMemberIrcImpl member = new ChatRoomMemberIrcImpl(this.provider, chatRoom, user.getNick(), user.getIdent(), user.getHostname(), - ChatRoomMemberRole.SILENT_MEMBER); + ChatRoomMemberRole.SILENT_MEMBER, IrcStatusEnum.ONLINE); ChatRoomMemberRole role; for (final IRCUserStatus status : channel.getStatusesForUser(user)) { @@ -791,11 +791,26 @@ public class ChannelManager private static final int IRC_ERR_NOTONCHANNEL = 442; /** + * IRC reply code for WHO reply entry for an individual user. + */ + private static final int IRC_RPL_WHOREPLY = 352; + + /** + * IRC reply code for end of WHO reply list. + */ + private static final int IRC_RPL_ENDOFWHO = 315; + + /** * Chat room for which this listener is working. */ private final ChatRoomIrcImpl chatroom; /** + * Periodic task timer. + */ + private final Timer presenceTaskTimer; + + /** * Constructor. Instantiate listener for the provided chat room. * * @param chatroom the chat room @@ -808,6 +823,27 @@ public class ChannelManager throw new IllegalArgumentException("chatroom cannot be null"); } this.chatroom = chatroom; + this.presenceTaskTimer = createPeriodicPresenceWatcher(); + } + + /** + * Create periodic task for updating channel presence statuses. + */ + private Timer createPeriodicPresenceWatcher() { + final Timer presence = new Timer(); + final TimerTask task = new TimerTask() + { + @Override + public void run() + { + irc.rawMessage("WHO " + chatroom.getIdentifier()); + } + }; + // FIXME create constants + presence.schedule(task, 1000L, 60000L); + LOGGER.debug("Scheduled periodic task for querying member presence " + + "for channel " + this.chatroom.getIdentifier()); + return presence; } /** @@ -858,7 +894,7 @@ public class ChannelManager final ChatRoomMemberIrcImpl member = new ChatRoomMemberIrcImpl(ChannelManager.this.provider, this.chatroom, user, ident, host, - ChatRoomMemberRole.SILENT_MEMBER); + ChatRoomMemberRole.SILENT_MEMBER, IrcStatusEnum.ONLINE); this.chatroom.fireMemberPresenceEvent(member, null, ChatRoomMemberPresenceChangeEvent.MEMBER_JOINED, null); } @@ -951,12 +987,49 @@ public class ChannelManager } break; + case IRC_RPL_WHOREPLY: + // FIXME filter out replies not for this channel + final String[] messageComponents = msg.getText().split(" "); + final String nick = messageComponents[4]; + final ChatRoomMemberIrcImpl member = + (ChatRoomMemberIrcImpl) this.chatroom + .getChatRoomMember(nick); + if (member != null) + { + final IrcStatusEnum status = + determineStatus(messageComponents[5]); + final IrcStatusEnum previous = + member.setPresenceStatus(status); + final ChatRoomMemberPropertyChangeEvent presenceEvent = + new ChatRoomMemberPropertyChangeEvent(member, + this.chatroom, + ChatRoomMemberPropertyChangeEvent.MEMBER_PRESENCE, + previous, status); + this.chatroom.fireMemberPropertyChangeEvent(presenceEvent); + } + break; + default: break; } } /** + * Determine the presence status by the code in the IRC WHO reply. + * + * @param presenceReply presence code + * @return returns corresponding IrcStatusEnum instance + */ + private IrcStatusEnum determineStatus(final String presenceReply) + { + if (presenceReply != null && presenceReply.startsWith("G")) + { + return IrcStatusEnum.AWAY; + } + return IrcStatusEnum.ONLINE; + } + + /** * Event in case of channel kick. * * @param msg channel kick message @@ -1009,9 +1082,12 @@ public class ChannelManager @Override public void onUserQuit(final QuitMessage msg) { - String user = msg.getSource().getNick(); - super.onUserQuit(msg); - if (!localUser(user)) + final String user = msg.getSource().getNick(); + if (localUser(user)) + { + this.presenceTaskTimer.cancel(); + } + else { final ChatRoomMember member = this.chatroom.getChatRoomMember(user); @@ -1022,6 +1098,18 @@ public class ChannelManager msg.getQuitMsg()); } } + super.onUserQuit(msg); + } + + /** + * Event in case of error. Cancel running timer then do the regular + * onError stuff. + */ + @Override + public void onError(ErrorMessage msg) + { + this.presenceTaskTimer.cancel(); + super.onError(msg); } /** @@ -1071,11 +1159,12 @@ public class ChannelManager final MessageIrcImpl message = MessageIrcImpl.newMessageFromIRC(msg.getText()); + // FIXME why create a new instance? final ChatRoomMemberIrcImpl member = new ChatRoomMemberIrcImpl(ChannelManager.this.provider, this.chatroom, msg.getSource().getNick(), msg.getSource() .getIdent(), msg.getSource().getHostname(), - ChatRoomMemberRole.MEMBER); + ChatRoomMemberRole.MEMBER, IrcStatusEnum.ONLINE); this.chatroom.fireMessageReceivedEvent(message, member, new Date(), ChatRoomMessageReceivedEvent.CONVERSATION_MESSAGE_RECEIVED); } @@ -1094,10 +1183,12 @@ public class ChannelManager } String userNick = msg.getSource().getNick(); + // FIXME why create a new instance? ChatRoomMemberIrcImpl member = new ChatRoomMemberIrcImpl(ChannelManager.this.provider, this.chatroom, userNick, msg.getSource().getIdent(), msg - .getSource().getHostname(), ChatRoomMemberRole.MEMBER); + .getSource().getHostname(), ChatRoomMemberRole.MEMBER, + IrcStatusEnum.ONLINE); MessageIrcImpl message = MessageIrcImpl.newActionFromIRC(msg.getText()); this.chatroom.fireMessageReceivedEvent(message, member, new Date(), @@ -1118,10 +1209,12 @@ public class ChannelManager } final String userNick = msg.getSource().getNick(); + // FIXME why create a new instance? final ChatRoomMemberIrcImpl member = new ChatRoomMemberIrcImpl(ChannelManager.this.provider, this.chatroom, userNick, msg.getSource().getIdent(), msg - .getSource().getHostname(), ChatRoomMemberRole.MEMBER); + .getSource().getHostname(), ChatRoomMemberRole.MEMBER, + IrcStatusEnum.ONLINE); final MessageIrcImpl message = MessageIrcImpl.newNoticeFromIRC(member, msg.getText()); this.chatroom.fireMessageReceivedEvent(message, member, new Date(), @@ -1133,6 +1226,7 @@ public class ChannelManager */ private void leaveChatRoom() { + this.presenceTaskTimer.cancel(); this.irc.deleteListener(this); ChannelManager.this.joined.remove(this.chatroom.getIdentifier()); LOGGER.debug("Leaving chat room " + this.chatroom.getIdentifier() @@ -1348,7 +1442,7 @@ public class ChannelManager member = new ChatRoomMemberIrcImpl(ChannelManager.this.provider, this.chatroom, "", "", "", - ChatRoomMemberRole.ADMINISTRATOR); + ChatRoomMemberRole.ADMINISTRATOR, IrcStatusEnum.ONLINE); } else if (source instanceof IRCUser) { diff --git a/src/net/java/sip/communicator/impl/protocol/irc/ChatRoomMemberIrcImpl.java b/src/net/java/sip/communicator/impl/protocol/irc/ChatRoomMemberIrcImpl.java index 19a9472..66f9bd8 100644 --- a/src/net/java/sip/communicator/impl/protocol/irc/ChatRoomMemberIrcImpl.java +++ b/src/net/java/sip/communicator/impl/protocol/irc/ChatRoomMemberIrcImpl.java @@ -59,6 +59,11 @@ public class ChatRoomMemberIrcImpl new TreeSet<ChatRoomMemberRole>(); /** + * Member's presence status in the chat room. + */ + private IrcStatusEnum status; + + /** * Creates an instance of <tt>ChatRoomMemberIrcImpl</tt>, by specifying the * protocol provider, the corresponding chat room, where this member is * joined, the identifier of the contact (the nickname), the login, the @@ -71,12 +76,14 @@ public class ChatRoomMemberIrcImpl * @param ident ident of member * @param hostname host name of member * @param chatRoomMemberRole the role that this member has in the + * @param status current presence status * corresponding chat room */ public ChatRoomMemberIrcImpl( final ProtocolProviderServiceIrcImpl parentProvider, final ChatRoom chatRoom, final String contactID, final String ident, - final String hostname, final ChatRoomMemberRole chatRoomMemberRole) + final String hostname, final ChatRoomMemberRole chatRoomMemberRole, + final IrcStatusEnum status) { if (parentProvider == null) { @@ -110,6 +117,11 @@ public class ChatRoomMemberIrcImpl throw new IllegalArgumentException("member role cannot be null"); } this.roles.add(chatRoomMemberRole); + if (status == null) + { + throw new IllegalArgumentException("status cannot be null"); + } + this.status = status; } /** @@ -298,4 +310,27 @@ public class ChatRoomMemberIrcImpl return false; return true; } + + /** + * Return the chat room member's most recent presence status. + * + * @return returns the most recent presence status + */ + @Override + public PresenceStatus getPresenceStatus() + { + return this.status; + } + + /** + * Set a new presence status. + * + * @param status the new presence status + */ + IrcStatusEnum setPresenceStatus(final IrcStatusEnum status) + { + final IrcStatusEnum previous = this.status; + this.status = status; + return previous; + } } diff --git a/src/net/java/sip/communicator/impl/protocol/irc/OperationSetMultiUserChatIrcImpl.java b/src/net/java/sip/communicator/impl/protocol/irc/OperationSetMultiUserChatIrcImpl.java index 4ee4755..8fc7c19 100644 --- a/src/net/java/sip/communicator/impl/protocol/irc/OperationSetMultiUserChatIrcImpl.java +++ b/src/net/java/sip/communicator/impl/protocol/irc/OperationSetMultiUserChatIrcImpl.java @@ -362,7 +362,7 @@ public class OperationSetMultiUserChatIrcImpl return new ChatRoomMemberIrcImpl(ircProvider, serverChatRoom, ircProvider.getAccountID().getService(), "", ircProvider .getAccountID().getServerAddress(), - ChatRoomMemberRole.GUEST); + ChatRoomMemberRole.GUEST, IrcStatusEnum.ONLINE); } } diff --git a/src/net/java/sip/communicator/impl/protocol/jabber/ChatRoomMemberJabberImpl.java b/src/net/java/sip/communicator/impl/protocol/jabber/ChatRoomMemberJabberImpl.java index 22916c5..ca91a4d 100644 --- a/src/net/java/sip/communicator/impl/protocol/jabber/ChatRoomMemberJabberImpl.java +++ b/src/net/java/sip/communicator/impl/protocol/jabber/ChatRoomMemberJabberImpl.java @@ -8,6 +8,7 @@ package net.java.sip.communicator.impl.protocol.jabber; import net.java.sip.communicator.service.protocol.*; import net.java.sip.communicator.service.protocol.jabber.*; +import net.java.sip.communicator.service.protocol.jabberconstants.*; import org.jivesoftware.smack.util.*; import org.jivesoftware.smackx.muc.*; @@ -250,4 +251,17 @@ public class ChatRoomMemberJabberImpl { this.contact = contact; } + + /** + * Current presence status of chat room member. + * + * @return returns current presence status + */ + @Override + public PresenceStatus getPresenceStatus() + { + // FIXME implement accurate status for chat room member + return ((ProtocolProviderServiceJabberImpl) getProtocolProvider()) + .getJabberStatusEnum().getStatus(JabberStatusEnum.AVAILABLE); + } } diff --git a/src/net/java/sip/communicator/impl/protocol/mock/MockChatRoomMember.java b/src/net/java/sip/communicator/impl/protocol/mock/MockChatRoomMember.java index cba9dbe..4c45603 100644 --- a/src/net/java/sip/communicator/impl/protocol/mock/MockChatRoomMember.java +++ b/src/net/java/sip/communicator/impl/protocol/mock/MockChatRoomMember.java @@ -134,4 +134,14 @@ public class MockChatRoomMember { return contact; } + + /** + * Returns status for fully available mock chat room member. + */ + @Override + public PresenceStatus getPresenceStatus() + { + // mock fully available + return MockStatusEnum.MOCK_STATUS_100; + } } diff --git a/src/net/java/sip/communicator/service/protocol/ChatRoomMember.java b/src/net/java/sip/communicator/service/protocol/ChatRoomMember.java index 82fac37..991f4be 100644 --- a/src/net/java/sip/communicator/service/protocol/ChatRoomMember.java +++ b/src/net/java/sip/communicator/service/protocol/ChatRoomMember.java @@ -89,4 +89,15 @@ public interface ChatRoomMember * to set for this member in its containing chat room. */ public void setRole(ChatRoomMemberRole role); + + /** + * Returns the status of the chat room member as per the last status update + * we've received for it. Note that this method is not to perform any + * network operations and will simply return the status received in the last + * status update message. + * + * @return the PresenceStatus that we've received in the last status update + * pertaining to this contact. + */ + public PresenceStatus getPresenceStatus(); } diff --git a/src/net/java/sip/communicator/service/protocol/event/ChatRoomMemberPropertyChangeEvent.java b/src/net/java/sip/communicator/service/protocol/event/ChatRoomMemberPropertyChangeEvent.java index f42924d..456ec44 100644 --- a/src/net/java/sip/communicator/service/protocol/event/ChatRoomMemberPropertyChangeEvent.java +++ b/src/net/java/sip/communicator/service/protocol/event/ChatRoomMemberPropertyChangeEvent.java @@ -31,6 +31,11 @@ public class ChatRoomMemberPropertyChangeEvent public static final String MEMBER_NICKNAME = "MemberNickname"; /** + * The presence status of the <tt>ChatRoomMember</tt> property. + */ + public static final String MEMBER_PRESENCE = "MemberPresence"; + + /** * The <tt>ChatRoom</tt>, to which the corresponding member belongs. */ private ChatRoom memberChatRoom; |