Android View事件分发机制理解
Posted wjinhhua
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Android View事件分发机制理解相关的知识,希望对你有一定的参考价值。
MainActiviity
public class MainActivity extends Activity
private TextView tv;
@Override
protected void onCreate(Bundle savedInstanceState)
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
tv = (TextView) findViewById(R.id.tv);
init();
private void init()
tv.setOnTouchListener(new OnTouchListener()
@Override
public boolean onTouch(View v, MotionEvent event)
switch (event.getAction())
case MotionEvent.ACTION_DOWN:
System.out.println("-----------DOWN-------");
break;
case MotionEvent.ACTION_UP:
System.out.println("-----------UP-------");
break;
default:
break;
//return false;
return true;
);
main.xml
<com.example.testevent.MyLinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context="com.example.testevent.MainActivity" >
<com.example.testevent.MyTextView
android:id="@+id/tv"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/hello_world" />
</com.example.testevent.MyLinearLayout>
其中MyLinearLayout继承LinearLayout
public class MyLinearLayout extends LinearLayout
@SuppressLint("NewApi")
public MyLinearLayout(Context context, AttributeSet attrs, int defStyleAttr)
super(context, attrs, defStyleAttr);
// TODO Auto-generated constructor stub
public MyLinearLayout(Context context, AttributeSet attrs)
super(context, attrs);
// TODO Auto-generated constructor stub
public MyLinearLayout(Context context)
super(context);
// TODO Auto-generated constructor stub
@Override
public boolean onTouchEvent(MotionEvent event)
// TODO Auto-generated method stub
int action = event.getAction();
switch (action)
case MotionEvent.ACTION_DOWN:
System.out.println("MyLinearLayout ---ACTION_DOWN ---");
break;
case MotionEvent.ACTION_UP:
System.out.println("MyLinearLayout ---ACTION_UP ---");
break;
default:
break;
System.out.println("MyLinearLayout ---onTouchEvent ---");
return true;
//return super.onTouchEvent(event);
@Override
public boolean onInterceptTouchEvent(MotionEvent ev)
// TODO Auto-generated method stub
System.out.println("MyLinearLayout ---onInterceptTouchEvent ---");
return super.onInterceptTouchEvent(ev);
//return true;
@Override
public boolean dispatchTouchEvent(MotionEvent ev)
// TODO Auto-generated method stub
System.out.println("MyLinearLayout ---dispatchTouchEvent ---");
return super.dispatchTouchEvent(ev);
//return true;
MyTextView继承TextView
public class MyTextView extends TextView
public MyTextView(Context context, AttributeSet attrs)
super(context, attrs);
// TODO Auto-generated constructor stub
public MyTextView(Context context)
super(context);
// TODO Auto-generated constructor stub
public MyTextView(Context context, AttributeSet attrs, int defStyleAttr)
super(context, attrs, defStyleAttr);
// TODO Auto-generated constructor stub
@SuppressLint("ClickableViewAccessibility")
@Override
public boolean onTouchEvent(MotionEvent event)
// TODO Auto-generated method stub
int action = event.getAction();
switch (action)
case MotionEvent.ACTION_DOWN:
System.out.println("MyTextView ---ACTION_DOWN ---");
break;
case MotionEvent.ACTION_UP:
System.out.println("MyTextView ---ACTION_UP ---");
break;
default:
break;
System.out.println("MyTextView ---onTouchEvent ---");
return super.onTouchEvent(event);
// return true;
@Override
public boolean dispatchTouchEvent(MotionEvent event)
// TODO Auto-generated method stub
System.out.println("MyTextView ---dispatchTouchEvent ---");
return super.dispatchTouchEvent(event);
//return true;
先看第一张图
通过图我们可以看到事件分发默认情况是由父控件捕捉向子控件传递,子控件不消费(但可以做自己的其他逻辑),最后再回传到父控件,父控件进行消费。
当子控件消费(onTouchEvent返回true)后,不再回传给父控件。这有点类似java的继承关系。如果父控件拦截(onInterceptTouchEvent返回true)之后,将不会传递给子控件。
再看第二张
通过图我们可以看到setOnTouchListener的优先级高于onTouchEvent。
最后,为了方便大家理解,我贴一下整理的输出内容,大家看图不明白,可以对着输出内容来理解
默认:
10-05 04:07:55.076: I/System.out(2502): MyLinearLayout ---dispatchTouchEvent ---
10-05 04:07:55.076: I/System.out(2502): MyLinearLayout ---onInterceptTouchEvent ---
10-05 04:07:55.076: I/System.out(2502): MyTextView ---dispatchTouchEvent ---
10-05 04:07:55.076: I/System.out(2502): MyTextView ---ACTION_DOWN ---
10-05 04:07:55.076: I/System.out(2502): MyTextView ---onTouchEvent ---
10-05 04:07:55.076: I/System.out(2502): MyLinearLayout ---ACTION_DOWN ---
10-05 04:07:55.076: I/System.out(2502): MyLinearLayout ---onTouchEvent ---
MyTextView-- onTouchEvent----return true===
10-05 04:14:15.616: I/System.out(2548): MyLinearLayout ---dispatchTouchEvent ---
10-05 04:14:15.616: I/System.out(2548): MyLinearLayout ---onInterceptTouchEvent ---
10-05 04:14:15.616: I/System.out(2548): MyTextView ---dispatchTouchEvent ---
10-05 04:14:15.616: I/System.out(2548): MyTextView ---ACTION_DOWN ---
10-05 04:14:15.616: I/System.out(2548): MyTextView ---onTouchEvent ---
10-05 04:14:15.696: I/System.out(2548): MyLinearLayout ---dispatchTouchEvent ---
10-05 04:14:15.696: I/System.out(2548): MyLinearLayout ---onInterceptTouchEvent ---
10-05 04:14:15.696: I/System.out(2548): MyTextView ---dispatchTouchEvent ---
10-05 04:14:15.696: I/System.out(2548): MyTextView ---ACTION_UP ---
10-05 04:14:15.696: I/System.out(2548): MyTextView ---onTouchEvent ---
MyTextView-- dispatchTouchEvent----return true=== //onTouchEvent&&dispatchTouchEvent----return true===
10-05 04:16:39.676: I/System.out(2591): MyLinearLayout ---dispatchTouchEvent ---
10-05 04:16:39.676: I/System.out(2591): MyLinearLayout ---onInterceptTouchEvent ---
10-05 04:16:39.676: I/System.out(2591): MyTextView ---dispatchTouchEvent ---
10-05 04:16:39.746: I/System.out(2591): MyLinearLayout ---dispatchTouchEvent ---
10-05 04:16:39.746: I/System.out(2591): MyLinearLayout ---onInterceptTouchEvent ---
10-05 04:16:39.746: I/System.out(2591): MyTextView ---dispatchTouchEvent ---
MyLinearLayout-- onTouchEvent----return true===
10-05 04:22:09.476: I/System.out(2677): MyLinearLayout ---dispatchTouchEvent ---
10-05 04:22:09.476: I/System.out(2677): MyLinearLayout ---onInterceptTouchEvent ---
10-05 04:22:09.476: I/System.out(2677): MyTextView ---dispatchTouchEvent ---
10-05 04:22:09.476: I/System.out(2677): MyTextView ---ACTION_DOWN ---
10-05 04:22:09.476: I/System.out(2677): MyTextView ---onTouchEvent ---
10-05 04:22:09.476: I/System.out(2677): MyLinearLayout ---ACTION_DOWN ---
10-05 04:22:09.476: I/System.out(2677): MyLinearLayout ---onTouchEvent ---
10-05 04:22:09.546: I/System.out(2677): MyLinearLayout ---dispatchTouchEvent ---
10-05 04:22:09.546: I/System.out(2677): MyLinearLayout ---ACTION_UP ---
10-05 04:22:09.546: I/System.out(2677): MyLinearLayout ---onTouchEvent ---
MyLinearLayout-- onInterceptTouchEvent----return true
10-05 04:28:40.086: I/System.out(2720): MyLinearLayout ---dispatchTouchEvent ---
10-05 04:28:40.096: I/System.out(2720): MyLinearLayout ---onInterceptTouchEvent ---
10-05 04:28:40.096: I/System.out(2720): MyLinearLayout ---ACTION_DOWN ---
10-05 04:28:40.096: I/System.out(2720): MyLinearLayout ---onTouchEvent ---
MyLinearLayout-- dispatchTouchEvent----return true===
10-05 04:31:52.536: I/System.out(2852): MyLinearLayout ---dispatchTouchEvent ---
10-05 04:31:52.636: I/System.out(2852): MyLinearLayout ---dispatchTouchEvent ---
-------------------------------------------------------
setOnTouchListener--- return false=======
默认:
10-05 04:48:19.746: I/System.out(3243): MyLinearLayout ---dispatchTouchEvent ---
10-05 04:48:19.746: I/System.out(3243): MyLinearLayout ---onInterceptTouchEvent ---
10-05 04:48:19.746: I/System.out(3243): MyTextView ---dispatchTouchEvent ---
10-05 04:48:19.746: I/System.out(3243): -----------DOWN-------
10-05 04:48:19.746: I/System.out(3243): MyTextView ---ACTION_DOWN ---
10-05 04:48:19.746: I/System.out(3243): MyTextView ---onTouchEvent ---
10-05 04:48:19.746: I/System.out(3243): MyLinearLayout ---ACTION_DOWN ---
10-05 04:48:19.746: I/System.out(3243): MyLinearLayout ---onTouchEvent ---
MyTextView--dispatchTouchEvent----return true
10-05 05:00:27.706: I/System.out(3419): MyLinearLayout ---dispatchTouchEvent ---
10-05 05:00:27.706: I/System.out(3419): MyLinearLayout ---onInterceptTouchEvent ---
10-05 05:00:27.706: I/System.out(3419): MyTextView ---dispatchTouchEvent ---
10-05 05:00:27.786: I/System.out(3419): MyLinearLayout ---dispatchTouchEvent ---
10-05 05:00:27.786: I/System.out(3419): MyLinearLayout ---onInterceptTouchEvent ---
10-05 05:00:27.786: I/System.out(3419): MyTextView ---dispatchTouchEvent ---
MyTextView--onTouchEvent----return true
10-05 05:03:39.846: I/System.out(3462): MyLinearLayout ---dispatchTouchEvent ---
10-05 05:03:39.846: I/System.out(3462): MyLinearLayout ---onInterceptTouchEvent ---
10-05 05:03:39.846: I/System.out(3462): MyTextView ---dispatchTouchEvent ---
10-05 05:03:39.846: I/System.out(3462): -----------DOWN-------
10-05 05:03:39.846: I/System.out(3462): MyTextView ---ACTION_DOWN ---
10-05 05:03:39.846: I/System.out(3462): MyTextView ---onTouchEvent ---
10-05 05:03:39.926: I/System.out(3462): MyLinearLayout ---dispatchTouchEvent ---
10-05 05:03:39.936: I/System.out(3462): MyLinearLayout ---onInterceptTouchEvent ---
10-05 05:03:39.936: I/System.out(3462): MyTextView ---dispatchTouchEvent ---
10-05 05:03:39.936: I/System.out(3462): -----------UP-------
10-05 05:03:39.936: I/System.out(3462): MyTextView ---ACTION_UP ---
10-05 05:03:39.936: I/System.out(3462): MyTextView ---onTouchEvent ---
MyLinearLayout-- dispatchTouchEvent----return true===== MyTextView-- setOnTouchListener无效
10-05 04:31:52.536: I/System.out(2852): MyLinearLayout ---dispatchTouchEvent ---
10-05 04:31:52.636: I/System.out(2852): MyLinearLayout ---dispatchTouchEvent ---
MyLinearLayout-- onInterceptTouchEvent----return true===== MyTextView-- setOnTouchListener无效
10-05 04:28:40.086: I/System.out(2720): MyLinearLayout ---dispatchTouchEvent ---
10-05 04:28:40.096: I/System.out(2720): MyLinearLayout ---onInterceptTouchEvent ---
10-05 04:28:40.096: I/System.out(2720): MyLinearLayout ---ACTION_DOWN以上是关于Android View事件分发机制理解的主要内容,如果未能解决你的问题,请参考以下文章