美文网首页
环信实现聊天界面查看大图左右轮滑效果

环信实现聊天界面查看大图左右轮滑效果

作者: 夏广成 | 来源:发表于2017-06-02 14:00 被阅读187次

环信提供了一个easeUI库,其中实现了一些简单的聊天界面。但是产品需求却是要我们能够在聊天界面中点击图片,并且可以查看大图,在大图页面能够左右滑动,类似qq以及微信的效果。

具体实现思路是,打开单人聊天界面时,开始从数据库中加载消息,直到消息加载完成,然后从所有的消息中获取属于图片的消息,然后保存到一个集合中,然后将这个集合中保存的图片地址,通过viewpager展示出来。

思路理清之后,我们看一下相关的api

一:EMConversation

这个类代表一个用户的对话,从他这里可以获取相关的消息。

image.png image.png image.png

上面这两个方法,其中getAllMessages()代表回去内存中已经加载的所有消息。loadMoreMsgFromDB()返回的是我们从本地数据库中加载的消息。待会我们就是要从这里遍历得到所有的图片消息。

二:EaseChatFragment

EaseChatFragment他代表的就是当前我们打开的聊天页面。我们主要是在这里对图片信息进行筛选,保存。由于我们并不知道数据库中到底有多少信息,因此我们需要不停调用EMConversation的loadMoreMsgFromDB()来获取消息,直到我们读取完毕。我们这里选用来handler来处理循环读取。而handler处理循环读取的触发条件就是EMConversation初始化完成。

 protected void onConversationInit() {
        conversation = EMClient.getInstance().chatManager().getConversation(toChatUsername, EaseCommonUtils.getConversationType(chatType), true);
        conversation.markAllMessagesAsRead();
        // the number of messages loaded into conversation is getChatOptions().getNumberOfMessagesLoaded
        // you can change this number
        final List<EMMessage> msgs = conversation.getAllMessages();
        int msgCount = msgs != null ? msgs.size() : 0;
        if (msgCount < conversation.getAllMsgCount() && msgCount < pagesize) {
            String msgId = null;
            if (msgs != null && msgs.size() > 0) {
                msgId = msgs.get(0).getMsgId();
            }
            conversation.loadMoreMsgFromDB(msgId, pagesize - msgCount);
        }
        handlerEM.sendEmptyMessage(111);

    }
image.png
1:创建一个Runnable来处理我们读到的消息。这个Runnable主要的思路是

(1):判断当前是不是单一会话,如果是单一聊天,那么就先读取内存中的所有消息,
(2):如果内存中的消息没有20条的话,因为我们在一开始的时候就试图从DB中加载20条消息,那就说明没有更多消息了。
(3):如果内存中有20条消息,那么就继续从DB中读取,直到我们读到的数据不够20条为止。
(4):需要注意我们在调用loadMoreMsgFromDB()的时候,传入的第一个参数是消息的id,我们应该取返回过来的集合当中的第一个消息的id,因为消息是从早到晚排列的,我们要想获得更早的消息,就需要用第一个消息的id。
(5):环信有一个机制,就是当我们从DB中读取消息的时候,读出来的消息会保存到内存中。因此最终的消息,我们可以通过getAllMessages()来获取。

//筛选出来的图片信息
    private ArrayList<String> imageuri;
//我们最终通过从内存中获取所有消息。
    private List<EMMessage> allMessages;
//临时存放从消息db中取出的消息
    private List<EMMessage> messagesEM;
//判断是否有更多的消息了
    private boolean isMoreEM=true;
//用来存放已经取出的消息,根据他的大小来判断有没有更多的消息
    ArrayList<EMMessage> emMessageArrayList =new ArrayList<>();
