基本信息
源码名称:android 读取微信聊天内容 示例源码(AccessibilityService)
源码大小:20.74M
文件格式:.zip
开发语言:Java
更新时间:2017-08-04
   友情提示:(无需注册或充值,赞助后即可获取资源下载链接)

     嘿,亲!知识可是无价之宝呢,但咱这精心整理的资料也耗费了不少心血呀。小小地破费一下,绝对物超所值哦!如有下载和支付问题,请联系我们QQ(微信同号):813200300

本次赞助数额为: 2 元 
   源码介绍

微信聊天界面的布局,查看方法:

AndroidStudio--Tools--Android--Android Device Monitor


public class WeChatLogService extends AccessibilityService {

    /**
     * 聊天对象
     */
    private String ChatName;
    /**
     * 聊天最新一条记录
     */
    private String ChatRecord = "cxk";

    /**
     * 小视频的秒数,格式为00:00
     */
    private String VideoSecond;

    @Override
    public void onAccessibilityEvent(AccessibilityEvent event) {
        int eventType = event.getEventType();
        switch (eventType) {
            //每次在聊天界面中有新消息到来时都出触发该事件
            case AccessibilityEvent.TYPE_VIEW_SCROLLED:
                //获取当前聊天页面的根布局
                AccessibilityNodeInfo rootNode = getRootInActiveWindow();
                //获取聊天信息
                getWeChatLog(rootNode);
                break;
        }

    }

    /**
     * 遍历所有控件获取聊天信息
     *
     * @param rootNode
     */

    private void getWeChatLog(AccessibilityNodeInfo rootNode) {
        if (rootNode != null) {
            //获取所有聊天的线性布局
            List<AccessibilityNodeInfo> listChatRecord = rootNode.findAccessibilityNodeInfosByViewId("com.tencent.mm:id/p");
            if (listChatRecord.size() == 0) {
                return;
            }
            //获取最后一行聊天的线性布局(即是最新的那条消息)
            AccessibilityNodeInfo finalNode = listChatRecord.get(listChatRecord.size() - 1);
            //获取聊天对象
            GetChatName(finalNode);
            //获取聊天内容
            GetChatRecord(finalNode);
        }
    }

    /**
     * 遍历所有控件,找到头像Imagview,里面有对联系人的描述
     */
    private void GetChatName(AccessibilityNodeInfo node) {
        for (int i = 0; i < node.getChildCount(); i  ) {
            AccessibilityNodeInfo node1 = node.getChild(i);
            if ("android.widget.ImageView".equals(node1.getClassName()) && node1.isClickable()) {
                //获取聊天对象,这里两个if是为了确定找到的这个ImageView是头像的
                if (!TextUtils.isEmpty(node1.getContentDescription())) {
                    ChatName = node1.getContentDescription().toString();
                    if (ChatName.contains("头像")) {
                        ChatName = ChatName.replace("头像", "");
                    }
                }

            }
            GetChatName(node1);
        }
    }

