5

我想在容器级别处理所有触摸事件。换句话说,我希望所有的触摸事件都达到容器级别。现在我发现 TouchEvents 只有在触摸位置没有落在视图组包含的 UI 组件上时才会到达包含的 ViewGroup。包含的 UI 元素处理 TouchEvent,它不会冒泡到容器中。有谁知道如何保证所有触摸事件都到达顶级容器?

为了清楚起见,想象一个带有几个按钮、几个编辑文本和几个复选框的活动。典型的形式。通常我会看到每个 UI 组件都会捕获落在它上面的 TouchEvent,而容器并不聪明。所以我想知道容器/视图组如何被告知在其区域内任何地方的所有触摸,无论该区域是否被按钮、空白空间或编辑文本占用。

4

2 回答 2

8

这就是我解释你的问题的方式:

你有这样的视图树

  • 视图组 G
    • 查看 A
    • 视图 B
    • ...

并且您希望 G 处理在触摸时创建的 MotionEvent,即使它被 A、B、...


如何:

我给你两个选择。取决于你是否想忽略消费

  1. 每个孩子
  2. 只有选定的孩子

使用以下模板之一:

  1. 在 G 中覆盖 dispatchTouchEvent()

    // In G
    @Override
    public boolean dispatchTouchEvent(MotionEvent event) {
         super.dispatchTouchEvent(event);
    
         // Handle event here instead of using an OnTouchListener
    
         return true;
     }
    
  2. 在每个应该忽略其消费的孩子中覆盖 dispatchTouchEvent()

    • 忽略一些孩子

      // In every child whose consumption should be ignored
      @Override
      public boolean dispatchTouchEvent(MotionEvent event) {
           super.dispatchTouchEvent(ev);
      
           return false; // false means "I did not consume the event"
       }
      
    • 不要忘记设置你的监听器

      // In G, before touch should be recognized
      setOnTouchListener(new OnTouchListener() {
          @Override
          public boolean onTouch(View v, MotionEvent event) {
              // Handle event here
      
              return true; // true means "I did consume the event"
          }
      });
      

以代码行来衡量,选项 1 要简单得多。选项 2 是为了以防您需要对某些 ​​A、B ...

于 2012-08-06T15:11:29.253 回答
1

我知道已经晚了,但我认为未来的读者可能想看看ViewGroups.onInterceptTouchEvent()

于 2014-03-24T13:18:06.883 回答