如何在smackx中得知当有人加入或离开多用户聊天室时,房间的占用者是谁?

4
我正在尝试使用smackx api实现多用户聊天(MultiUserChat)。
到目前为止,我已经成功创建了一个新的聊天室、加入了聊天室并发送了邀请。但是我的问题是,如果有人加入或离开聊天室,我该如何找出谁在聊天室里。我认为可以将一个存在监听器(presence listener)添加到聊天室中来解决这个问题。
muc.addParticipantListener(new PacketListener() {

    @Override
    public void processPacket(Packet packet) {
        System.out.println("user count changed, now:" + muc.getOccupcantsCount());
    }
});

addParticipantListener的Javadoc描述如下:

添加一个数据包监听器,该监听器将在发送到群聊的任何新出席报文时得到通知。使用侦听器是一种适当的方式,可以了解由于任何更改而应重新加载占用者列表的时间。

所以我认为这会起作用。但是,在processPacket方法内部,muc.getOccupantsCount()以及muc.getOccupants()都返回processPacket调用之前的值。 因此,如果聊天室中只有一个用户并且另一个用户加入,输出将为:

用户计数已更改,现在:1

如果有两个用户并且另一个用户加入,则输出为:

用户计数已更改,现在:2

如果有三个用户并且其中一个离开,则输出为:

用户计数已更改,现在:3

同样,当在processPacket内部调用时,muc.getOccupants()不会给我刚刚加入的用户,并仍然给我刚刚离开的用户。

如何有效地从processPacket方法内部找出当前谁在聊天室中?


我有一个问题,如果没有房间名称,我们如何添加邀请监听器(如何初始化MultiuserChat)? - Jashan PJ
3个回答

3
你无法在PacketListenermuc.getOccupantsCount()中执行此操作。
使用smackx中的PacketListener也可以确定占用者计数。但不能保证这个PacketListener在你的监听器之前运行,并因此有机会更新占用者计数。
目前解决问题的一种方法是检查出席数据包并与当前成员列表进行交叉检查,基本上与内置出席监听器执行相同的操作。或者您可以人为延迟操作,以便所有PacketListeners都有机会完成。
我已创建SMACK-424来跟踪Smack中的此问题。

1
谢谢您澄清这一点。作为解决方法,我现在使用((Presence) packet).isAvailable()来检查PacketListener中用户状态,并相应地更新内部用户名集合。 - Haf

0

针对您的新问题,即如果没有房间名称如何初始化MultiuserChat,我找到了MultiUserChat的源代码,并且只声明了一个构造函数:

 public MultiUserChat(Connection connection, String room) {
        this.connection = connection;
        this.room = room.toLowerCase();
        init();
    }

0

这是一个很好的问题,并且需要找出这些方法(例如getOccupants(),getOccupantsCount())在实际效果中存在的缺陷。

正如您所看到的,关键问题在于PacketListeners无法及时响应。因此,您需要检测用户状态活动。使用Presence来检测用户状态是确保及时更新用户信息的有效方法。此外,可能存在其他实现方法。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接