9

I am developing chat application by using Openfire XMPP server. I can text chat between two user. But i want to know Typing status when some one is typing message. So i created a class :-

public class typingStatus implements ChatStateListener {

    @Override
    public void processMessage(Chat arg0, Message arg1) {
        // TODO Auto-generated method stub

    }

    @Override
    public void stateChanged(Chat arg0, ChatState arg1) {
        // TODO Auto-generated method stub
        System.out.println(arg0.getParticipant() + " is " + arg1.name());

    }

}

But i am confuse so that How will it work? I know that i need a packet where i can it in Listener. But i am unable to find that packet.

Please any one suggest, How will it work?

and also what is difference between Smack and asmack?

Thank you!

user2160008
  • 379
  • 2
  • 5
  • 20
  • Kindly check this question in Stackoverflow : http://stackoverflow.com/questions/21154833/how-to-get-typing-status-notification-in-xmpp – Aneez Jan 21 '14 at 10:03

8 Answers8

12

To enable ChatStateListener you need to create a custom MessageListener Class

public class MessageListenerImpl implements MessageListener,ChatStateListener  {

    @Override
    public void processMessage(Chat arg0, Message arg1) {
        System.out.println("Received message: " + arg1);

    }

    @Override
    public void stateChanged(Chat arg0, ChatState arg1) {
        if (ChatState.composing.equals(arg1)) {
            Log.d("Chat State",arg0.getParticipant() + " is typing..");
        } else if (ChatState.gone.equals(arg1)) {
            Log.d("Chat State",arg0.getParticipant() + " has left the conversation.");
        } else {
            Log.d("Chat State",arg0.getParticipant() + ": " + arg1.name());
        }

    }

}

Then you create MessageListener object

MessageListener messageListener = new MessageListenerImpl();

And then pass this in the create chat method

Chat newChat = chatmanager.createChat(jabber_id_of_friend, messageListener);

what is difference between Smack and asmack? <-- Check This

Community
  • 1
  • 1
Sunil Mishra
  • 3,796
  • 1
  • 27
  • 40
  • Thank you sunil. looking good and gave me solution. I will check. – user2160008 Aug 26 '13 at 05:57
  • no userID is the jid of the other participant, not the one who logged in – Sunil Mishra Aug 26 '13 at 06:23
  • thank you sunil. if you have a bit time. please check also http://stackoverflow.com/questions/18437329/how-to-know-message-send-status-not-send-delivery-read-like-as-whatsapp?noredirect=1#comment27090174_18437329 – user2160008 Aug 26 '13 at 06:30
  • To handle message events look at this http://www.igniterealtime.org/builds/smack/docs/latest/documentation/extensions/messageevents.html – Sunil Mishra Aug 26 '13 at 08:29
  • i checked but did not get stateChanged. plz suggest – user2160008 Aug 26 '13 at 15:58
  • please check, It is not working ,i am still unable to get typing status . – user2160008 Aug 27 '13 at 06:12
  • are you sending composing status from the other end? – Sunil Mishra Aug 27 '13 at 06:28
  • sry, i am just using this code. i think, i should use focusonEditText and when user will typing, it will send a composing status. do you have any example ? – user2160008 Aug 27 '13 at 06:34
  • let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/36299/discussion-between-sunil-mishra-and-user2160008) – Sunil Mishra Aug 27 '13 at 06:39
  • @SunilMishra getting error on Chat newChat = chatmanager.createChat(jabber_id_of_friend, messageListener);..can u please explain this line? It shows red line with error `Cannot make a static reference to the non-static method createChat(String, MessageListener) from the type ChatManager` – Bhoomika Brahmbhatt Oct 23 '13 at 10:26
  • @geet createChat is not a static method, you need an instance of ChatManager to invoke that method – Sunil Mishra Jan 02 '14 at 14:26
  • It did not work on openfire. type notification need XEP-0085: Chat State Notifications, BUT THE OPENFIRE DOSE NOT HAVE THIS XEP. Any other suggestion except changing openfire? – majid mobini Nov 24 '15 at 06:18
  • Its not working any other solution to get user status..? – Er.Nancy Thakkar Mar 01 '18 at 07:46
4

finally I got the solution. I need to use chat listener along with chat manager and also I need to use in built sendcomposingnotification function. No need to use Messageeventrequestlistener interface or any other custom class for this. I added the following lines,,

connection.getChatManager().addChatListener(new ChatManagerListener() {

            @Override
            public void chatCreated(final Chat arg0, final boolean arg1) {
                // TODO Auto-generated method stub

                arg0.addMessageListener(new MessageListener()
                {

                    @Override
                    public void processMessage(Chat arg0, Message arg1) 
                    {
                        // TODO Auto-generated method stub

                        Log.d("TYpe Stat",title[0] + " is typing......");
                        Toast.makeText(getApplicationContext(),title[0] + " is typing......",Toast.LENGTH_SHORT).show();
                    }



                    }
                }); 
            }
        });

and also need to send notification like this..

