XMPP aSmack - 如何获取当前用户状态(离线/在线/离开等)?

18

我是新手,在安卓中使用xmpp/asmack。

请问有人可以帮我获取用户好友的在线状态吗(花名册列表)?

我正在使用以下代码:

Presence availability = roster.getPresence(user);
Mode userMode = availability.getMode();

我还需要做什么来获取我的花名册中每个用户的可用状态?

5个回答

19

就像这样使用:

Presence availability = roster.getPresence(user);
Mode userMode = availability.getMode();

retrieveState_mode(availability.getMode(),availability.isAvailable());

public static int retrieveState_mode(Mode userMode, boolean isOnline) {
        int userState = 0;
        /** 0 for offline, 1 for online, 2 for away,3 for busy*/
        if(userMode == Mode.dnd) {
            userState = 3;
        } else if (userMode == Mode.away || userMode == Mode.xa) {   
            userState = 2;
        } else if (isOnline) {
            userState = 1;
        }
        return userState;
}

如果您在xmpp/asmack方面遇到任何问题,请告诉我。


1
我尝试了这段代码,但每次都得到0(离线),即使用户状态在线!请给我建议。 - Rahul Upadhyay
嗨@samsad,我无法获取用户的在线状态,我们需要启用任何设置吗?? - KK_07k11A0585
1
@KK_07k11A0585请分享你的代码片段并解释你遇到了什么错误,那我可以帮助你。 - Gaurav Arora
2
嗨@GauravArora,请看一下这个http://pastebin.com/j113RzV6 我总是得到用户模式为0。如果我漏掉了什么,请告诉我。 - KK_07k11A0585
嗨@GauravArora,我也使用相同的代码,但我总是得到false,但在服务器上用户在线但无法获得正确的结果。不知道为什么。 - Navjot.jassal
显示剩余3条评论

4
用法如下:
userFromServer = con.getRoster().getPresence(userID);
userState = retrieveState(userFromServer.getMode(), userFromServer.isAvailable());

public int retrieveState(Mode userMode, boolean isOnline) {
    int userState = XmppFriend.OFFLINE; // default return value
    if (userMode == Mode.dnd) {
        userState = XmppFriend.BUSY;
    } else if (userMode == Mode.away || userMode == Mode.xa) {
        userState = XmppFriend.AWAY;
    } else if (isOnline) {
        userState = XmppFriend.ONLINE;
    }
    return userState;
}

