Loading [MathJax]/jax/output/CommonHTML/config.js
前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >专栏 >View 事件分发机制,看这一篇就够了

View 事件分发机制,看这一篇就够了

作者头像
音视频开发进阶
发布于 2021-06-09 11:16:08
发布于 2021-06-09 11:16:08
76200
代码可运行
举报
运行总次数:0
代码可运行

Android 开发当中,View 的事件分发机制是一块很重要的知识。不仅在开发当中经常需要用到,面试的时候也经常被问到。

如果你在面试的时候,能把这块讲清楚,对于校招生或者实习生来说,算是一块不错的加分项。对于工作几年的我们来说,这是必须掌握的,讲不明白,那你回去等通知吧,哈哈。

目录大概如下:

  1. View 事件分发机制简介
  2. View 常见滑动冲突解决
  3. View 双击,多击事件是怎么实现的
  4. 手势识别
  5. 小结

View 事件分发机制简介

View 触摸事件

对于屏幕的点击,滑动,抬起等一系的动作,其实都是由一个一个MotionEvent对象组成的。根据不同动作,主要有以下三种事件类型:

1.ACTION_DOWN:手指刚接触屏幕,按下去的那一瞬间产生该事件 2.ACTION_MOVE:手指在屏幕上移动时候产生该事件 3.ACTION_UP:手指从屏幕上松开的瞬间产生该事件 4.ACTION_CANCEL 当前 View 的手势被打断,后续不会再收到任何事件

从 ACTION_DOWN 开始到 ACTION_UP/ACTION_CANCEL 结束我们称为一个事件序列

正常情况下,无论你手指在屏幕上有多么骚的操作,最终呈现在 MotionEvent 上来讲无外乎下面 3 种 case。

  1. 点击后抬起,也就是单击操作:ACTION_DOWN -> ACTION_UP
  2. 点击后再风骚的滑动一段距离,再抬起:ACTION_DOWN -> ACTION_MOVE -> … -> ACTION_MOVE -> ACTION_UP
  3. 某些情况下,我们可能会没有收到 ACTION_UP 事件,是收到 ACTION_CANCEL 事件。

ACTION_CANCEL 一般是指 ChildView 原先拥有事件处理权,后面由于某些原因,该处理权需要交回给上层去处理,ChildView便会收到ACTION_CANCEL事件。对于一些复位或者重置操作,我们应该在 ACTION_UP 和 ACTION_CANCEL 里面同时进行处理。

代码逻辑上是:上层判断之前交给ChildView的事件处理权需要收回来了,便会做事件的拦截处理,拦截时给ChildView发一个ACTION_CANCEL事件

几个主要方法

我们知道,View 的事件分发机制主要涉及到以下几个方法

  • dispatchTouchEvent ,这个方法主要是用来分发事件的
  • onInterceptTouchEvent,这个方法主要是用来拦截事件的(需要注意的是 ViewGroup 才有这个方法,View 没有 onInterceptTouchEvent 这个方法)
  • onTouchEvent 这个方法主要是用来处理事件的
  • requestDisallowInterceptTouchEvent(true),这个方法能够影响父View是否拦截事件,true 表示父 View 不拦截事件,false 表示父 View 拦截事件

我们先来看一张图。

以下内容参考图解 Android 事件分发机制这一篇博客

在这里插入图片描述

  • 仔细看的话,图分为3层,从上往下依次是Activity、ViewGroup、View
  • 事件从左上角那个白色箭头开始,由 Activity 的 dispatchTouchEvent 进行分发
  • 箭头的上面字代表方法返回值,(return true、return false、return super.xxxxx(),super 的意思是调用父类实现。)
  • dispatchTouchEvent和 onTouchEvent的框里有个【true---->消费】的字,表示的意思是如果方法返回true,那么代表事件就此消费,不会继续往别的地方传了,事件终止。
  • 目前所有的图的事件是针对ACTION_DOWN的,对于ACTION_MOVE和ACTION_UP我们最后做分析。

当触摸事件发生时,首先 Activity 将 TouchEvent 传递给最顶层的 View,TouchEvent最先到达最顶层 view 的 dispatchTouchEvent ,然后由 dispatchTouchEvent 方法进行分发,