mem.sendComposingNotification(etRecipient.getText().toString(), message.getPacketID());
        System.out.println("Sending notification");

where mem is type of MessageEventManger. Ref: http://www.igniterealtime.org/builds/smack/docs/latest/javadoc/org/jivesoftware/smackx/MessageEventManager.html

Aneez
  • 205
  • 3
  • 12
  • hi i tried above..but not working! here is my code! any help will be appreciated....... Message msg1 = new Message(to, Message.Type.chat); msg1.setFrom("user1@192.168.0.98"); // my id MessageEventManager event=new MessageEventManager(connection); //recipient id event.sendComposingNotification("tech1@192.168.0.98",msg1.getPacketId()); – Mohit Sep 10 '14 at 12:41
  • @Aneez, you need to process the message received in the ````processMessage()```` , because it receives all the incoming packets, not only the ````typing```` status. It might be paused, offline/online status packets, or messages.. so try to process it and then handle.. – Kamalakannan J Dec 30 '15 at 07:07
  • Hi. I tried the same but it did'nt work for me..it neither sendComposingNotification nor receiving it. gives me null at receiving and while received it from ios. Help me to find out this. Thank you. – Kutbi Jan 09 '16 at 12:25
  • FYI: merged from http://stackoverflow.com/questions/21154833/how-to-get-typing-status-notification-in-xmpp – Shog9 Oct 08 '16 at 03:57
2
ChatManager chatManager = ChatManager.getInstanceFor(connection);
Chat chat= chatManager.createChat(to, new ChatStateListener() {
      @Override
      public void stateChanged(Chat chat, ChatState state) {
                switch (state){
                        case active:
                             Log.d("state","active");
                             break;
                        case composing:
                             Log.d("state","composing");
                             break;
                        case paused:
                             Log.d("state","paused");
                             break;
                        case inactive:
                             Log.d("state","inactive");
                             break;
                        case gone:
                             Log.d("state","gone");
                             break;
                 }
        }

        @Override
        public void processMessage(Chat chat, Message message) {
               Log.d("processMessage","processMessage");
        }
});

use this code.hope so will work

Rajesh Jadav
  • 12,801
  • 5
  • 53
  • 78
John smith
  • 1,781
  • 17
  • 27
  • Hello, Ahesanali Momin, can you please let me know exact scenario at your end.and what kind of error you are facing in XMPP. for more info message me at skype @ piyush.gupta326. then we can discuss more,your problem and hopefully will reach success point. – John smith Jul 12 '16 at 09:39
  • I am not getting any error but when i start tyoping code doesn't enter in any state, i mean stateChangeListener not called. – Ahesanali Suthar Jul 12 '16 at 10:01
  • hey man, have you read this doc http://xmpp.org/extensions/xep-0085.html – John smith Jul 12 '16 at 10:07
  • this is completely theory and not interesting as of now, as most of the things pretty clear by using chat client. – Ahesanali Suthar Jul 12 '16 at 10:15
  • I meant, please read the documentation in that link. I hope you will found the solution there. else we can discuss same here. – John smith Jul 12 '16 at 10:15
  • Should i have to add something while sending message? – Ahesanali Suthar Jul 13 '16 at 01:39
  • Let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/117163/discussion-between-ahesanali-momin-and-piyushgupta202390). – Ahesanali Suthar Jul 13 '16 at 06:25
  • It was my mistake that i am not sending composing status when user starts typing and send other status when stops typing. But chatstate listener you have mentioned is perfact. – Ahesanali Suthar Jul 13 '16 at 15:57
1

i am using chat state listener :

Chat chat = chatManager.createChat(jid,
                        new ChatStateChangedListener());

bind the chatstatelistener with each jid like above , then :

public class ChatStateChangedListener implements ChatStateListener {

    public ChatStateChangedListener() {
        printLog("Chat State Changed Listner Constructor");
    }

    @Override
    public void processMessage(Chat arg0, Message arg1) {

    }


    @Override
    public void stateChanged(Chat chat, ChatState state) {

        if (state.toString().equals(ChatState.composing.toString())) {
                tvLastSeen.setText("Typing...");
            } else if (state.toString().equals(ChatState.paused.toString())) {
                tvLastSeen.setText("paused...");
            } else {
                tvLastSeen.setText("nothing");
            }

        }


    }

}
Akshay Paliwal
  • 3,718
  • 2
  • 39
  • 43
  • FYI: merged from http://stackoverflow.com/questions/21154833/how-to-get-typing-status-notification-in-xmpp – Shog9 Oct 08 '16 at 03:57
1

Create On Class MMessageListener to listen incoming messages

private class MMessageListener implements MessageListener, ChatStateListener {

    public MMessageListener(Context contxt) {
    }


