Android事件分发机制

前言

 Android的事件分发机制看了不少文章,背都背出来了,可是一直没有本身去看源码追一遍,如今写下这篇文章记录下从源码分析Android的事件分发机制,若是有哪一个地方说的不对的,望你们指出!谢谢!源码分析

事件分发示意图

事件分发机制示意图

解析

本文基于API 26spa

点击事件到Activity

详情可见这一篇,引用大佬的文章 Touch事件如何传递到Activity .net

Activity到PhoneWindow再到DecorView

 Activity收集到点击事件后会调用到本身的dispatchTouchEvent方法,而且在其中经过调用window的superDispatchTouchEvent的方法来判断是否消费该事件,由于window是一个抽象类,他有一个惟一的子类Phonewindow,因此实际上会调用到PhoneWindow中的superDispatchTouchEvent,而到了PhoneWindow那就是直接调用DecorView,没有其余的判断3d

  • Activity中调用PhoneWindow的superDispatchTouchEvent方法判断是否消费该事件
    Activity中的dispatchTouchEvent方法
  • PhoneWindow直接调用DecorView中的superDispatchTouchEvent方法
    在这里插入图片描述

DecorView到ViewGroup再到View

 DecorView继承自FrameLayou,FrameLayout继承于ViewGroup,因此DecorView也是ViewGroup的子类,DecorView中的superDispatchTouchEvent调用父类ViewGroup的dispatchTouchEvent进行事件的分发orm

  • DecorView调用父类的dispatchTouchEvent方法 cdn

    在这里插入图片描述
     ViewGroup中dispatchTouchEvent进行了事件拦截的处理,首先判断了当前是否能够进行拦截,而后调用onInterceptTouchEvent进行拦截判断,若是返回为false,则继续向子View进行分发事件(前提是存在子View的状况下,若是不存在,而且拦截为false,则dispatchTouchEvent返回为false,向上级传递告诉他们大家本身消费去吧)
    在这里插入图片描述
    在这里插入图片描述

  • 向子类分发事件,首先判断是否存在子View,若是存在子View,则调用dispatchTransformedTouchEvent方法去筛选,调用子View的dispatchTouchEvent方法 blog

    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述

  • 子View中判断自身的onTouchEvent是否执行,若是不执行,则返回false,若是执行返回true继承

在这里插入图片描述

总结

 事件分发理解起来比较容易,就是一层一层的关系,中间任何一个环节出现了消费事件的操做,则都不用下发给下一层了,而且消费事后告诉上一层我已经消费了,而后上一层再告诉上上层,直到顶层。事件

事件cancel的时机

 文章刚发出来就被群里的大佬提醒了一点,何时会cancel,个人天,我还懵逼中,而后我正在查,又一位大佬把答案发出来了,感谢两位!  另外加上一篇博客,里面也说了:":ACTION_CANCEL事件是收到前驱事件后,后续事件被父控件拦截的状况下产生,onTouchEvent的事件回传到父控件只会发生在ACTION_DOWN事件中。 因此当父View拦截到后续事件时才会触发ACTION_CENCEL,咱们正常的流程只有DOWN,UP,MOVE,这三个事件,因此保证ACTION_CENCEL事件不会触发便可"。图片

解决自定义View触发ACTION_CANCEL

在这里插入图片描述
相关文章
相关标签/搜索