如果dispatchTouchEvent返回true 消费事件,事件终结。

如果dispatchTouchEvent返回 false ,则回传给父View的onTouchEvent事件处理;

如果dispatchTouchEvent返回super的话,默认会调用自己的onInterceptTouchEvent方法。

  • 默认的情况下onInterceptTouchEvent回调用super方法,super方法默认返回false,所以会交给子View的onDispatchTouchEvent方法处理
  • 如果 interceptTouchEvent 返回 true ,也就是拦截掉了,则交给它的 onTouchEvent 来处理,
  • 如果 interceptTouchEvent 返回 false ,那么就传递给子 view ,由子 view 的 dispatchTouchEvent 再来开始这个事件的分发。

关于更多详细分析,请查看原博客图解 Android 事件分发机制,真心推荐,写得很好。


View 滑动事件冲突

在开发当中,View 的滑动冲突时经常遇到的,比如 ViewPager 嵌套 ViewPager,ScrollView 嵌套 ViewPager。下面让我们一起来看看怎么解决。

常见的三种情况

第一种情况,滑动方向不同

第二种情况,滑动方向相同

第三种情况,上述两种情况的嵌套

在这里插入图片描述

解决思路

看了上面三种情况,我们知道他们的共同特点是父View 和子View都想争着响应我们的触摸事件,但遗憾的是我们的触摸事件 同一时刻只能被某一个View或者ViewGroup拦截消费,所以就产生了滑动冲突。

那既然同一时刻只能由某一个 View 或者 ViewGroup 消费拦截,那我们就只需要 决定在某个时刻由这个 View 或者 ViewGroup 拦截事件,另外的 某个时刻由 另外一个 View 或者 ViewGroup 拦截事件,不就 OK了吗?

综上,正如 在 《Android开发艺术》 一书提出的,总共 有两种解决方案

以下解决思路来自于 《Android开发艺术》 书籍

下面的两种方法针对第一种情况(滑动方向不同),父View是上下滑动,子View是左右滑动的情况。

外部解决法

从父View着手,重写onInterceptTouchEvent方法,在父View需要拦截的时候拦截,不要的时候返回false,为代码大概 如下

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
@Override
public boolean onInterceptTouchEvent(MotionEvent ev) {
    final float x = ev.getX();
    final float y = ev.getY();

    final int action = ev.getAction();
    switch (action) {
        case MotionEvent.ACTION_DOWN:
            mDownPosX = x;
            mDownPosY = y;

            break;
        case MotionEvent.ACTION_MOVE:
            final float deltaX = Math.abs(x - mDownPosX);
            final float deltaY = Math.abs(y - mDownPosY);
            // 这里是够拦截的判断依据是左右滑动,读者可根据自己的逻辑进行是否拦截
            if (deltaX > deltaY) {
                return false;
            }
    }

    return super.onInterceptTouchEvent(ev);
}

内部解决法

从子View着手,父View先不要拦截任何事件,所有的事件传递给 子View,如果子View需要此事件就消费掉,不需要此事件的话就交给 父View处理。

实现思路 如下,重写子 View的dispatchTouchEvent方法,在Action_down 动作中通过方法 requestDisallowInterceptTouchEvent(true) 先请求 父 View不要拦截事件,这样保证子 View 能够接受到 Action_move 事件,再在 Action_move 动作中根据自己的逻辑是否要拦截事件,不需要拦截事件的话再交给 父 View 处理。

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
@Override
public boolean dispatchTouchEvent(MotionEvent ev) {
    int x = (int) ev.getRawX();
    int y = (int) ev.getRawY();
    int dealtX = 0;
    int dealtY = 0;

    switch (ev.getAction()) {
        case MotionEvent.ACTION_DOWN:
            dealtX = 0;
            dealtY = 0;
            // 保证子View能够接收到Action_move事件
            getParent().requestDisallowInterceptTouchEvent(true);
            break;
        case MotionEvent.ACTION_MOVE:
            dealtX += Math.abs(x - lastX);
            dealtY += Math.abs(y - lastY);
            Log.i(TAG, "dealtX:=" + dealtX);
            Log.i(TAG, "dealtY:=" + dealtY);
            // 这里是够拦截的判断依据是左右滑动,读者可根据自己的逻辑进行是否拦截
            if (dealtX >= dealtY) {
                getParent().requestDisallowInterceptTouchEvent(true);
            } else {
                getParent().requestDisallowInterceptTouchEvent(false);
            }
            lastX = x;
            lastY = y;
            break;
        case MotionEvent.ACTION_CANCEL:
            break;
        case MotionEvent.ACTION_UP:
            break;

    }
    return super.dispatchTouchEvent(ev);
}

