android-从不调用MotionEvent.ACTION_UP

时间:2019-02-21 07:30:29

标签: android android-view android-touch-event

我想在用户将手放在视图上并放开它时停止它的同时做一些工作。我的代码如下:

viewHolder.plus.setOnTouchListener(new View.OnTouchListener() {
        private Handler mHandler;
        @Override
        public boolean onTouch(View view, MotionEvent event) {
            switch(event.getAction()) {
                case MotionEvent.ACTION_DOWN:
                    if(mHandler==null)
                        mHandler = new Handler();
                    mHandler.postDelayed(mAction, 500);
                    return true;
                case MotionEvent.ACTION_UP:
                    Log.v("this","cancel");
                    if (mHandler != null) {
                        mHandler.removeCallbacks(mAction);
                        mHandler = null;
                        Log.v("this", "c cancel");
                    }
                    break;
            }
            return false;
        }

        Runnable mAction = new Runnable() {
            @Override public void run() {
                ChangeTedad(item.getid(), "plus");
                Log.v("this","Cc");
                mHandler.postDelayed(this, 500);
            }
        };

    });

问题是,从不会调用ACTION_UP,并且可运行的对象将永远运行。

当用户取消触摸时如何停止运行?

2 个答案:

答案 0 :(得分:0)

您没有在触摸事件中正确设置中断和返回标志。

请替换为您的代码,

viewHolder.plus.setOnTouchListener(new View.OnTouchListener() {
        private Handler mHandler;
        @Override
        public boolean onTouch(View view, MotionEvent event) {
            switch(event.getAction()) {
                case MotionEvent.ACTION_DOWN:
                    if(mHandler==null)
                        mHandler = new Handler();
                    mHandler.postDelayed(mAction, 500);
                    break;
                case MotionEvent.ACTION_UP:
                    Log.v("this","cancel");
                    if (mHandler != null) {
                        mHandler.removeCallbacks(mAction);
                        mHandler = null;
                        Log.v("this", "c cancel");
                    }
                    break;
            }
            return true;
        }

        Runnable mAction = new Runnable() {
            @Override public void run() {
                ChangeTedad(item.getid(), "plus");
                Log.v("this","Cc");
                mHandler.postDelayed(this, 500);
            }
        };
    });

希望这对您有帮助

答案 1 :(得分:0)

每当在视图中进行一次触摸时,Android都会创建a series of touch events而不是a single touch event并缓冲这些事件,然后根据该方法返回的值顺序调用onTouch方法。 / p>

例如,当您对视图进行一次触摸时,正常的事件顺序将是

  • ACTION_DOWN(当您放下手指时)
  • 可选地ACTION_MOVE(如果您在触摸屏幕时移动手指)
  • ACTION_UP(当您从屏幕上移开手指时)

但是,如果您为响应false事件而从onTouchEvent覆盖返回ACTION_XXX,则不会收到任何后续事件的通知(您的代码将不会执行)。

回到您的情况,因为您从false返回了onTouchEvent,所以在收到第一个事件(ACTION_DOWN)之后,所有后续事件(包括ACTION_UP)都不会叫。

您需要做的就是从true方法返回onTouchEvent。就是这样!

viewHolder.plus.setOnTouchListener(new View.OnTouchListener() {
    private Handler mHandler;

    @Override
    public boolean onTouch(View view, MotionEvent event) {
        switch(event.getAction()) {
            case MotionEvent.ACTION_DOWN:
                if (mHandler == null) {
                    mHandler = new Handler();
                }
                mHandler.postDelayed(mAction, 500);
                break;
            case MotionEvent.ACTION_UP:
                Log.v("this","cancel");
                if (mHandler != null) {
                    mHandler.removeCallbacks(mAction);
                    mHandler = null;
                    Log.v("this", "c cancel");
                }
                break;
        }

        // [IMPORTANT] Return true here
        return true;
    }

    Runnable mAction = new Runnable() {
        @Override public void run() {
            ChangeTedad(item.getid(), "plus");
            Log.v("this","Cc");
            mHandler.postDelayed(this, 500);
        }
    };
}); 

This是一篇非常不错的文章,介绍了Android中的触摸操作。有空的时候看看吧。