    @Override
    public void stateChanged(Chat chat, ChatState chatState) {

        mStatus = "Online";

        if (ChatState.composing.equals(chatState)) {

            mStatus = chat.getParticipant() + " is typing..";
            Log.d("Chat State", chat.getParticipant() + " is typing..");
        } else if (ChatState.gone.equals(chatState)) {
            Log.d("Chat State", chat.getParticipant() + " has left the conversation.");
            mStatus = chat.getParticipant() + " has left the conversation.";
        } else if (ChatState.paused.equals(chatState)){
            Log.d("Chat State", chat.getParticipant() + ": " + chatState.name());
            mStatus = "Paused";
        }else if (ChatState.active.equals(chatState)){
            mStatus = "Online";
        }

        // do whatever you want to do once you receive status


    }


    @Override
    public void processMessage(Message message) {

    }

    @Override
    public void processMessage(Chat chat, Message message) {


    }
}

Add Listener to your chat object

Chat Mychat = ChatManager.getInstanceFor(connection).createChat( "user2@localhost"), mMessageListener);

Send status to receiving user on edittext text change

ChatStateManager.getInstance(connection).setCurrentState(ChatState.composing, Mychat);

This works fine for me.

Dharmesh
  • 221
  • 2
  • 3
  • Hi Dharmesh, i did the same but i am getting null always in composing state message in processMessage. My EditText text change method is : newChat = chatmanager.createChat(send_to, messageListener); Message msg = new Message(send_to, Message.Type.chat); msg.setFrom(USERNAME_LOGIN+"@"+HOST_NAME); // my id newChat.sendMessage(msg); ChatStateManager.getInstance(connection).setCurrentState(ChatState.composing, newChat); And this also not send status to others. – Kutbi Jan 09 '16 at 12:20
  • FYI: merged from http://stackoverflow.com/questions/21154833/how-to-get-typing-status-notification-in-xmpp – Shog9 Oct 08 '16 at 03:56
  • How to check if user has paused or is no longer typing in the editext? – Kaveesh Kanwal Jan 22 '18 at 10:38
0

Your or another xmpp client which you use, should sending chat state for You can catch the state.

Like This;

try {
      ChatStateManager.getInstance(GlobalVariables.xmppManager.connection).setCurrentState(ChatState.composing, chat);
    } catch (XMPPException e) {
        e.printStackTrace();
    }

or

try {
        ChatStateManager.getInstance(GlobalVariables.xmppManager.connection).setCurrentState(ChatState.gone, chat);
    } catch (XMPPException e) {
        e.printStackTrace();
    }
Savas Adar
  • 4,083
  • 3
  • 46
  • 54
  • Maybe your Server application doesnt support it. – Savas Adar Jan 09 '16 at 15:42
  • you mean to say our server is not configure for that ? but its working fine with ios to ios. i am writting this line on textChangeListner of EditText. and chat object is chatmanager = connection.getChatManager(); Chat chat = chatmanager.createChat("user@", listner); Even when i receive compose status from ios processMessage gives me null. Please help me to find solution for both send and receive. P.S. i am using asmack library – Kutbi Jan 10 '16 at 07:45
  • FYI: merged from http://stackoverflow.com/questions/22225394/how-to-get-the-typing-status-in-asmack-android – Shog9 Oct 08 '16 at 03:58
  • This needs to be done on editext text text change listener..right? – Kaveesh Kanwal Jan 22 '18 at 09:41
0

However you can get it from ProcessPacket also. there you will get a Message object, after you can extract xml portion from there and handle them its contain specific chatstate or not.

    Message message = (Message) packet;
    String msg_xml = message.toXML().toString();

    if (msg_xml.contains(ChatState.composing.toString())) {
        //handle is-typing, probably some indication on screen
    } else if (msg_xml.contains(ChatState.paused.toString())) {
        // handle "stopped typing"
    } else {
       // normal msg
    }

now handle as per your requirement.

Nikhil Borad
  • 2,065
  • 16
  • 20
0

Just add ChatStateManager after ChatManager intalization:

chatManager =  ChatManager.getInstanceFor(getXmpptcpConnection());
ChatStateManager.getInstance(getXmpptcpConnection());

Then you need to add ChatStateListener during createChat(to,chatMesageListener):

chatManager.createChat(message.getTo(), chatMessageListener).sendMessage(message);

private ChatStateListener chatMessageListener = new ChatStateListener() {

    @Override
    public void stateChanged(Chat chat, ChatState state) {
        //State Change composing,active,paused,gone,etc
        Log.d(TAG, "ChatStateListener:::stateChanged -> " + chat.toString() + " \n -> " + state.toString());
    }

    @Override
    public void processMessage(Chat chat, Message message) {
        //Incoming Message
        Log.d(TAG, "ChatStateListener:::processMessage -> " + chat.toString() + " \n -> " + message.toString());
    }
};
Hexaholic
  • 3,299
  • 7
  • 30
  • 39
dastan
  • 892
  • 10
  • 17
  • FYI: merged from http://stackoverflow.com/questions/22225394/how-to-get-the-typing-status-in-asmack-android – Shog9 Oct 08 '16 at 03:58
  • Next time, maybe just answer one question and flag the rest to let us know that they're duplicates; posting the same answer 7 times is pretty excessive. – Shog9 Oct 08 '16 at 04:02