java - 如何实现GestureListener.onFling()方法

标签 java android image-processing scroll gesture

像这样的问题有很多,但大多数都是问如何将 GestureDetector 设置为 View。我已经这样做了,现在我想知道,android 没有提供任何让图像快速播放的功能。 我遇到的问题是我不知道如何处理该方法中提供的velocityX/Y。 我的最后一次尝试如下所示:

public class TouchableImage extends SizeableImage 
    implements GestureDetector.OnGestureListener, 
    GestureDetector.OnDoubleTapListener,
    OnTouchListener{

    protected GestureDetector mDetector;

    protected Matrix mCurrentMatrix;

    public TouchableImage(Context context) {
        super(context);
        init();
    }

    public TouchableImage(Context context, AttributeSet attrs) {
        super(context, attrs);
        init();
    }

    protected void init() {
        mCurrentMatrix = new Matrix();
        mDetector = new GestureDetector(getContext(), this);
        mDetector.setOnDoubleTapListener(this);
        if (hasImage()){
            onNewImage();

        }
    }

    private void onNewImage() {
        setOnTouchListener(this);
        setScaleType(ScaleType.MATRIX);
        setImageMatrix(mCurrentMatrix);
    }

    @Override
    public void setImageDrawable(Drawable d){
        super.setImageDrawable(d);
        onNewImage();
    }



    @Override
    public void setImageBitmap(Bitmap bm) {
        super.setImageBitmap(bm);
        onNewImage();
    }

    public boolean hasImage(){
        return getDrawable() != null;
    }

    /*GestureDetector.OnGestureListener */
    @Override
    public boolean onDown(MotionEvent e) {
        // do nothing on one finger down
        return true;
    }

    @Override
    public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX,
            float velocityY) {
        LogCat.d("ZoomableImage_FLING", "x:" + velocityX + " y:" + velocityY);
        float distanceX = velocityX / 1000;
        float distanceY = velocityY/ 1000;
        long end = System.currentTimeMillis() + (long)(Math.abs(velocityX)> Math   .abs(velocityY) ? Math.abs(velocityX) / 8: Math.abs(velocityY)/8);
            long now = System.currentTimeMillis();

        while (now < end){
            FlingRunnable fr = new FlingRunnable(e1, e2, distanceX, distanceY);
            postDelayed(fr, 10);
            distanceX -= distanceX / 100;
            distanceY -= distanceY / 100;
            now = System.currentTimeMillis();
        }

        return true;
    }

    @Override
    public void onLongPress(MotionEvent e) {
        // do nothing onLongPress       
    }

    @Override
    public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX,
            float distanceY) {
        LogCat.d("ZoomableImage_SCROLL", "x:" + distanceX + " y:" + distanceY);
        mCurrentMatrix.postTranslate(distanceX * -1, distanceY *-1);
        setImageMatrix(mCurrentMatrix);
        return true;
    }

    @Override
    public void onShowPress(MotionEvent e) {
        // do nothing onShowPress
    }

    @Override
    public boolean onSingleTapUp(MotionEvent e) {
        // do nothing onSingleTapUp
        return true;
    }


    /*GestureDetector.OnDoubleTapListener*/
    @Override
    public boolean onDoubleTap(MotionEvent e) {
        // TODO Auto-generated method stub
        return false;
    }

    @Override
    public boolean onDoubleTapEvent(MotionEvent e) {
        // TODO Auto-generated method stub
        return false;
    }

    @Override
    public boolean onSingleTapConfirmed(MotionEvent e) {
        // TODO Auto-generated method stub
        return false;
    }

    /* Images onTouchListener */
    @Override
    public boolean onTouch(View v, MotionEvent event) {
        /* simply dispatch the motion Events to our GestureDetector */
        return mDetector.onTouchEvent(event);
    }


    /* sizeable Image*/
    @Override
    public Matrix getCurrentMatrix() {
        return mCurrentMatrix;
    }

    @Override
    public void setImageBounds(PointF point) {

    }

    public class FlingRunnable implements Runnable{


        public MotionEvent e1;
        public MotionEvent e2;
        public float distanceX;
        public float distanceY;

        public FlingRunnable(MotionEvent e1, MotionEvent e2, float distanceX, floa t distanceY){
                this.e1 = e1;
            this.e2 = e2;
            this.distanceX = distanceX;
            this.distanceY = distanceY;
        }

        @Override
        public void run() {
            onScroll(e1, e2, distanceX, distanceY);
        }

    }

}    

我遇到的一个问题是为 distanceX/Yend 找到合理的值。 我遇到的另一个问题是,即使我有一些值,fling() 似乎“立即”出现,就像所有 onScroll() 调用都被添加和应用一样同时。

注意:我的构建目标是 2.1 (Eclair),因此我无法使用 2.2 (Froyo) 中发明的更好的检测器

最佳答案

看看这段代码,

public class gesture extends Activity implements OnGestureListener
{
private GestureDetector gestureScanner;

@Override
public void onCreate(Bundle savedInstanceState)
 {
super.onCreate(savedInstanceState);
gestureScanner = new GestureDetector(this);
 Toast.makeText(gesture.this, "Perform Some gestures on screen",  Toast.LENGTH_LONG).show();
 setContentView(R.layout.main);
}

 @Override
 public boolean onTouchEvent(MotionEvent me)
 {
 return gestureScanner.onTouchEvent(me);
 }

 @Override
 public boolean onDown(MotionEvent e)
 {
 Toast.makeText(gesture.this, "Motion Event Performed", Toast.LENGTH_LONG).show();
 return true;
   }

 @Override
 public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY)
{
Toast.makeText(gesture.this, "Fling Event performed", Toast.LENGTH_LONG).show();
return true;
}

@Override
public void onLongPress(MotionEvent e)
{
Toast.makeText(gesture.this, "Long-Press event performed", Toast.LENGTH_LONG).show();
}

@Override
public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY)
{
Toast.makeText(gesture.this, "Scroll event performed", Toast.LENGTH_LONG).show();
return true;
}

@Override
public void onShowPress(MotionEvent e)
{
Toast.makeText(gesture.this, "Show-Press event performed", Toast.LENGTH_LONG).show();
}

@Override
public boolean onSingleTapUp(MotionEvent e)
{
Toast.makeText(gesture.this, "Single-Tap event performed", Toast.LENGTH_LONG).show();
 return true;
}
}

Documentation of GestureListenerTutorials project

这是根据您的问题的最佳解决方案,请查看以下答案:

Fling gesture detection on grid layoutHow to make horizontal scrolling view in android

另一个 Fling 教程: how to implement both ontouch and also onfling in a same listview?

关于java - 如何实现GestureListener.onFling()方法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8714913/

相关文章:

c++ - OpenCV Mat bitwise_xor with randu()

java - 如何在运行时更改 kubernetes 托管服务中 Java slf4j 记录器的日志级别?

java - Android 应用程序支持的设备是否取决于编写代码的 Java 版本?

java - 无法按需从 Kafka 读取记录

android - 如何在没有视频 View 的情况下从 Android 中的 URL 获取以毫秒为单位的视频长度?

android - 没有这样的字段错误: No field TextAppearance_fontFamily of type I

android 找不到符号 com.google.android.gms.wallet 构建错误

java - 图像大小调整 Java

python - 使用 Python 的 Opencv : pointPolygonTest gives obviously wrong result

java - JNativeHook 在按键期间注册的按键次数多于所需次数