更多细节,可以查看我的这篇文章,里面有详细介绍哦 ViewPager,ScrollView 嵌套ViewPager滑动冲突解决


View 双击,多击事件是怎么实现的

实现之前,我们首先来阐述一下思路,怎样实现双击事件,正所谓,授人以鱼不如授人以渔。

单击:用户点击一次之后,一段时间之内不再点击

双击;用户点击一次之后,一段时间之内再次点击

实现思路

  1. 我们监听 onTouch 事件,在 ACTION_DOWN 的时候,点击次数 clickCount +1;
  2. 同时,在 ACTION_DOWN 的时候,延时一段时间,执行相应的 Runnable 任务,这里我们用 handler 的 postDelayed 实现
  3. 在延时任务执行的时候,我们根据点击的次数,进行单击或者多级的回调,最后,记得重置点击次数,以及移除延时任务
代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
open class MyDoubleTouchListener(private val myClickCallBack: MyClickCallBack) : OnTouchListener {

    private var clickCount = 0 //记录连续点击次数
    private val handler: Handler = Handler()

    interface MyClickCallBack {
        fun oneClick() //点击一次的回调
        fun doubleClick() //连续点击两次的回调
    }

    override fun onTouch(v: View, event: MotionEvent): Boolean {
        if (event.action == MotionEvent.ACTION_DOWN) {
            clickCount++
            handler.postDelayed({
                if (clickCount == 1) {
                    myClickCallBack.oneClick()
                } else if (clickCount == 2) {
                    myClickCallBack.doubleClick()
                }
                handler.removeCallbacksAndMessages(null)
                //清空handler延时,并防内存泄漏
                clickCount = 0 //计数清零
            }, timeout.toLong()) //延时timeout后执行run方法中的代码
        }
        return false //让点击事件继续传播,方便再给View添加其他事件监听
    }

    companion object {
        private const val TAG = "MyClickListener"
        private val timeout = ViewConfiguration.getDoubleTapTimeout() //双击间四百毫秒延时

        init {
            Log.i(TAG, "timeout is $timeout ")
        }
    }


}

三击事件

三级事件呢,其实也很简单,我们直接判断在指定时间间隔内点击的次数即可

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
open class MyMultiTouchListener(private val myClickCallBack: MyClickCallBack) : OnTouchListener {

    private var clickCount = 0 //记录连续点击次数
    private val handler: Handler = Handler()

    interface MyClickCallBack {
        fun oneClick() //点击一次的回调
        fun doubleClick() //连续点击两次的回调
        fun threeClick() // 连续点击三次的回调
    }

    override fun onTouch(v: View, event: MotionEvent): Boolean {
        if (event.action == MotionEvent.ACTION_DOWN) {
            clickCount++
            handler.postDelayed({
                if (clickCount == 1) {
                    myClickCallBack.oneClick()
                } else if (clickCount == 2) {
                    myClickCallBack.doubleClick()
                } else if (clickCount == 3) {
                    myClickCallBack.threeClick()
                }
                handler.removeCallbacksAndMessages(null)
                //清空handler延时,并防内存泄漏
                clickCount = 0 //计数清零
            }, timeout.toLong()) //延时timeout后执行run方法中的代码
        }
        return false //让点击事件继续传播,方便再给View添加其他事件监听
    }

    companion object {
        private const val TAG = "MyClickListener"
        private val timeout = 600 //双击间四百毫秒延时

        init {
            Log.i(TAG, "timeout is $timeout ")
        }
    }
}

手势识别

在 Android 开发当中,几乎所有的事件都会与用户进行交互,而我们用得的最多的就是手势了。

