面试官:View的事件分发我必问,不会给你一个pass(1),2024年最新面试流程4轮技术面+1轮HR

先自我介绍一下,小编浙江大学毕业,去过华为、字节跳动等大厂,目前阿里P7

深知大多数程序员,想要提升技能,往往是自己摸索成长,但自己不成体系的自学效果低效又漫长,而且极易碰到天花板技术停滞不前!

因此收集整理了一份《2024年最新Android移动开发全套学习资料》,初衷也很简单,就是希望能够帮助到想自学提升又不知道该从何学起的朋友。
img
img
img
img
img
img
img

既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,涵盖了95%以上Android开发知识点,真正体系化!

由于文件比较多,这里只是将部分目录截图出来,全套包含大厂面经、学习笔记、源码讲义、实战项目、大纲路线、讲解视频,并且后续会持续更新

如果你需要这些资料,可以添加V获取:vip204888 (备注Android)
img

正文

递归?那你讲讲事件分发如何通过递归实现的

递归分为递过程和归过程。

图 2

当 UI 事件来临时,它首先被分发到 activity,activity 分发给 window,window 再分发给 view 树。分发过程 通过 dispatchTouchEvent 函数完成。它的返回值是 Boolean,如果为 true,表示事件被消费;为 false,表示事件未被消费。 dispatchTouchEvent 在不同的分发阶段有不同的作用

对于 View 而言,它没有子 View,View 自己的 dispatchTouchEvent 实际上会执行到 onTouchEvent 来进行事件的消费

图 7

对于 ViewGroup 而言,它重写了 dispatchTouchEvent, 先将事件分发给自己的子 View。

如果子 View 可以消费事件, dispatchTouchEvent 直接返回 true;如果子 View 都不消费事件,就调用自己的 onTouchEvent 来进行事件的消费。(ViewGroup 的 onTouchEvent 实际上就是 super.dispatchTouchEvent)

图 8

这样,Activity 通过调用 Window#superDispatchTouchEvent 方法将事件分发给 Window,Window 调用 DecorView#dispatchTouchEvent 将事件分发给 decorView。DecorView 是一个 ViewGroup,它又将事件分发给子 ViewGroup 和子 View。当有一个 View 消费掉事件时,他就会向上返回,通过递归链返回到 Activity#dispatchTouchEvent。最终完成事件的分发,消费和返回。

每一个事件的分发都需要递归吗?


那我问你,每一个事件的分发都需要递归吗?用户一次操作会产生大量的 UI 事件,频繁的递归遍历不会对性能有影响吗?

当然会有!所以 Android 为了避免每个事件都递归遍历,定义了一个 【事件序列】 的概念:将用户每一次触摸屏幕 --> 移动屏幕–>抬起手指称为一个事件序列。

一个事件序列必然包含 ACTION_DOWN,ACTION_MOVE,ACTION_UP 等多个事件。其中 ACTION_MOVE 数量不确定,ACTION_DOWN 和 ACTION_UP 数量则为 1

当接收到 ACTION_DOMN 事件时,意味着一次完成事件序列的开始。ViewGroup 会通过递归遍历找到 View 树中真正对事件进行消费的子 View,并将其保存。这之后接收到 ACTION_MOVE 和 ACTION_DOWN 事件时,则跳过递归遍历的过程,直接交给之前保存的消费者。当下一次 ACTION_DOWN 事件来临时重置整个过程

图 9

如何在事件被分发前拦截


嗯,了解的还挺仔细的嘛。那如果有一个 view 可以消费事件,但我想在事件分发给它之前进行拦截,该怎么做?

ViewGroup 提供了一个拦截事件的函数onInterceptTouchEvent,返回值为 Boolean。 表示是否拦截事件。如果拦截,则会调用 onTouchEvent 进行事件的进一步处理。

图 10

如何处理滑动冲突


可以,我看你理论掌握的差不多了,平常有遇到滑动冲突的问题吗?你是怎么处理滑动冲突的呢?

当父 View 和子 View 都有机会消费事件,但消费的时机不符合业务的需要(比如需要子 View 消费事件但父 View 先消费了),就会产生滑动冲突问题

解决办法一般分为内部拦截法外部拦截法

内部拦截法就是通过重写底层 View 的 dispatchTouchEvent 和 onTouchEvent 方法来决定是否消费事件。

外部拦截法就是重写 ViewGroup 的 dispatchTouchEvent 和 onInterceptTouchEvent 方法决定是否把事件分发给 View。

两种方法实际上就是对分发事件的 View 和被分发事件的 View 做不同的逻辑判断。

讲讲ACTION_CANCEL事件?


好的,看来平时没少解决滑动冲突的问题哈。刚才你提到了事件序列对吧,你说说 ACTION_CANCEL 事件是用来干嘛的?

前面我们提到在一个事件序列中,如果有 View 能够消费事件,那么该事件序列所有的后续事件都会交给这个 View 处理。但如果不希望它处理全部的后续事件怎么办?比如手指点击一个 Button 然后滑出它的边界。在这个事件序列中,我只希望 Button 处理它边界内的 move 事件。对于边界外的 move 事件,虽然它们都在一个事件序列中,但理论上不应该再传递给 Button 了。

图 4

可以看到,当我点击Button不动滑动到view之外时,Button实际上已经不响应事件了。这是怎么实现的呢?

ACTION_CANCEL 就是用来解决这个问题的。当 Button 判断 move 事件已经超出 view 的边界时,会将自己的 mPrivateFlags 置为 cancel 状态。等下次事件分发来临,Button 的父 ViewGroup 会检测 Button 的 mPrivateFlags,如果为 cancel 则将之前保存的 mFirstTouchTarget(也就是指向 Button 的引用) 设为 null,并向 Button 发送一个 ACTION_CANCEL 事件,表示以后不会再接受事件了。

图 11

不错不错,看来基础的 View 绘制和事件分发已经难不倒你了,下面我们来聊聊 Handler 相关面试题的知识吧~

最后,在这里我给大家提供一份自己收录整理上述Android技术体系图相关的高级面试进阶必刷文档(已整理成PDF模板),包含了Android 基础,进阶,架构、 Kotlin,Flutter,NDK,小程序,面试题,面经,都有收录,供君一览。

总结

最后为了帮助大家深刻理解Android相关知识点的原理以及面试相关知识,这里放上相关的我搜集整理的24套腾讯、字节跳动、阿里、百度2019-2021面试真题解析,我把技术点整理成了视频和PDF(实际上比预期多花了不少精力),包知识脉络 + 诸多细节

还有 高级架构技术进阶脑图、Android开发面试专题资料 帮助大家学习提升进阶,也节省大家在网上搜索资料的时间来学习,也可以分享给身边好友一起学习。

一线互联网面试专题

379页的Android进阶知识大全

379页的Android进阶知识大全

网上学习 Android的资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。希望这份系统化的技术体系对大家有一个方向参考。

2021年虽然路途坎坷,都在说Android要没落,但是,不要慌,做自己的计划,学自己的习,竞争无处不在,每个行业都是如此。相信自己,没有做不到的,只有想不到的。祝大家2021年万事大吉。

网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。

需要这份系统化的资料的朋友,可以添加V获取:vip204888 (备注Android)
img

一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!

需要这份系统化的资料的朋友,可以添加V获取:vip204888 (备注Android)
[外链图片转存中…(img-9zqul3Ah-1713384247583)]

一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!

  • 11
    点赞
  • 16
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值