本文为大家分享了Android使用TouchDelegate增加View触摸范围的方法,供大家参考,具体内容如下
还不知道TouchDelegate这个东西的可以先看一下API,这里大致说一下它的作用:假设有两个View,分别是v1,v2,我们可以通过v1的setTouchDelegate(bounds, v2)来委派触摸事件,其中bounds是一个Rect。v1中,落在这个范围的TouchEvent都会传给v2。
既然是这样,那我们可以通过设置某个view的parent的touchDelegate来达到扩大这个view触摸范围的目的。关键是什么时候去执行parent.setTouchDelegate()方法呢?要设置这个委派,必须得知道当前view大小以及它在parent的位置。而这些数据都是在onLayout才能确定(注:如果不是自定义View,只是在Activity中设置,请将这些操作置于onWindowFocusChanged()方法中)。至此,实现的思路已经很清晰了,我们通过自定义一个Button来检验一下,下面开始上代码:
为了方便在xml中使用我们自定义的View,并且可以自定义扩大的触摸范围,我们再自定义一个attrs,res/values/attrs.xml:
1
2
3
4
5
6
7
8
9
10
|
<? xml version = "1.0" encoding = "utf-8" ?>
< resources >
< declare-styleable name = "LargeTouchableAreaView" >
< attr name = "addition" format = "dimension" />
< attr name = "additionBottom" format = "dimension" />
< attr name = "additionLeft" format = "dimension" />
< attr name = "additionRight" format = "dimension" />
< attr name = "additionTop" format = "dimension" />
</ declare-styleable >
</ resources >
|
Button实现:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
|
public class LargeTouchableAreasButton extends Button {
private final int TOUCH_ADDITION = 0 ;
private int mTouchAdditionBottom = 0 ;
private int mTouchAdditionLeft = 0 ;
private int mTouchAdditionRight = 0 ;
private int mTouchAdditionTop = 0 ;
private int mPreviousLeft = - 1 ;
private int mPreviousRight = - 1 ;
private int mPreviousBottom = - 1 ;
private int mPreviousTop = - 1 ;
public LargeTouchableAreasButton(Context context) {
super (context);
}
public LargeTouchableAreasButton(Context context, AttributeSet attrs) {
super (context, attrs);
init(context, attrs);
}
public LargeTouchableAreasButton(Context context, AttributeSet attrs,
int defStyle) {
super (context, attrs, defStyle);
init(context, attrs);
}
private void init(Context context, AttributeSet attrs) {
TypedArray a = context.obtainStyledAttributes(attrs,
R.styleable.LargeTouchableAreaView);
int addition = ( int ) a.getDimension(
R.styleable.LargeTouchableAreaView_addition, TOUCH_ADDITION);
mTouchAdditionBottom = addition;
mTouchAdditionLeft = addition;
mTouchAdditionRight = addition;
mTouchAdditionTop = addition;
mTouchAdditionBottom = ( int ) a.getDimension(
R.styleable.LargeTouchableAreaView_additionBottom,
mTouchAdditionBottom);
mTouchAdditionLeft = ( int ) a.getDimension(
R.styleable.LargeTouchableAreaView_additionLeft,
mTouchAdditionLeft);
mTouchAdditionRight = ( int ) a.getDimension(
R.styleable.LargeTouchableAreaView_additionRight,
mTouchAdditionRight);
mTouchAdditionTop = ( int ) a.getDimension(
R.styleable.LargeTouchableAreaView_additionTop,
mTouchAdditionTop);
a.recycle();
}
@Override
protected void onLayout( boolean changed, int left, int top, int right,
int bottom) {
super .onLayout(changed, left, top, right, bottom);
if (left != mPreviousLeft || top != mPreviousTop
|| right != mPreviousRight || bottom != mPreviousBottom) {
mPreviousLeft = left;
mPreviousTop = top;
mPreviousRight = right;
mPreviousBottom = bottom;
final View parent = (View) this .getParent();
parent.setTouchDelegate( new TouchDelegate( new Rect(left
- mTouchAdditionLeft, top - mTouchAdditionTop, right
+ mTouchAdditionRight, bottom + mTouchAdditionBottom), this ));
}
}
}
|
然后在具体要使用到这个Button的xml中加上以下代码:
1
|
xmlns:lta="http://schemas.android.com/apk/res/com.xxx.xxx"
|
其中"lta"这个名字可以随便取,最后的是你的app包名。
最后在这个Button中定义希望增大的尺寸:
1
2
3
4
|
< com.xxx.LargeTouchableAreasButton
android:layout_width = "wrap_content"
android:layout_height = "wrap_content"
lta:addition = "30dp" />
|
大功告成。
但这个自定义的View并不是完美的,还存在以下问题:
1、必须保证parent足够大,如果自定义的范围超出parent的大小,则超出的那部分无效。
2、一个parent只能设置一个触摸委派,设置多个时,只有最后设置的child有效。如果希望一个view能设置多个委派,需要再自定义parent,具体方法可参考:链接地址
总而言之,要触发委派,必须保证parent接收到了触摸事件,并且落在了你定义的范围内。
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持服务器之家。
原文链接:https://blog.csdn.net/sgwhp/article/details/10963383