1
        roster.addRosterListener(new RosterListener() {

        public void entriesAdded(Collection<String> param) {}

        public void entriesDeleted(Collection<String> addresses) {
        }
        public void entriesUpdated(Collection<String> addresses) {  
        }
        public void presenceChanged(Presence presence) {

            String user = presence.getFrom();
            Presence bestPresence = roster.getPresence(user);

            Log.d(TAG, "BestPresence: " + user + ": " + bestPresence);

            String[] temp = presence.getFrom().split("\\@");
            Log.d(TAG, "Presence: " + temp[0] + "-" + presence.toString());

            String status = presence.toString();
            // ShowInfoDialog(temp[0]+"is "+status);

            for (int i = 0; i < friendslist.size(); i++) {

                if (temp[0].equalsIgnoreCase(friendslist.get(i).getName())) {

                    friendslist.get(i).setStatus(status);
                    Log.d(TAG, "kilepet/belepet " + friendslist.get(i).getName() + " - " + friendslist.get(i).getStatus());

                    // ShowInfoDialog(friendslist.get(i).getName()+"is "+status);
                    Log.d(TAG, "WATERFAK");

                }
            }

        }

如果您使用RosterListener,它会实时更新出席状态,对我来说很有效。

你能解释一下你代码中的friendslist类型吗? - Amarnath Baitha
实体Friend包含了另一个用户可能拥有的所有数据(如姓名、电子邮件、状态、头像等),当我请求app启动后的名单时,我会填充列表,并使用第三方服务器来弥补ejjaberd的不足。 - cesztoszule
嗨@cesztoszule..我正在使用上面的方法来检测我的名册是否存在..但是更改状态的方法调用了7-8次,我想知道为什么会这样。 <presence id="NAR9p-198" from="xxxxxxxx@domainim/domain/86xxxxxxxxx5198" type="unavailable"></presence><presence id="NAR9p-199" from="xxxxxxxx@domainim/domain/86xxxxxxxxx5198" type="unavailable"></presence><presence id="NAR9p-200" from="xxxxxxxx@domainim/domain/86xxxxxxxxx5198" type="unavailable"></presence><presence id="NAR9p-201" from="xxxxxxxx@domainim/domain/86xxxxxxxxx5198" type="unavailable"></pres> - shyam.y

0

根据我的经验,在查看用户状态和其他信息之前,您需要订阅该用户的“Presence”。

例如: 用户A想要查看用户B的状态和可用状态, 在这种情况下,用户A需要订阅用户B。之后,用户A就可以看到用户B的“Presence”了。

订阅代码

try {
            roster.setDefaultSubscriptionMode(Roster.SubscriptionMode.manual);
            String userName = responders.getUsers().get(i).getUsername();
            roster.createEntry("userB@domain", userName, null);
            Presence pres = new Presence(Presence.Type.subscribe);
            pres.setFrom("userA@domain");
            connection.sendStanza(pres);
        } catch (Exception e) {
            android.util.Log.e("tag", "unable to add contact: ", e);
        }

0
ConnectToServer(){
    final ProgressDialog dialog = ProgressDialog.show(ChatWindowFragmentActivity.this,
            "Connecting...", "Please wait...", false);
    Thread t = new Thread(new Runnable() {
        @Override
        public void run() {


            // Object of XmppClient class
            XmppClient mXmppClient = new XmppClient();

            /*
             * // Create a connection ConnectionConfiguration connConfig =
             * new ConnectionConfiguration(HOST, PORT);
             */
            XMPPConnection connection = null;

            try {
                SmackAndroid.init(ChatWindowFragmentActivity.this);
                connection = mXmppClient.connectionToXmppServer();
            } catch (XMPPException e) {
                // TODO Auto-generated catch block
      //                    setConnection(null, null);
            }
            try {
                mXmppClient.loginUser(connection, USERNAME, PASSWORD);
                Log.i("XMPPChatDemoActivity",
                        "Logged in as" + connection.getUser());
                // Set the status to available
                Presence presence = new Presence(Presence.Type.available);
                connection.sendPacket(presence);

                setConnection(connection);

                Roster roster = connection.getRoster();

                 /*
                Fetch USER availability
                */


                switch (isUserAvailable(connection)){
                    case 0:
                        imgAvailability.setBackgroundColor(Color.GRAY);
                        break;
                    case 1:
                        imgAvailability.setBackgroundColor(Color.GREEN);
                        break;
                    case 2:
                        imgAvailability.setBackgroundColor(Color.YELLOW);
                        break;
                    case 3:
                        imgAvailability.setBackgroundColor(Color.RED);
                        break;
                    default:
                        break;
                }


                Collection<RosterEntry> entries = roster.getEntries();
                for (RosterEntry entry : entries) {

                    Log.d("XMPPChatDemoActivity",
                            "--------------------------------------");
                    Log.d("XMPPChatDemoActivity", "RosterEntry " + entry);
                    Log.d("XMPPChatDemoActivity",
                            "User: " + entry.getUser());
                    Log.d("XMPPChatDemoActivity",
                            "Name: " + entry.getName());
                    Log.d("XMPPChatDemoActivity",
                            "Status: " + entry.getStatus());
                    Log.d("XMPPChatDemoActivity",
                            "Type: " + entry.getType());
                    Presence entryPresence = roster.getPresence(entry
                            .getUser());

                    Log.d("XMPPChatDemoActivity", "Presence Status: "
                            + entryPresence.getStatus());
                    Log.d("XMPPChatDemoActivity", "Presence Type: "
                            + entryPresence.getType());

                    Presence.Type type = entryPresence.getType();
                    if (type == Presence.Type.available)
                        Log.d("XMPPChatDemoActivity", "Presence AVAILABLE");
                    Log.d("XMPPChatDemoActivity", "Presence : "
                            + entryPresence);
                }



            } catch (XMPPException e) {

                e.printStackTrace();
                Log.e("XMPPChatDemoActivity", "Failed to log in as "
                        + USERNAME);
                Log.e("XMPPChatDemoActivity", e.toString());
                new ShowAlert(ChatWindowFragmentActivity.this,e.getMessage(), false).show(
                        getSupportFragmentManager(), TAG);
   //                    setConnection(null, null);
            }

            dialog.dismiss();
        }
    });
    t.start();
    dialog.show();
}

以及在其中调用的方法。


我得到了Presence.Mode用户模式“null”,布尔值isOnline为“false”。 - Rahul Upadhyay
嗨@Rahul Upadhyay,我也遇到了同样的问题,我使用了Gaurav Arora建议的解决方案,但对我没有用。你找到了任何替代解决方案吗? - KK_07k11A0585
@KK_07k11A0585 没有,我没有找到任何东西。 - Rahul Upadhyay
@Crazy,我还没有找到任何东西。从那天起就没有再处理它了。:( 对于这个问题的一个建议是使用GCM,它包含了xmpp,所以使用它很好。http://developer.android.com/google/gcm/ccs.html - Rahul Upadhyay

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