2012-07-10 115 views
17

我试图利用片段内的手势;我在处理我的细节片段的FragmentActivity中有以下内容。我试图发生的事情是在视图上检测到滑动以用上一个或下一个条目替换该视图内部的数据。Android的片段onCreateView与手势

如果有更好的处理方法,我完全同意。然而,这里发生的是onFling方法从来没有被实际调用过。

public static class DetailsFragment extends Fragment { 
    @Override 
    public View onCreateView(LayoutInflater inflater, ViewGroup container, 
     Bundle savedInstanceState) { 
     if (container == null) { 
      return null; 
     } 
     View v = inflater.inflate(R.layout.my_view, null, false); 
     final GestureDetector gesture = new GestureDetector(getActivity(), 
      new GestureDetector.SimpleOnGestureListener() { 
       @Override 
       public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, 
        float velocityY) { 

        final int SWIPE_MIN_DISTANCE = 120; 
        final int SWIPE_MAX_OFF_PATH = 250; 
        final int SWIPE_THRESHOLD_VELOCITY = 200; 
        try { 
         if (Math.abs(e1.getY() - e2.getY()) > SWIPE_MAX_OFF_PATH) 
          return false; 
         if (e1.getX() - e2.getX() > SWIPE_MIN_DISTANCE 
          && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY) { 
          Log.i(Constants.APP_TAG, "Right to Left"); 
         } else if (e2.getX() - e1.getX() > SWIPE_MIN_DISTANCE 
          && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY) { 
          Log.i(Constants.APP_TAG, "Left to Right"); 
          titles.showDetails(getPosition() - 1); 
         } 
        } catch (Exception e) { 
         // nothing 
        } 
        return super.onFling(e1, e2, velocityX, velocityY); 
       } 
      }); 

     v.setOnTouchListener(new View.OnTouchListener() { 
      @Override 
      public boolean onTouch(View v, MotionEvent event) { 
       return gesture.onTouchEvent(event); 
      } 
     }); 

     return v; 
    } 
} 

回答

43

貌似以下问题解释如下:Android: GestureDetector won't catch Gestures

另外这里是结果:

的解决方案实际上是重写onDown方法和返回true;否则姿态探测器将停止,而不是检测了起来:

 final GestureDetector gesture = new GestureDetector(getActivity(), 
      new GestureDetector.SimpleOnGestureListener() { 

       @Override 
       public boolean onDown(MotionEvent e) { 
        return true; 
       } 

       @Override 
       public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, 
        float velocityY) { 
        Log.i(Constants.APP_TAG, "onFling has been called!"); 
        final int SWIPE_MIN_DISTANCE = 120; 
        final int SWIPE_MAX_OFF_PATH = 250; 
        final int SWIPE_THRESHOLD_VELOCITY = 200; 
        try { 
         if (Math.abs(e1.getY() - e2.getY()) > SWIPE_MAX_OFF_PATH) 
          return false; 
         if (e1.getX() - e2.getX() > SWIPE_MIN_DISTANCE 
          && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY) { 
          Log.i(Constants.APP_TAG, "Right to Left"); 
         } else if (e2.getX() - e1.getX() > SWIPE_MIN_DISTANCE 
          && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY) { 
          Log.i(Constants.APP_TAG, "Left to Right"); 
         } 
        } catch (Exception e) { 
         // nothing 
        } 
        return super.onFling(e1, e2, velocityX, velocityY); 
       } 
      }); 

     v.setOnTouchListener(new View.OnTouchListener() { 
      @Override 
      public boolean onTouch(View v, MotionEvent event) { 
       return gesture.onTouchEvent(event); 
      } 
     }); 
+3

只是好奇:为什么不参考手势丢失? – 2012-09-27 07:18:01

+1

@LemLordjeKo为什么对'gesture'的引用会丢失? 'gesture'作为我们创建的'View.OnTouchListener'的参考,并且通过视图本身'v'来保存。 Java已经足够成熟,如果有对象的路径,它几乎肯定不会得到GC'd。 – bclymer 2013-12-17 16:02:50

+0

上述代码段需要以下导入才能工作: import android.view.View.OnTouchListener; import android.view.MotionEvent; import android.view.GestureDetector; import android.util.Log; class常量public static final String APP_TAG =“mytag”; } – FuzzyAmi 2016-05-01 14:03:53

2

一对夫妇的评论

  1. 我不得不调整我的代码如下:

    v.setOnTouchListener(new View.OnTouchListener() { 
        @Override   
        public boolean onTouch(View v, MotionEvent event) { 
    
         // return gesture.onTouchEvent(event); 
    
         gesture.onTouchEvent(event); 
         return true; // <-- this line made the difference 
        } 
    }); 
    
  2. 另外,如果你正在使用xml文件来创建您的视图

    View v = inflater.inflate(R.layout.my_view, null, false); 
    

确保您确实按下了预期的视图。夸大测试的一个好方法是在布局xml文件中将宽度和高度都设置为“match_parent”而不是“wrap_content”。

+0

我错过了@mwillbanks重写onDown以返回SimpleOnGestureListener的true。我只在onSingleTapConfirmed和onDoubleTap上实现。 – gnemnk 2016-08-12 04:16:49