Runnable runnableeEM=new Runnable() {
        @Override
        public void run() {
            try {
                if (chatType == EaseConstant.CHATTYPE_SINGLE) {
                    if(emMessageArrayList.size()==0){
                        List<EMMessage> allMessages = conversation.getAllMessages();
                        messagesEM=conversation.loadMoreMsgFromDB(allMessages.get(0).getMsgId(),20);
                        emMessageArrayList.addAll(messagesEM);
                    }else{
                        messagesEM=conversation.loadMoreMsgFromDB(emMessageArrayList.get(0).getMsgId(),20);
                        emMessageArrayList.clear();
                        emMessageArrayList.addAll(messagesEM);

                    }

                } else {
                    if(emMessageArrayList.size()==0){
                        List<EMMessage> allMessages = conversation.getAllMessages();
                        messagesEM=conversation.loadMoreMsgFromDB(allMessages.get(allMessages.size()-1).getMsgId(),20);
                        emMessageArrayList.addAll(messagesEM);
                    }else{
                        messagesEM=conversation.loadMoreMsgFromDB(emMessageArrayList.get(emMessageArrayList.size()-1).getMsgId(),20);
                        emMessageArrayList.clear();
                        emMessageArrayList.addAll(messagesEM);
                    }

                }
            } catch (Exception e1) {
                return;
            }

            if (emMessageArrayList.size() > 0) {
                if (emMessageArrayList.size() != 20) {
                    isMoreEM=false;
                    //没有更多消息了
                    handlerEM.sendEmptyMessage(222);
                    Toast.makeText(getActivity(), getResources().getString(R.string.no_more_messages),
                            Toast.LENGTH_SHORT).show();
                }else{
                    isMoreEM=true;
                    //还有更多消息
                    handlerEM.sendEmptyMessage(111);
                }
            } else {
                isMoreEM=false;
                    //没有更多消息了
                handlerEM.sendEmptyMessage(222);
                Toast.makeText(getActivity(), getResources().getString(R.string.no_more_messages),
                        Toast.LENGTH_SHORT).show();
            }
        }
    };
2:创建一个handler来处理任务

(1):当发送的是111表示还有更多消息,于是就继续从DB中获取。
(2):当发送的是222表示没有更多消息了,我们就可以获取所有内存中的消息,然后遍历取到图片的消息。然后保存到集合中,当我们点击图片的时候使用。

 Handler handlerEM = new Handler() {
        @Override
        public void handleMessage(android.os.Message message) {
            switch (message.what){
                case 111:
                    if(isMoreEM){
                        handlerEM.postDelayed(runnableeEM,1000);
                    }
                    break;
                case 222:
                    allMessages = conversation.getAllMessages();
                    imageuri = new ArrayList<String>();
                    if(allMessages!=null){
                        for(EMMessage emMessage:allMessages){
                            if(emMessage.getBody() instanceof  EMImageMessageBody) {
                                EMImageMessageBody imgBody = (EMImageMessageBody) emMessage.getBody();
                                imageuri.add(imgBody.getRemoteUrl());
                            }
                        }
                    }
                    break;
            }


        }
    };

三:EaseChatRowImage

这个view代表的就是自定义的图片view,他展示在聊天页面中。在这个页面我们的实现思路
(1):获取到保存在imageuri中的图片地址。
(2):传递到查看大图的页面中。

 @Override
    protected void onBubbleClick() {
        Intent intent = new Intent(context, ViewBigImageActivity.class);
//        File file = new File(imgBody.getLocalUrl());
        Bundle bundle = new Bundle();
        bundle.putInt("selet", 1);
//        bundle.putInt("code", 0);
        ArrayList<String> imageuri = easeChatFragment.getImageuri();
        if(imageuri!=null&&imageuri.size()>0){
            for(int i=0;i<imageuri.size();i++){
                if(TextUtils.equals(imageuri.get(i),imgBody.getRemoteUrl())){
                    bundle.putInt("code", i);
                }
            }
        }

//        if (file.exists()) {
//            bundle.putBoolean("isLocal", true);
//            imageuri.add(imgBody.getLocalUrl());
//        } else {
//            imageuri.add(imgBody.getRemoteUrl());
//        }
        bundle.putStringArrayList("imageuri", imageuri);
        if (message != null && message.direct() == EMMessage.Direct.RECEIVE && !message.isAcked()
                && message.getChatType() == EMMessage.ChatType.Chat) {
            try {
                EMClient.getInstance().chatManager().ackMessageRead(message.getFrom(), message.getMsgId());
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
        intent.putExtras(bundle);
        context.startActivity(intent);
    }

四:ViewBigImageActivity

查看大图的页面,其实就是一个Viewpager,和一个ImageLoader。如果要实现放大缩小的功能的话,可以使用开源库uk.co.senab.photoview。这里就不再赘述了。

相关文章

网友评论

      本文标题:环信实现聊天界面查看大图左右轮滑效果

      本文链接:https://www.haomeiwen.com/subject/aqtxfxtx.html