[饼干]安卓小秘密-不扩大view宽高增加其可触控范围

xiaoxiao2021-02-28  79

原文地址:http://halohoop.com/2017/06/06/cookies-android-touchdelegate/

开门撞山:

今天我要记录的是TouchDelegate,有很多人应该都不知道还有这个东西,知道的孩子都没你们事了,都散了散了吧,不知道的请往下看。其实也不算什么秘密,只要你仔细的走过神迹一样的事件分发的源码,很容易发现的。

场景:

如下图,有这样一个场景,View a 需要有这么大,比如可以是一个按钮,UI要求显示View a的黑框部分,但是为了更好的用户体验,我们一般会增大其触控范围,比如点击绿框中都能够触发a的事件,咋做?(说好的不卖关子的呢?)

Don’t do:

增加a的Padding? 后期如果修改bgColor,那么不好了,绿色框内全变色。套多一层透明的FrameLayout? 增加布局复杂度,我TM一脚飞死你。 自定义view限制绘制区域? 写完了?你很棒!但是你可以收拾包袱走人了。

What should do (How to use TouchDelegate):

要学会站在巨人的肩膀,要知道,“你遇到的,巨人也会遇到”,巨人给我们留下了TouchDelegate

直接上菜:

注意方法ViewGroup.setTouchDelegate(Rect,View)

以下代码出自我一个自定义View—UsoppBubble.java

@Override protected void onLayout(boolean changed, int left, int top, int right, int bottom) { super.onLayout(changed, left, top, right, bottom); if (changed) { float largedSize = (bottom - top) * mTouchAreaLargerRatio;//乘以放大倍数 int deltaY = (int) (largedSize - (bottom - top)); int deltaX = largedSize > (right - left) ? (int) (largedSize - (right - left)) : 0; ViewGroup vg = (ViewGroup) getParent(); Rect rect = new Rect(left - deltaX, top - deltaY, right + deltaX, bottom + deltaY); //构建出来的Rect对象就相当于绿色框框,而this就是这个view的实例。 vg.setTouchDelegate(new TouchDelegate(rect, this)); } }

相信上述代码是极度容易的,ViewGroup.setTouchDelegate(Rect,View)接受两个参数:

可触控区域。谁(哪个子view)需要用这个可触控区域。

实际应用场景

QQ消息气泡可触控区域

当然我也模仿qq做了一个自己的消息气泡版本

小米贴边悬浮球点击唤醒

锤子的闪念胶囊贴边点击唤醒

总结

View.setTouchDelegate(Rect,View),这句还不够吗?还要我怎样?你遇到的,巨人也会遇到,如果换位思考一下,你就是“巨人”,那么子View获取到的触摸事件是从ViewGroup分发下来的,那么如果在分发之前加一些条件判断,比如区域什么的,那么TouchDelegate这玩意儿是不是就出来了呢?Stay hungry stay foolish!

仅作知识点记录,如有疏漏,全(欢)都(迎)怪(指)你(正)。


确保这文章被看完了,我在上面留了一个无伤大雅的bug,不知道有人发现没有,那就是:

setTouchDelegate其实是View的方法。而ViewGroup : View,无伤大雅。

顺便说一下,科学上网之后浏览本站文章可以评论。

转载请注明原文地址: https://www.6miu.com/read-25784.html

最新回复(0)