日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

onInterceptTouchEvent和onTouchEvent调用时序

發布時間:2025/6/15 编程问答 46 豆豆
生活随笔 收集整理的這篇文章主要介紹了 onInterceptTouchEvent和onTouchEvent调用时序 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

onInterceptTouchEvent()是ViewGroup的一個方法,目的是在系統向該ViewGroup及其各個childView觸發onTouchEvent()之前對相關事件進行一次攔截,Android這么設計的想法也很好理解,由于ViewGroup會包含若干childView,因此需要能夠統一監控各種touch事件的機會,因此純粹的不能包含子view的控件是沒有這個方法的,如LinearLayout就有,TextView就沒有。?

onInterceptTouchEvent()使用也很簡單,如果在ViewGroup里覆寫了該方法,那么就可以對各種touch事件加以攔截。但是如何攔截,是否所有的touch事件都需要攔截則是比較復雜的,touch事件在onInterceptTouchEvent()和onTouchEvent以及各個childView間的傳遞機制完全取決于onInterceptTouchEvent()和onTouchEvent()的返回值。并且,針對down事件處理的返回值直接影響到后續move和up事件的接收和傳遞。?

關于返回值的問題,基本規則很清楚,如果return true,那么表示該方法消費了此次事件,如果return false,那么表示該方法并未處理完全,該事件仍然需要以某種方式傳遞下去繼續等待處理。

SDK給出的說明如下:

  • You will receive the down event here.
  • The down event will be handled either by a child of this view group, or given to your own onTouchEvent() method to handle; this means you should implement onTouchEvent() to return true, so you will continue to see the rest of the gesture (instead of looking for a parent view to handle it). Also, by returning true from onTouchEvent(), you will not receive any following events in onInterceptTouchEvent() and all touch processing must happen in onTouchEvent() like normal.
  • For as long as you return false from this function, each following event (up to and including the final up) will be delivered first here and then to the target's onTouchEvent().
  • If you return true from here, you will not receive any following events: the target view will receive the same event but with the action?ACTION_CANCEL, and all further events will be delivered to your onTouchEvent() method and no longer appear here.

?

