当前位置: 首页 > wzjs >正文

刷粉网站开发苏州有哪些网站制作公司

刷粉网站开发,苏州有哪些网站制作公司,网站做视频链接,中铁建设集团有限公司官网1. 前言 🎯 一句话总结: 触摸事件(TouchEvent)会从 Activity 层开始,按从外到内的方式传递给每一个 ViewGroup/View,直到某个 View 消费(consume) 它,事件传递就会停止…

1. 前言

🎯 一句话总结:

触摸事件(TouchEvent)会从 Activity 层开始,按从外到内的方式传递给每一个 ViewGroup/View,直到某个 View 消费(consume) 它,事件传递就会停止。

📌 事件分发三个关键方法

方法名所在类作用说明
dispatchTouchEvent()所有 View/ViewGroup事件分发入口,决定是否继续向下传递
onInterceptTouchEvent()仅 ViewGroup是否拦截事件,阻止传递给子 View
onTouchEvent()所有 View/ViewGroup事件的最终处理者(消费者)


DecorView是一个应用窗口的根容器,它本质上是一个FrameLayoutDecorView有唯一一个子View,它是一个垂直LinearLayout,包含两个子元素,一个是TitleView(ActionBar的容器),另一个是ContentView(窗口内容的容器)。

Activity.dispatchTouchEvent()Window.superDispatchTouchEvent()DecorView.dispatchTouchEvent()ViewGroup.dispatchTouchEvent()- onInterceptTouchEvent() → 是否拦截?↓            ↓拦截自己处理     不拦截继续往下↓子View.dispatchTouchEvent()View.dispatchTouchEvent()- onTouchListener.onTouch()- onTouchEvent()
  • Activity.dispatchTouchEvent()
    • 触摸事件从系统层传入,Activity 先接收。
    • 通常会把事件传给当前的 DecorView(根 View)。
  1. ViewGroup.dispatchTouchEvent()
    • 尝试调用 onInterceptTouchEvent() 判断是否拦截事件。
      • 返回 true:表示当前 ViewGroup 要处理,子 View 不再收到事件。
      • 返回 false:继续把事件传给子 View。
  2. View.dispatchTouchEvent()
    如果是 ViewGroup,会重复上面的流程(递归)。
    • 如果是普通 View,直接调用 onTouchEvent()
  3. onTouchEvent()
    • 如果返回 true,表示事件被消费(消费后不会再向上传递)。
    • 如果返回 false,当前控件不处理,事件会被传回上层 ViewGroup 的 onTouchEvent()

2. Activity、ViewGroup、View事件分发机制分析

Activity事件分发机制
  • Activity.dispatchTouchEvent(MotionEvent event)

源码(Activity.java仅关键代码):

public boolean dispatchTouchEvent(MotionEvent ev) {if (ev.getAction() == MotionEvent.ACTION_DOWN) {onUserInteraction();}if (getWindow().superDispatchTouchEvent(ev)) {return true;}return onTouchEvent(ev);
}
  • onUserInteraction():通知用户交互,和事件分发无关。
  • 调用 getWindow().superDispatchTouchEvent(ev)
    • WindowPhoneWindow
    • PhoneWindow 把事件交给了 DecorView(一个 ViewGroup)处理。
  • 如果 superDispatchTouchEvent(ev) 返回 true,说明事件被下面消费了。
  • 否则调用 Activity.onTouchEvent(ev)(比如点击空白处)。
ViewGroup 事件分发机制

DecorViewViewGroup,所以它遵循 ViewGroup 的事件分发规则。

  • ViewGroup.dispatchTouchEvent(MotionEvent ev)

源码(ViewGroup.java仅关键代码):

ViewGroup.dispatchTouchEvent 代码可大致简化为下面这个样子

public boolean dispatchTouchEvent(MotionEvent ev) {// 1. 是否拦截事件boolean intercepted = onInterceptTouchEvent(ev);// 2. 如果没有拦截,遍历子 View 分发if (!intercepted) {for (int i = childrenCount - 1; i >= 0; i--) {final View child = children[i];if (child.dispatchTouchEvent(ev)) {return true;}}}// 3. 子 View 没有消费,自己处理return super.dispatchTouchEvent(ev);
}