我们知道当我们触摸屏幕的时候,会产生很多事件,比如 down,move,up, fling 事件等等。一些简单的处理,我们可以直接重写 View 的 onTouchEvent 方法,根据 View 的 MotionEvent 事件进行处理。

而 Google 为了方便开发者方便接入,提供了几个默认处理类,那就是 GestureDetector 和 ScaleGestureDetector。

GestureDetector这个类对外提供了两个接口和一个外部类 。 接口:OnGestureListener,OnDoubleTapListener

内部类:SimpleOnGestureListener,同时实现了 OnGestureListener,OnDoubleTapListener 接口,如果只想使用接口里面的某个方法,可以直接使用它,方便快捷。

讲解之前,我们向来看一下怎么使用

GestureDetector(Context context, GestureDetector.OnGestureListener listener)

GestureDetector 基本使用

第一步,初始化 GestureDetector 对象

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
 mDetector = GestureDetectorCompat(this, MyGestureListener())

可以看到有两个参数,第一个参数 context,第二个参数 OnGestureListener,我们可以直接实现 OnGestureListener 接口,也可以直接使用 GestureDetector.SimpleOnGestureListener

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
    private class MyGestureListener : GestureDetector.OnGestureListener {

        private val TAG = "GestureDemoActivity"

        override fun onShowPress(e: MotionEvent?) {
            Log.d(TAG, "onShowPress: e is $e")
        }


        override fun onSingleTapUp(e: MotionEvent?): Boolean {
            Log.d(TAG, "onSingleTapUp: e is $e")
            return false
        }

        override fun onDown(event: MotionEvent): Boolean {
            Log.d(TAG, "onDown: $event")
            return true
        }

        override fun onFling(
                event1: MotionEvent,
                event2: MotionEvent,
                velocityX: Float,
                velocityY: Float
        ): Boolean {
            Log.d(TAG, "onFling: $event1 $event2")
            return false
        }

        override fun onScroll(e1: MotionEvent?, e2: MotionEvent?, distanceX: Float, distanceY: Float): Boolean {
            Log.d(TAG, "onScroll: distanceX is $distanceX,distanceY is $distanceY ")
            return false
        }

        override fun onLongPress(e: MotionEvent?) {
            Log.d(TAG, "onLongPress: e is $e")
        }
    }

第二步:设置双击监听

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
// 设置双击监听
mDetector.setOnDoubleTapListener(object : GestureDetector.OnDoubleTapListener {
            override fun onDoubleTap(e: MotionEvent?): Boolean {
                Log.d(TAG, "onDoubleTap: e is e")
                return false
            }

            override fun onDoubleTapEvent(e: MotionEvent?): Boolean {
                Log.d(TAG, "onDoubleTapEvent: e is e")
                return false
            }

            override fun onSingleTapConfirmed(e: MotionEvent?): Boolean {
                Log.d(TAG, "onSingleTapConfirmed: e is e")
                return false
            }

        })

最后,重写 Activity 或者 View 的 onTouchEvent ,将事件交给 mDetector 处理。

通常会有两种写法,第一种是如果手势处理器处理了,直接返回 true,进行消费。否则,进行默认处理

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
override fun onTouchEvent(event: MotionEvent): Boolean {
        return if (mDetector.onTouchEvent(event)) {
            true
        } else {
            super.onTouchEvent(event)
        }
    }

第二种写法是直接在 onTouchEvent 方法中,直接调用 mDetector.onTouchEvent(event) 方法

代码语言:javascript
代码运行次数:0
运行
AI代码解释
复制
override fun onTouchEvent(event: MotionEvent): Boolean {
        mDetector.onTouchEvent(event)
        return super.onTouchEvent(event)
    }

第二种写法,一般不会影响当前 View 或者 Activity 事件的传递,在开发当中,有时候为了减少一些触摸事件的冲突,经常这样写。

ScaleGestureDetector 这里暂时不展开描述了,写着写着,发现好多呀,一个周末就这样过去,贼快,觉得对你有帮助的,请来个三连,点赞,收藏,转发?


小结

这篇文章,其实不难。主要是将 View 的事件分发机制,滑动冲突,以及开发当中经常用到的一些知识点,总结一下。

参考博客:

http://www.jianshu.com/p/e99b5e8bd67b