由于onInterceptTouchEvent()的機制比較復雜,上面的說明寫的也比較復雜,總結一下,基本的規則是:

  • down事件首先會傳遞到onInterceptTouchEvent()方法
  • 如果該ViewGroup的onInterceptTouchEvent()在接收到down事件處理完成之后return false,那么后續的move, up等事件將繼續會先傳遞給該ViewGroup,之后才和down事件一樣傳遞給最終的目標view的onTouchEvent()處理。
  • 如果該ViewGroup的onInterceptTouchEvent()在接收到down事件處理完成之后return true,那么后續的move, up等事件將不再傳遞給onInterceptTouchEvent(),而是和down事件一樣傳遞給該ViewGroup的onTouchEvent()處理,注意,目標view將接收不到任何事件。
  • 如果最終需要處理事件的view的onTouchEvent()返回了false,那么該事件將被傳遞至其上一層次的view的onTouchEvent()處理。
  • 如果最終需要處理事件的view?的onTouchEvent()返回了true,那么后續事件將可以繼續傳遞給該view的onTouchEvent()處理。
  • ?

    下面用一個簡單的實驗說明上述復雜的規則。視圖自底向上共3層,其中LayoutView1和LayoutView2就是LinearLayout,?MyTextView就是TextView:

    對應的xml布局文件如下:

    <?xml?version="1.0"?encoding="utf-8"?>

    <com.touchstudy.LayoutView1?xmlns:android="http://schemas.android.com/apk/res/android"

    ????android:orientation="vertical"

    ????android:layout_width="fill_parent"

    ????android:layout_height="fill_parent"?>

    ????<com.touchstudy.LayoutView2

    ????????android:orientation="vertical"

    ????????android:layout_width="fill_parent"

    ????????android:layout_height="fill_parent"

    ????????android:gravity="center">

    ???????<com.touchstudy.MyTextView?

    ????????????android:layout_width="wrap_content"

    ????????????android:layout_height="wrap_content"

    ????????????android:id="@+id/tv"

    ????????????android:text="AB"

    ????????????android:textSize="40sp"

    ????????????android:textStyle="bold"

    ????????????android:background="#FFFFFF"

    ????????????android:textColor="#0000FF"/>

    ???</com.touchstudy.LayoutView2>

    </com.touchstudy.LayoutView1>

    ?

    下面看具體情況:

  • 1.???????onInterceptTouchEvent()處理down事件均返回falseonTouchEvent()處理事件均返回true
  • ------------------------------------------------------------------------------------------------------------------------------

    04-11 03:58:42.620: DEBUG/LayoutView1(614): onInterceptTouchEvent action:ACTION_DOWN

    04-11 03:58:42.620: DEBUG/LayoutView2(614): onInterceptTouchEvent action:ACTION_DOWN

    04-11 03:58:42.620: DEBUG/MyTextView(614): onTouchEvent action:ACTION_DOWN

    04-11 03:58:42.800: DEBUG/LayoutView1(614): onInterceptTouchEvent action:ACTION_MOVE

    04-11 03:58:42.800: DEBUG/LayoutView2(614): onInterceptTouchEvent action:ACTION_MOVE

    04-11 03:58:42.800: DEBUG/MyTextView(614): onTouchEvent action:ACTION_MOVE

    …… //省略過多的ACTION_MOVE

    04-11 03:58:43.130: DEBUG/LayoutView1(614): onInterceptTouchEvent action:ACTION_UP

    04-11 03:58:43.130: DEBUG/LayoutView2(614): onInterceptTouchEvent action:ACTION_UP

    04-11 03:58:43.150: DEBUG/MyTextView(614): onTouchEvent action:ACTION_UP

    ------------------------------------------------------------------------------------------------------------------------------

    這是最常見的情況,onInterceptTouchEvent并沒有做任何改變事件傳遞時序的操作,效果上和沒有覆寫該方法是一樣的。可以看到,各種事件的傳遞本身是自底向上的,次序是:LayoutView1->LayoutView2->MyTextView。注意,在onInterceptTouchEvent均返回false時,LayoutView1LayoutView2onTouchEvent并不會收到事件,而是最終傳遞給了MyTextView。

    ?

  • 2.?? ??LayoutView1onInterceptTouchEvent()處理down事件返回true
  • MyTextViewonTouchEvent()處理事件返回true

    ------------------------------------------------------------------------------------------------------------------------------

    04-11 03:09:27.589: DEBUG/LayoutView1(446): onInterceptTouchEvent action:ACTION_DOWN

    04-11 03:09:27.589: DEBUG/LayoutView1(446): onTouchEvent action:ACTION_DOWN

    04-11 03:09:27.629: DEBUG/LayoutView1(446): onTouchEvent action:ACTION_MOVE

    04-11 03:09:27.689: DEBUG/LayoutView1(446): onTouchEvent action:ACTION_MOVE

    …… //省略過多的ACTION_MOVE

    04-11 03:09:27.959: DEBUG/LayoutView1(446): onTouchEvent action:ACTION_UP

    ------------------------------------------------------------------------------------------------------------------------------

    從Log可以看到,由于LayoutView1在攔截第一次down事件時return true,所以后續的事件(包括第一次的down)將由LayoutView1本身處理,事件不再傳遞下去。

    ?

  • LayoutView1LayoutView2onInterceptTouchEvent()處理down事件返回false
  • MyTextViewonTouchEvent()處理事件返回false

    LayoutView2onTouchEvent()處理事件返回true

    ----------------------------------------------------------------------------------------------------------------------------

    04-11 09:50:21.147: DEBUG/LayoutView1(301): onInterceptTouchEvent action:ACTION_DOWN

    04-11 09:50:21.147: DEBUG/LayoutView2(301): onInterceptTouchEvent action:ACTION_DOWN

    04-11 09:50:21.147: DEBUG/MyTextView(301): onTouchEvent action:ACTION_DOWN

    04-11 09:50:21.147: DEBUG/LayoutView2(301): onTouchEvent action:ACTION_DOWN

    04-11 09:50:21.176: DEBUG/LayoutView1(301): onInterceptTouchEvent action:ACTION_MOVE

    04-11 09:50:21.176: DEBUG/LayoutView2(301): onTouchEvent action:ACTION_MOVE

    04-11 09:50:21.206: DEBUG/LayoutView1(301): onInterceptTouchEvent action:ACTION_MOVE

    04-11 09:50:21.217: DEBUG/LayoutView2(301): onTouchEvent action:ACTION_MOVE

    …… //省略過多的ACTION_MOVE

    04-11 09:50:21.486: DEBUG/LayoutView1(301): onInterceptTouchEvent action:ACTION_UP

    04-11 09:50:21.486: DEBUG/LayoutView2(301): onTouchEvent action:ACTION_UP

    ----------------------------------------------------------------------------------------------------------------------------

    可以看到,由于MyTextView在onTouchEvent()中return false,down事件被傳遞給其父view,即LayoutView2的onTouchEvent()方法處理,由于在LayoutView2的onTouchEvent()中return true,所以down事件傳遞并沒有上傳到LayoutView1。注意,后續的moveup事件均被傳遞給LayoutView2onTouchEvent()處理,而沒有傳遞給MyTextView

    ?

    ----------------------------------------------------------------------------------------------------------------

    應大家的要求,我把源代碼貼上,其實很簡單,就是基礎文件,主要是用來觀察事件的傳遞。

    ?

    主Activity: InterceptTouchStudyActivity.java:

    ?

    public?class?InterceptTouchStudyActivity?extends?Activity {

    ????static?final?String?TAG?=?"ITSActivity";

    ??? TextView?tv;

    ???

    ????/** Called when the activity is first created. */

    ????@Override

    ????public?void?onCreate(Bundle savedInstanceState) {

    ????????super.onCreate(savedInstanceState);

    ??????? setContentView(R.layout.layers_touch_pass_test);

    ??? ?}

    ?}


    ?? ? ?LayoutView1.java:


    ?? ? ?public?class?LayoutView1?extends?LinearLayout {

    ???? ?private?final?String?TAG?=?"LayoutView1";

    ?? ??? ?public?LayoutView1(Context context, AttributeSet attrs) {

    ?????????super(context, attrs);

    ???????? Log.d(TAG,TAG);

    ???? }

    ?

    ?????@Override

    ?????public?boolean?onInterceptTouchEvent(MotionEvent ev) {

    ?????????int?action = ev.getAction();

    ?????????switch(action){

    ?????????case?MotionEvent.ACTION_DOWN:

    ????????????? Log.d(TAG,"onInterceptTouchEvent action:ACTION_DOWN");

    //??????????? return true;

    ??????????????break;

    ?????????case?MotionEvent.ACTION_MOVE:

    ????????????? Log.d(TAG,"onInterceptTouchEvent action:ACTION_MOVE");

    ??????????????break;

    ?????????case?MotionEvent.ACTION_UP:

    ????????????? Log.d(TAG,"onInterceptTouchEvent action:ACTION_UP");

    ??????????????break;

    ?????????case?MotionEvent.ACTION_CANCEL:

    ????????????? Log.d(TAG,"onInterceptTouchEvent action:ACTION_CANCEL");

    ??????????????break;

    ???????? }

    ????????

    ?????????return?false;

    ???? }

    ?

    ?????@Override

    ?????public?boolean?onTouchEvent(MotionEvent ev) {

    ?????????int?action = ev.getAction();

    ?????????switch(action){

    ?????????case?MotionEvent.ACTION_DOWN:

    ????????????? Log.d(TAG,"onTouchEvent action:ACTION_DOWN");

    ??????????????break;

    ?????????case?MotionEvent.ACTION_MOVE:

    ????????????? Log.d(TAG,"onTouchEvent action:ACTION_MOVE");

    ??????????????break;

    ?????????case?MotionEvent.ACTION_UP:

    ????????????? Log.d(TAG,"onTouchEvent action:ACTION_UP");

    ??????????????break;

    ?????????case?MotionEvent.ACTION_CANCEL:

    ????????????? Log.d(TAG,"onTouchEvent action:ACTION_CANCEL");

    ??????????????break;

    ???????? }

    ????????

    ?????????return?true;

    ???? }

    ?

    ?????@Override

    ?????protected?void?onLayout(boolean?changed,?int?l,?int?t,?int?r,?int?b) {

    ?????????//?TODO?Auto-generated method stub

    ?????????super.onLayout(changed, l, t, r, b);

    ???? }

    ?

    ?????@Override

    ?????protected?void?onMeasure(int?widthMeasureSpec,?int?heightMeasureSpec) {

    ?????????//?TODO?Auto-generated method stub

    ?????????super.onMeasure(widthMeasureSpec, heightMeasureSpec);

    ???? }

    }


    LayoutView2.java:

    public?class?LayoutView2?extends?LinearLayout {

    ????private?final?String?TAG?=?"LayoutView2";

    ???

    ????public?LayoutView2(Context context, AttributeSet attrs) {

    ???????super(context, attrs);

    ?????? Log.d(TAG,TAG);

    ??? }

    ?

    ????@Override

    ????public?boolean?onInterceptTouchEvent(MotionEvent ev) {

    ???????int?action = ev.getAction();

    ???????switch(action){

    ???????case?MotionEvent.ACTION_DOWN:

    ?????????? Log.d(TAG,"onInterceptTouchEvent action:ACTION_DOWN");

    ???????????break;

    ???????case?MotionEvent.ACTION_MOVE:

    ?????????? Log.d(TAG,"onInterceptTouchEvent action:ACTION_MOVE");

    ???????????break;

    ???????case?MotionEvent.ACTION_UP:

    ?????????? Log.d(TAG,"onInterceptTouchEvent action:ACTION_UP");

    ???????????break;

    ???????case?MotionEvent.ACTION_CANCEL:

    ?????????? Log.d(TAG,"onInterceptTouchEvent action:ACTION_CANCEL");

    ???????????break;

    ?????? }

    ??????

    ???????return?false;

    ??? }

    ?

    ????@Override

    ????public?boolean?onTouchEvent(MotionEvent ev) {

    ???????int?action = ev.getAction();

    ???????switch(action){

    ???????case?MotionEvent.ACTION_DOWN:

    ?????????? Log.d(TAG,"onTouchEvent action:ACTION_DOWN");

    ???????????break;

    ???????case?MotionEvent.ACTION_MOVE:

    ?????????? Log.d(TAG,"onTouchEvent action:ACTION_MOVE");

    ???????????break;

    ???????case?MotionEvent.ACTION_UP:

    ?????????? Log.d(TAG,"onTouchEvent action:ACTION_UP");

    ???????????break;

    ???????case?MotionEvent.ACTION_CANCEL:

    ?????????? Log.d(TAG,"onTouchEvent action:ACTION_CANCEL");

    ???????????break;

    ?????? }

    ??????

    ???????return?true;

    ??? }?

    }


    MyTextView.java:

    public?class?MyTextView?extends?TextView {

    ????private?final?String?TAG?=?"MyTextView";

    ???

    ????public?MyTextView(Context context, AttributeSet attrs) {

    ???????super(context, attrs);

    ?????? Log.d(TAG,TAG);

    ??? }

    ?

    ????@Override

    ????public?boolean?onTouchEvent(MotionEvent ev) {

    ???????int?action = ev.getAction();

    ???????switch(action){

    ???????case?MotionEvent.ACTION_DOWN:

    ?????????? Log.d(TAG,"onTouchEvent action:ACTION_DOWN");

    ???????????break;

    ???????case?MotionEvent.ACTION_MOVE:

    ?????????? Log.d(TAG,"onTouchEvent action:ACTION_MOVE");

    ???????????break;

    ???????case?MotionEvent.ACTION_UP:

    ?????????? Log.d(TAG,"onTouchEvent action:ACTION_UP");

    ???????????break;

    ???????case?MotionEvent.ACTION_CANCEL:

    ?????????? Log.d(TAG,"onTouchEvent action:ACTION_CANCEL");

    ???????????break;

    ?????? }

    ??????

    ???????return?false;

    ??? }

    ???

    ????public?void?onClick(View v) {

    ?????? Log.d(TAG,?"onClick");

    ??? }

    ???

    ????public?boolean?onLongClick(View v) {

    ?????? Log.d(TAG,?"onLongClick");

    ???????return?false;

    ??? }

    }

    ?

    #?re: onInterceptTouchEvent和onTouchEvent調用時序 2011-08-19 09:25 | 米其林的微笑
    博主,你好,我想請問一下onTouchEvent的事件是是由childView傳到 parentView,還是由parentView傳到childView?你說由底向上,但是標志的順序又很奇怪,底是指父親節點,還是?如果我在 parentView想接收down事件,在childView接收down,up,move的事件,哪些函數的返回值,該怎么處理。請指點,謝謝 了。??回復??更多評論
    ?? #?re: onInterceptTouchEvent和onTouchEvent調用時序[未登錄] 2011-08-19 09:30 | tigertian
    @米其林的微笑
    onTouchEvent事件是由childView傳到parentView。
    你 在parentView想接收down事件的話,childView在收到事件后onTouchEvent方法都要返回false,這樣讓 parentView也能收到事件,同時parentView中只捕捉ACTION_DOWN,在childView中捕捉三個事件。??回復??更多評論
    ?? #?re: onInterceptTouchEvent和onTouchEvent調用時序 2011-08-20 00:30 | 米其林的微笑
    @tigertian
    謝謝你的回答。那childView在收到事件后onTouchEvent方法都要返回false,down,up,move的事件會響應么?如果在parentView中想處理up 事件呢。我現在怎么處理都是只有一個有響應。??回復??更多評論
    ?? #?re: onInterceptTouchEvent和onTouchEvent調用時序 2012-02-07 11:05 | 周歡
    @tigertian
    你在parentView想接收down事件的話,childView在收到 事件后onTouchEvent方法都要返回false,這樣讓parentView也能收到事件,同時Child中只捕捉ACTION_DOWN,在 Parent中捕捉三個事件.樓主可能說反了??回復??更多評論
    ??

    #?re: onInterceptTouchEvent和onTouchEvent調用時序 2012-09-07 13:35 | 248933223@qq.com
    其實這是設計模式中比較常見的一個模式,叫責任鏈模式,類似filter的功能??回復??更多評論

    ?

    FromAddress

    總結

    以上是生活随笔為你收集整理的onInterceptTouchEvent和onTouchEvent调用时序的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。

    主站蜘蛛池模板: 少妇乱淫| 美女极度色诱图片www视频 | 日韩精品av一区二区三区 | 波多一区 | 亚洲日本欧美 | 男人的天堂国产 | 538国产精品一区二区免费视频 | 一区二区三区四区在线免费观看 | 欧美一级射 | 午夜精品极品粉嫩国产尤物 | 致单身男女免费观看完整版 | 亚洲激情网址 | 亚一区| 91亚洲视频 | 亚洲九九爱| 成人视屏在线 | 91精品视频免费在线观看 | 精品国产一区二区三区日日嗨 | 欧美aa在线| wwwww在线观看 | 欧美乱子伦 | 在线免费黄色片 | 一级二级三级黄色片 | 国产精品一区二区三区免费看 | 最好看的日本字幕mv视频大全 | 黄色片在哪里看 | 国产刺激对白 | 日本国产精品一区 | www.九色| 国产大片aaa | 国产麻豆剧传媒精品国产av | 国产精品桃色 | 亚洲视频123 | 国偷自拍第113页 | 亚洲在线视频 | 少妇一级淫片免费视频 | 青青草视频在线观看 | 国产精品第二页 | 熟妇高潮一区二区三区 | 强行挺进白丝老师翘臀网站 | 国产奶水涨喷在线播放 | 久久亚洲精品国产精品黑人v | 久久精品999 | 一级免费黄色片 | 女人脱下裤子让男人桶 | 东京热一区二区三区四区 | 午夜精品久久久久久久99 | 日韩三级麻豆 | 成人自拍视频网站 | 久久不雅视频 | 性欢交69国产精品 | av在线不卡播放 | 风间由美在线观看 | av中文字幕第一页 | 长篇乱肉合集乱500小说日本 | 97se.com| 亚洲欧美少妇 | 亚洲中文在线一区 | 午夜两性视频 | 国产无套精品 | 天天操你 | 国产精品视频免费 | 国产全是老熟女太爽了 | 欧美日韩亚洲国产一区 | www狠狠操| 亚洲一线视频 | 成人娱乐网 | 色优久久| 国产精品午夜福利 | 国产大学生av | 日韩精品在线免费视频 | 三级网站免费观看 | 日韩网站免费观看 | 国产欧美日韩三级 | 福利视频一区二区 | av不卡在线免费观看 | 亚洲国产一二三 | 亚洲乱码国产乱码精品精剪 | 久久久久久美女 | 国产在线麻豆精品观看 | 成人a毛片久久免费播放 | 日韩在线视频观看免费 | 亚洲精品色午夜无码专区日韩 | 秋霞在线一区二区 | 国产欧美精品一区二区在线播放 | 成人在线免费视频 | 精品久久久久久久中文字幕 | 亚洲中文在线一区 | 日本高清视频免费看 | 狠狠干2020| 成人性毛片 | 久久久国 | 久久综合在线 | 无码黑人精品一区二区 | 男人的天堂网在线 | 成人午夜av | 久操免费在线视频 | 国产精品丝袜黑色高跟鞋的设计特点 | 人与禽性7777777 |