View的requestDisallowInterceptTouchEvent对事件的影响
思路:1.定义一个LinearLayout,重写其dispatchTouchEvent和onTouchEvent
2.定义一个View,重写dispatchTouchEvent和onTouchEvent
3.在Activity中重写dispatchTouchEvent和onTouchEvent
源码:
MainActivity类
package com.example.eventtestdemo;
import android.os.Bundle;
import android.app.Activity;
import android.util.Log;
import android.view.Menu;
import android.view.MotionEvent;
/**
*
* @author huozhenpeng
* 事件的分发测试分析
*
*
*/
public class MainActivity extends Activity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
@Override
public boolean dispatchTouchEvent(MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
Log.e("abc", "activity------dispatch---->down");
break;
case MotionEvent.ACTION_MOVE:
Log.e("abc", "activity-----dispatch----->move");
break;
case MotionEvent.ACTION_UP:
Log.e("abc", "activity-----dispatch----->up");
break;
default:
break;
}
return super.dispatchTouchEvent(event);
}
@Override
public boolean onTouchEvent(MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
Log.e("abc", "activity------touch---->down");
break;
case MotionEvent.ACTION_MOVE:
Log.e("abc", "activity-----touch----->move");
break;
case MotionEvent.ACTION_UP:
Log.e("abc", "activity-----touch----->up");
break;
default:
break;
}
return super.onTouchEvent(event);
}
}
LinearLayout1类
package com.example.eventtestdemo;
import android.content.Context;
import android.util.AttributeSet;
import android.util.Log;
import android.view.MotionEvent;
import android.widget.LinearLayout;
public class LinearLayout1 extends LinearLayout{
public LinearLayout1(Context context, AttributeSet attrs, int defStyleAttr,
int defStyleRes) {
super(context, attrs, defStyleAttr, defStyleRes);
}
public LinearLayout1(Context context, AttributeSet attrs) {
super(context, attrs);
}
public LinearLayout1(Context context) {
super(context);
}
@Override
public boolean dispatchTouchEvent(MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
Log.e("abc", "LinearLayout1------dispatch---->down");
break;
case MotionEvent.ACTION_MOVE:
Log.e("abc", "LinearLayout1-----dispatch----->move");
break;
case MotionEvent.ACTION_UP:
Log.e("abc", "LinearLayout1-----dispatch----->up");
break;
default:
break;
}
return super.dispatchTouchEvent(event);
}
@Override
public boolean onTouchEvent(MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
Log.e("abc", "LinearLayout1------touch---->down");
break;
case MotionEvent.ACTION_MOVE:
Log.e("abc", "LinearLayout1-----touch----->move");
break;
case MotionEvent.ACTION_UP:
Log.e("abc", "LinearLayout1-----touch----->up");
break;
default:
break;
}
return super.onTouchEvent(event);
}
}
View1类
package com.example.eventtestdemo;
import android.content.Context;
import android.util.AttributeSet;
import android.util.Log;
import android.view.MotionEvent;
import android.view.View;
public class View1 extends View{
public View1(Context context, AttributeSet attrs, int defStyleAttr,
int defStyleRes) {
super(context, attrs, defStyleAttr, defStyleRes);
}
public View1(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
public View1(Context context, AttributeSet attrs) {
super(context, attrs);
}
public View1(Context context) {
super(context);
}
@Override
public boolean dispatchTouchEvent(MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
Log.e("abc", "View1------dispatch---->down");
break;
case MotionEvent.ACTION_MOVE:
Log.e("abc", "View1-----dispatch----->move");
break;
case MotionEvent.ACTION_UP:
Log.e("abc", "View1-----dispatch----->up");
break;
default:
break;
}
return super.dispatchTouchEvent(event);
}
@Override
public boolean onTouchEvent(MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
Log.e("abc", "View1------touch---->down");
break;
case MotionEvent.ACTION_MOVE:
Log.e("abc", "View1-----touch----->move");
break;
case MotionEvent.ACTION_UP:
Log.e("abc", "View1-----touch----->up");
break;
default:
break;
}
return super.onTouchEvent(event);
}
}
1.如果对事件不做任何处理。
2.如果LinearLayout1处理了down事件之后(在onTouchEvent中)
private boolean flag=false;
@Override
public boolean onTouchEvent(MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
Log.e("abc", "LinearLayout1------touch---->down");
flag=true;
break;
case MotionEvent.ACTION_MOVE:
Log.e("abc", "LinearLayout1-----touch----->move");
flag=false;
break;
case MotionEvent.ACTION_UP:
Log.e("abc", "LinearLayout1-----touch----->up");
flag=false;
break;
default:
break;
}
// return super.onTouchEvent(event);
return flag;
}
就是说如果view1没有处理down事件,而linearlayout1处理了down事件,那么后续事件就传递不到view1了,那么如何让view1处理down事件,而LinearLayout1处理move事件呢?
子view可以通过在dispatchTouchEvent中通过requestDisallowInterceptTouchEvent改变父容器的dispatchTouchEvent的返回值。
3.让LinearLayout1处理move事件和up事件,不处理down事件,而子view处理down事件。
LinearLayout1代码:
private boolean flag=false;
@Override
public boolean onInterceptTouchEvent(MotionEvent ev) {
switch (ev.getAction()) {
case MotionEvent.ACTION_DOWN:
Log.e("abc", "LinearLayout1------Intercept---->down");
flag=false;
break;
case MotionEvent.ACTION_MOVE:
Log.e("abc", "LinearLayout1-----Intercept----->move");
flag=true;
break;
case MotionEvent.ACTION_UP:
Log.e("abc", "LinearLayout1-----Intercept----->up");
flag=true;
break;
default:
break;
}
// return super.onInterceptTouchEvent(ev);
return flag;
}
private boolean flag=false;
@Override
public boolean onTouchEvent(MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
Log.e("abc", "View1-----touch----->down");
flag=true;
break;
case MotionEvent.ACTION_MOVE:
Log.e("abc", "View1-----touch----->move");
break;
case MotionEvent.ACTION_UP:
Log.e("abc", "View1-----touch----->up");
break;
default:
break;
}
// return super.onTouchEvent(event);
return flag;
}
运行结果:
view1处理了down事件,LinearLayout1虽然拦截了move事件但是在onTouchEvent中并没有处理,所以move事件会回传到activity.
4.requestDisallowInterceptTouchEvent
修改代码:
@Override
public boolean dispatchTouchEvent(MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
Log.e("abc", "View1------dispatch---->down");
getParent().requestDisallowInterceptTouchEvent(true);
break;
case MotionEvent.ACTION_MOVE:
Log.e("abc", "View1-----dispatch----->move");
getParent().requestDisallowInterceptTouchEvent(false);
break;
case MotionEvent.ACTION_UP:
Log.e("abc", "View1-----dispatch----->up");
break;
default:
break;
}
return super.dispatchTouchEvent(event);
}
可以看到view1又接收到了move事件。