https://xujun.blog.csdn.net/article/details/52939127

https://github.com/gdutxiaoxu/TouchDemo

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2021-05-28,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 音视频开发进阶 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
拇指记者打探事件分发机制背后的秘密(下)
上一期跟随拇指记者,发现了Android公司在指派具体的人之前的种种机制,今天就继续探索,看看任务具体的处理消费逻辑。
码上积木
2021/04/16
4450
图解 Android 事件分发机制
在Android开发中,事件分发机制是一块Android比较重要的知识体系,了解并熟悉整套的分发机制有助于更好的分析各种点击滑动失效问题,更好去扩展控件的事件功能和开发自定义控件,同时事件分发机制也是Android面试必问考点之一,如果你能把下面的一些事件分发图当场画出来肯定加分不少。废话不多说,总结一句:事件分发机制很重要。 Android 事件分发流 关于Android 事件分发机制网上的博文很多,但是很多都是写个Demo然后贴一下输出的Log或者拿源码分析,然后一堆的注释和说明,如果用心的去看肯定是收
非著名程序员
2018/02/02
1.3K0
图解 Android 事件分发机制
android viewgroup事件分发机制
今天给大家代码ViewGroup事件分发的源码解析~~凡是自定义ViewGroup实现各种滑动效果的,不可避免的会出现很多事件的冲突,对ViewGroup事件分发机制的了解,也有益于大家了解冲突产生的原因,以及对冲突进行处理~ 1、案例 首先我们接着上一篇的代码,在代码中添加一个自定义的LinearLayout: package com.example.zhy_event03;   import android.content.Context;   import android.util.Attrib
xiangzhihong
2018/01/30
9950
一文读懂Android View事件分发机制
Android View 虽然不是四大组件,但其并不比四大组件的地位低。而View的核心知识点事件分发机制则是不少刚入门同学的拦路虎。ScrollView嵌套RecyclerView(或者ListView)的滑动冲突这种老大难的问题的理论基础就是事件分发机制。
陈宇明
2020/12/15
3760
一文读懂Android View事件分发机制
Android View的事件分发机制
在用户触摸屏幕时,总是离用户触摸点最近的控件来响应触摸事件,如果最近的控件没有实现响应事件,那这个事件会不断的向父类传递,直到有view响应时,就会将触摸反馈的事件流传递给这个view的onTouchEvent()方法,如下图: 如果CustmoView中不响应onTouchEvent(),那面事件会传递给LayoutView中,如果在LayoutView中响应了onTouchEvent(),那面事件就不会再传递给RootView了。
艳龙
2021/12/16
3830
Android View的事件分发机制
Android查缺补漏(View篇)--事件分发机制
事件分发机制是Android中非常重要的一个知识点,同时也是难点,相信到目前为止很多Android开发者对事件分发机制并没有一个非常系统的认识,当然也包括博主个人在内。可能在平时的开发工作中我们并没有意识到事件分发机制起到的作用,其实它是时刻存在的只是我们不知道而已,就像一些滑动冲突、点击事件之间的冲突等等大多是因为事件分发处理不当导致的。想起了博主大学时做过一个小项目,里面就出现了滑动冲突的问题,虽然最后在网上一步步看着别人的教程也糊里糊涂的解决了,但终究不知其所以然,那么今天就让我们一起来深入的探索一下
codingblock
2018/03/30
6520
进阶必备-Android事件分发机制
或许你会问,“为什么我一定要知道View的事件分发机制?”。因为我们在实际开发的过程中,经常会遇到多层的View互相嵌套以后,对某一个View进行滑动的时候,特别不灵敏,甚至于没法滑动。这种滑动冲突的解决需要我们清楚的掌握View的事件分发机制。那下面我们详细的讲解下View的整个事件机制。 Android将View的事件封装到MotionEvent这个类中,这也是监听touch事件中回调给我们的参数public boolean onTouchEvent(MotionEvent event) 。通常事件我们主要关心下面几种类型:
吴延宝
2018/10/18
9510
进阶必备-Android事件分发机制
笔记(四)——事件分发机制
1、事件分发机制:整个事件分发是一个U形传递的,递归传递。图解 Android 事件分发机制
木溪bo
2020/03/27
1.3K0
View事件分发机制源码解析
注:本文解析的源码基于 API 25,部分内容来自于《Android开发艺术探索》。
俞其荣
2022/07/28
3970
重新复习Android View事件分发
一个Activity包含了一个Window对象,这个对象是由PhoneWindow来实现的。PhoneWindow将DecorView作为整个应用窗口的根View,而这个DecorView又将屏幕划分为两个区域:一个是TitleView,另一个是ContentView,而我们平时所写的就是展示在ContentView中
老马的编程之旅
2022/06/22
3800
重新复习Android View事件分发
Android事件分发机制完全解析,带你从源码的角度彻底理解(上)
其实我一直准备写一篇关于Android事件分发机制的文章,从我的第一篇博客开始,就零零散散在好多地方使用到了Android事件分发的知识。也有好多朋友问过我各种问题,比如:onTouch和onTouc
用户1158055
2018/01/05
1.3K0
Android事件分发机制完全解析,带你从源码的角度彻底理解(上)
Android高级进阶之路【二】十分钟彻底弄明白 View 事件分发机制
此处需要特别说明:事件列,即指从手指接触屏幕至手指离开屏幕这个过程产生的一系列事件。一般情况下,事件列都是以DOWN事件开始、UP事件结束,中间有无数的MOVE事件。
做个快乐的码农
2021/11/18
6840
Android高级进阶之路【二】十分钟彻底弄明白 View 事件分发机制
开发笔记-自定义View(十)-View的事件分发机制
关于自定义View系列的文章,好久没有写了。今天抽空看了下Android开发艺术探索。正好看到了View的事件分发机制,所以将它写成笔记记录下来。 关于View的事件分发,我起初是学习郭神的2篇文章。感觉其实也没有什么。大致也就了解下。不过看完其他很多优秀的文章和书籍后,才知道自己too young too simple。下面我们就一起来分析下Android的时间分发机制。
g小志
2018/09/11
6620
开发笔记-自定义View(十)-View的事件分发机制
Android必知必会--事件分发机制
所谓的安卓事件是什么?具体来说的就是点击和滑动两个操作;抽象着来说就是下面的表格。
ClericYi
2020/07/21
6140
Android事件分发机制完全解析,带你从源码的角度彻底理解(下)
记得在前面的文章中,我带大家一起从源码的角度分析了Android中View的事件分发机制,相信阅读过的朋友对View的事件分发已经有比较深刻的理解了。 还未阅读过的朋友,请先参考 Android事件分
用户1158055
2018/01/05
1.3K0
Android事件分发机制完全解析,带你从源码的角度彻底理解(下)
事件分发机制三问
只要有点击,就会涉及到事件分发机制,点击屏幕后,view会怎么反应?今天一起来看看事件分发机制的三问:
码上积木
2020/10/10
4620
View的事件分发机制
当一个点击事件产生后,他的传递过程遵循Activity->Window->View的逐级传递。我们这里讨论的是在Android系统View里事件传递。
1025645
2018/08/23
4220
笔记——事件分发机制(四)
1、事件分发机制:整个事件分发是一个U形传递的,递归传递。图解 Android 事件分发机制
木溪bo
2018/12/27
8501
这次,我把Android事件分发机制翻了个遍
作者:积木zz 链接:https://juejin.im/post/5eb3e0d6f265da7c002028cd 以下是原文:
胡飞洋
2020/07/23
2.2K0
这次,我把Android事件分发机制翻了个遍
高级 UI 成长之路 (二) 深入理解 Android 8.0 View 触摸事件分发机制
在上一篇文章中我们介绍了 View 的基础知识以及 View 滑动的实现,本篇将为大家带来 View 的一个核心知识点 事件分发机制。事件分发机制不仅仅是核心知识点也是 Android 中的一个难点,下面我们就从源码的角度来分析事件的传递还有最后是如何解决滑动冲突的。
做个快乐的码农
2021/11/12
7510
高级 UI 成长之路 (二) 深入理解 Android 8.0 View 触摸事件分发机制
相关推荐
拇指记者打探事件分发机制背后的秘密(下)
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
本文部分代码块支持一键运行,欢迎体验
本文部分代码块支持一键运行,欢迎体验