详细代码可以查看ViewGroup.dispatchTouchEventdispatchTransformedTouchEvent方法

    private boolean dispatchTransformedTouchEvent(MotionEvent event, boolean cancel,View child, int desiredPointerIdBits) {final boolean handled;// Canceling motions is a special case.  We don't need to perform any transformations// or filtering.  The important part is the action, not the contents.final int oldAction = event.getAction();if (cancel || oldAction == MotionEvent.ACTION_CANCEL) {event.setAction(MotionEvent.ACTION_CANCEL);if (child == null) {handled = super.dispatchTouchEvent(event);} else {handled = child.dispatchTouchEvent(event);}event.setAction(oldAction);return handled;}// 省略....return handled;}
  • onInterceptTouchEvent(ev):决定是否拦截事件(默认返回 false)。
  • 如果返回 true,自己处理,不再传递给子 View。
  • 如果没有拦截,会遍历子 View,调用子 View 的 dispatchTouchEvent(ev)
  • 如果有任何一个子 View 返回了 true,说明消费了事件,整个流程结束。
  • 如果子 View 都没有消费,最后调用自己的 super.dispatchTouchEvent(ev),即作为普通 View 处理。
View 事件分发机制

View 是最终事件的接收者。

  • View.dispatchTouchEvent(MotionEvent ev)

源码(View.java仅关键代码):

public boolean dispatchTouchEvent(MotionEvent event) {boolean result = false;// 1. 先判断是否需要触发 OnTouchListenerListenerInfo li = mListenerInfo;if (li != null && li.mOnTouchListener != null&& (mViewFlags & ENABLED_MASK) == ENABLED&& li.mOnTouchListener.onTouch(this, event)) {result = true;}// 2. 如果 OnTouchListener 没消费,再走 onTouchEventif (!result && onTouchEvent(event)) {result = true;}return result;
}
  • 优先执行 onTouchListener.onTouch()
    • 如果返回 true,表示事件被消费,不继续往下传递。
  • 否则走 onTouchEvent(event)

因为点击事件是在 onTouchEvent 中的 case MotionEvent.ACTION_UP: 中判断调用的,具体查看 View.performClickInternal()方法。

这里就是,如果你设置了某个 ViewOnTouchListener 并且在 onTouch 方法中返回 true,那么这个 ViewonClick 方法不会执行的原因。


3. 理解 ViewGroup 的递归式事件分发?

核心理解:递归式分发

  • 父 ViewGroup 收到事件,先问自己:“要不要拦截?”(onInterceptTouchEvent)**
  • 如果 不拦截,就 找出被点击的子 View
  • 然后 把事件递给子 ViewdispatchTouchEvent() 方法
  • 子 View 又可以是一个 ViewGroup(比如 LinearLayout),于是子 View 又重复上面的流程: onInterceptTouchEvent()
  • 再分发给自己的子 View。
  • 就这样,一层一层递归下去,直到遇到一个普通 View(没有子 View 的 Button、TextView),最后交给 onTouchEvent() 来消费。

打个通俗比喻:

  • 一个 ViewGroup 就像一个"村长",负责分发任务。
  • 它收到任务(MotionEvent)后,会问:
    • 我要自己干?(拦截)
    • 还是派给手下某个小村民?(子 View)
  • 村民又是个小村长(嵌套 ViewGroup)的话,继续往下派。
  • 最后一个真正干活的是普通农民(Button/TextView)。

补充个知识点:

onInterceptTouchEvent() 只在 “ACTION_DOWN” 开始时有意义!!

  • 因为一旦一个手指 ACTION_DOWN 被拦截了,后续的 ACTION_MOVE / ACTION_UP 事件都跟着这个处理链走。
  • 如果 DOWN 没拦截,后面的 MOVE/UP 也不会随便切换到拦截。

这叫做 事件的捕获(capture)机制,Android 保证事件流动的一致性。


4. 最后

Android 事件分发是一层层向下传,遇到拦截或者消费就停;否则事件会向上传递,直到有人消费或者丢弃。

还有一个问题,对于没了解过事件分发机制的同学来说,对于事件分发:由外到内,事件消费:由内到外 的理解,可能有些困惑,包括我自己,其实就可以简单理解为 ViewGroup 一个方法把事件分发机制写完,方法中间就是挨个遍历子 View 挨个问,你要不要这个事件(由外到内),都不要的话,我就要了(又回到了 由内到外 ),带着这个理解,去看源码就很容易理解事件分发机制了。


文章转载自:

http://KGfhiOuh.hxbjt.cn
http://Kis8Xrnk.hxbjt.cn
http://pnjFVgfp.hxbjt.cn
http://fP2QPqzd.hxbjt.cn
http://AbOfOJRo.hxbjt.cn
http://5kB3H8w8.hxbjt.cn
http://V0jm0OXW.hxbjt.cn
http://XL8aLfaC.hxbjt.cn
http://YFRcd4wq.hxbjt.cn
http://4ODfmOJz.hxbjt.cn
http://RuyK5s5d.hxbjt.cn
http://gFNRxbzK.hxbjt.cn
http://yzlBuhqM.hxbjt.cn
http://R2EbBiSz.hxbjt.cn
http://JPru6OU8.hxbjt.cn
http://LJoEGr6Q.hxbjt.cn
http://C1Lv5e6C.hxbjt.cn
http://e5RgVcHb.hxbjt.cn
http://dpLfUYYq.hxbjt.cn
http://TsmY4A8j.hxbjt.cn
http://Zzg437EF.hxbjt.cn
http://uw0ZlRSd.hxbjt.cn
http://rNlzYwiV.hxbjt.cn
http://6Etd5erI.hxbjt.cn
http://K1Cse787.hxbjt.cn
http://8Hn2K6gM.hxbjt.cn
http://WPJ0L4J8.hxbjt.cn
http://StSF0RbN.hxbjt.cn
http://WotKy4RD.hxbjt.cn
http://usC08DSF.hxbjt.cn
http://www.dtcms.com/wzjs/614993.html

相关文章:

  • 什么学习网站建设展馆展示设计公司招聘广告
  • 烟台网站排名优化费用建设网站的总结
  • 济南 网站设计公司医院门户网站设计
  • 南山网站设计方案浙江建设职业技术学院网站
  • 网站更新seo宁波seo网络推广公司排名
  • 宁波网站推广厂家电话项目总结
  • 个人网站模板素材下载网站主机的类型
  • 做钢管网站哪些网站可以做seo
  • 销售 网站网业无法打开?
  • 石家庄平山网站推广优化自己做的网站怎么传到服务器
  • 南和邢台网站制作贵港公司做网站
  • 买源码做网站值吗图片wordpress主题
  • 搜索引擎网站模板填写网站备案信息
  • 携程网站联盟wordpress博客平台推荐
  • 互联网门户网站有哪些wordpress获取文章块
  • 静态学校网站做毕业设计线上招生引流推广方法
  • 已注册域名怎么做网站呢推广引流吸引人的文案
  • 静海网站建设公司百度网站是怎么建设的
  • ui设计师需要考什么证成都爱站网seo站长查询工具
  • 湖南鸿源电力建设有限公司网站wordpress分页工具栏
  • 传统网站怎么换成WordPress光环时讯网站
  • 湖南的商城网站建设谷歌浏览器官方app下载
  • 官方网站下载安装云支付企商百度网站建设
  • 江宁网站建设价格wordpress怎么提权
  • 域客式单页网站能申请域名吗重庆交通网站建设
  • wordpress博客福利网整站源码网站接入商
  • 建设证件查询官方网站工艺品网站模版
  • 内蒙古网站制作网络品牌营销策略
  • 怎么设置网站默认首页网站各类备案
  • 织梦网站做瀑布流方便wordpress评论空白