现在的智能手机不敢说百分百的都是触摸屏,也应该是百分之九九以上为触摸屏了,触摸屏为我们操作无键盘、无鼠标的手机系统带来了很多的便利。当用户触摸屏幕时会产生很多的触摸事件,down、up、move等等。View类有个View.OnTouchListener内部接口,通过重写他的onTouch(View v, MotionEvent event)方法,我们可以处理一些touch事件,如下:
OnTouch提供的事件还是相对较简单,如果需要处理一些复杂的手势,用这个接口就会很麻烦,因为我们要根据用户触摸的轨迹去判断是什么手势。Android sdk给我们提供了GestureDetector(Gesture:手势Detector:识别)类,通过这个类我们可以识别很多的手势。
public class GestureDetector extends Object
java.lang.Object
android.view.GestureDetector
GestureDetector属于android.view包,android还提供了android.gesture包支持更多的手势操作,以后我们会介绍到。官方的介绍中使用了GestureDetectorCompat处理手势识别,为什么使用GestureDetectorCompat替换了GestureDetector呢,官方的是这样解释的:
GestureDetectorCompat实例化有下面两种方法:
GestureDetector类对外提供了两个接口:OnGestureListener,OnDoubleTapListener,还有一个内部类SimpleOnGestureListener;SimpleOnGestureListener类是GestureDetector提供给我们的一个更方便的响应不同手势的类,它实现了上述两个接口,该类是static class,也就是说它实际上是一个外部类,我们可以在外部继承这个类,重写里面的手势处理方法。因此实现手势识别有两种方法,一种实现OnGestureListener接口,另一种是使用SimpleOnGestureListener类。
OnGestureListener有下面的几个动作:
按下(onDown): 刚刚手指接触到触摸屏的那一刹那,就是触的那一下。
抛掷(onFling): 手指在触摸屏上迅速移动,并松开的动作。
长按(onLongPress): 手指按在持续一段时间,并且没有松开。
滚动(onScroll): 手指在触摸屏上滑动。
按住(onShowPress): 手指按在触摸屏上,它的时间范围在按下起效,在长按之前。
抬起(onSingleTapUp):手指离开触摸屏的那一刹那。
使用OnGestureListener接口,这样需要重载OnGestureListener接口所有的方法,适合监听所有的手势,正如官方文档提到的“Detecing All Supported Gestures”。
这样会造成有些手势动作我们用不到,但是还要重载。SimpleOnGestureListener类的出现为我们解决了这个问题,如果你想“Detecting a Subset of Supported Gestures”,SimpleOnGestureListener是最好的选择。
最后了我们也解释两个问题:
1、onTouchEvent中为什么使用了MotionEventCompat,而不直接使用MotionEvent。因为MotionEventCompat使更多的Action适配到API 4。
2、Android的view怎么使用手势,方法如下:
参考:
http://developer.android.com/reference/android/view/GestureDetector.html
http://developer.android.com/training/gestures/detector.html
另外补充:
- public class ActivityMain extends Activity implements GestureDetector.OnGestureListener {
- GestureDetector detector;
- /**
- * Called when the activity is first created.
- */
- @Override
- public void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- setContentView(R.layout.main);
- //构造GestureDetector;Context context, OnGestureListener listener
- detector = new GestureDetector(this, this);
- detector.setOnDoubleTapListener(new GestureDetector.OnDoubleTapListener() {
- //短快的点击算一次单击
- @Override
- public boolean onSingleTapConfirmed(MotionEvent e) {
- System.out.println("onSingleTapConfirmed");
- return false;
- }
- //双击时产生一次
- @Override
- public boolean onDoubleTap(MotionEvent e) {
- System.out.println("onDoubleTap");
- return false;
- }
- //双击时产生两次
- @Override
- public boolean onDoubleTapEvent(MotionEvent e) {
- System.out.println("onDoubleTapEvent");
- return false;
- }
- });
- }
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- return detector.onTouchEvent(event);
- }
- // 用户轻触触摸屏,由1个MotionEvent ACTION_DOWN触发
- @Override
- public boolean onDown(MotionEvent e) {
- System.out.println("onDown");
- return false;
- }
- // 用户轻触触摸屏,尚未松开或拖动,由一个1个MotionEvent ACTION_DOWN触发
- // 注意和onDown()的区别,强调的是没有松开或者拖动的状态
- @Override
- public void onShowPress(MotionEvent e) {
- }
- //用户(轻触触摸屏后)松开,由一个1个MotionEvent ACTION_UP触发
- @Override
- public boolean onSingleTapUp(MotionEvent e) {
- System.out.println("onSingleTapUp");
- return false;
- }
- // 用户按下触摸屏,并拖动,由1个MotionEvent ACTION_DOWN, 多个ACTION_MOVE触发
- @Override
- public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) {
- System.out.println("onScroll");
- return false;
- }
- // 用户长按触摸屏,由多个MotionEvent ACTION_DOWN触发
- @Override
- public void onLongPress(MotionEvent e) {
- System.out.println("onLongPress" + e.getEventTime());
- }
- //用户按下触摸屏、快速移动后松开,由1个MotionEvent ACTION_DOWN, 多个ACTION_MOVE, 1个ACTION_UP触发
- @Override
- public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
- System.out.println("onFling: " + (e1.getX() - e2.getX()) + " " + (e1.getY() - e2.getY()) + " " + velocityX + " " + velocityY);
- System.out.println(e1.getY());
- return false;
- }
- }
转自:http://blog.csdn.net/xyz_lmn/article/details/16826669
http://maxuefeng.blog.51cto.com/1876326/564128