    /**
     * 遍历所有控件:这里分四种情况
     * 文字聊天: 一个TextView,并且他的父布局是android.widget.RelativeLayout
     * 语音的秒数: 一个TextView,并且他的父布局是android.widget.RelativeLayout,但是他的格式是0"的格式,所以可以通过这个来区分
     * 图片:一个ImageView,并且他的父布局是android.widget.FrameLayout,描述中包含“图片”字样(发过去的图片),发回来的图片现在还无法监听
     * 表情:也是一个ImageView,并且他的父布局是android.widget.LinearLayout
     * 小视频的秒数:一个TextView,并且他的父布局是android.widget.FrameLayout,但是他的格式是00:00"的格式,所以可以通过这个来区分
     *
     * @param node
     */
    public void GetChatRecord(AccessibilityNodeInfo node) {
        for (int i = 0; i < node.getChildCount(); i  ) {
            AccessibilityNodeInfo nodeChild = node.getChild(i);

            //聊天内容是:文字聊天(包含语音秒数)
            if ("android.widget.TextView".equals(nodeChild.getClassName()) && "android.widget.RelativeLayout".equals(nodeChild.getParent().getClassName().toString())) {
                if (!TextUtils.isEmpty(nodeChild.getText())) {
                    String RecordText = nodeChild.getText().toString();
                    //这里加个if是为了防止多次触发TYPE_VIEW_SCROLLED而打印重复的信息
                    if (!RecordText.equals(ChatRecord)) {
                        ChatRecord = RecordText;
                        //判断是语音秒数还是正常的文字聊天,语音的话秒数格式为5"
                        if (ChatRecord.contains("\"")) {
                            Toast.makeText(this, ChatName   "发了一条"   ChatRecord   "的语音", Toast.LENGTH_SHORT).show();

                            Log.e("WeChatLog",ChatName   "发了一条"   ChatRecord   "的语音");
                        } else {
                            //这里在加多一层过滤条件,确保得到的是聊天信息,因为有可能是其他TextView的干扰,例如名片等
                            if (nodeChild.isLongClickable()) {
                                Toast.makeText(this, ChatName   ":"   ChatRecord, Toast.LENGTH_SHORT).show();

                                Log.e("WeChatLog",ChatName   ":"   ChatRecord);
                            }

                        }
                        return;
                    }
                }
            }

            //聊天内容是:表情
            if ("android.widget.ImageView".equals(nodeChild.getClassName()) && "android.widget.LinearLayout".equals(nodeChild.getParent().getClassName().toString())) {
                Toast.makeText(this, ChatName "发的是表情", Toast.LENGTH_SHORT).show();

                Log.e("WeChatLog",ChatName "发的是表情");

                return;
            }

            //聊天内容是:图片
            if ("android.widget.ImageView".equals(nodeChild.getClassName())) {
                //安装软件的这一方发的图片(另一方发的暂时没实现)
                if("android.widget.FrameLayout".equals(nodeChild.getParent().getClassName().toString())){
                    if(!TextUtils.isEmpty(nodeChild.getContentDescription())){
                        if(nodeChild.getContentDescription().toString().contains("图片")){
                            Toast.makeText(this, ChatName "发的是图片", Toast.LENGTH_SHORT).show();

                            Log.e("WeChatLog",ChatName "发的是图片");
                        }
                    }
                }
            }

            //聊天内容是:小视频秒数,格式为00:00
            if ("android.widget.TextView".equals(nodeChild.getClassName()) && "android.widget.FrameLayout".equals(nodeChild.getParent().getClassName().toString())) {
                if (!TextUtils.isEmpty(nodeChild.getText())) {
                    String second = nodeChild.getText().toString().replace(":", "");
                    //正则表达式,确定是不是纯数字,并且做重复判断
                    if (second.matches("[0-9] ") && !second.equals(VideoSecond)) {
                        VideoSecond = second;
                        Toast.makeText(this, ChatName   "发了一段"   nodeChild.getText().toString()   "的小视频", Toast.LENGTH_SHORT).show();

                        Log.e("WeChatLog","发了一段"   nodeChild.getText().toString()   "的小视频");
                    }
                }

            }

            GetChatRecord(nodeChild);
        }
    }


    /**
     * 必须重写的方法:系统要中断此service返回的响应时会调用。在整个生命周期会被调用多次。
     */
    @Override
    public void onInterrupt() {
        Toast.makeText(this, "我快被终结了啊-----", Toast.LENGTH_SHORT).show();
    }

    /**
     * 服务开始连接
     */
    @Override
    protected void onServiceConnected() {
        Toast.makeText(this, "服务已开启", Toast.LENGTH_SHORT).show();
        super.onServiceConnected();
    }

    /**
     * 服务断开
     *
     * @param intent
     * @return
     */
    @Override
    public boolean onUnbind(Intent intent) {
        Toast.makeText(this, "服务已被关闭", Toast.LENGTH_SHORT).show();
        return super.onUnbind(intent);
    }