package com.example.myapp;import android.animation.Animator;import android.animation.AnimatorListenerAdapter;import android.animation.AnimatorSet;import android.animation.ObjectAnimator;import android.content.Context;import android.graphics.Bitmap;import android.graphics.PixelFormat;import android.os.Handler;import android.os.Vibrator;import android.util.AttributeSet;import android.util.Log;import android.view.*;import android.view.animation.AccelerateDecelerateInterpolator;import android.widget.GridView;import android.widget.ImageView;import java.util.LinkedList;import java.util.List;/**  * Created by yp-tc-m-2781 on 16/5/3.  */ public class MyGridView extends GridView {    private final String tag = "#myapp.MyGridView";    private View mStartDragItemView = null;    private ImageView mDragImageView;    private Bitmap mDragBitmap;    private WindowManager mWindowManager;    private WindowManager.LayoutParams mWindowLayoutParams;    private Handler mHandler;    private long dragResponseMS = 800;    private boolean isDrag;    private boolean normalMove;    private int mDownX;    private int mDownY;    private int itemHeight;    private int mDragPosition;    private Vibrator mVibrator;    private int mPoint2ItemLeft;    private int mPoint2ItemTop;    private boolean mAnimationEnd = true;    private int paddingTop;    private int paddingBottom;    int mNumColumns;    public MyGridView(Context context) {        this(context,null);    }    public MyGridView(Context context, AttributeSet attrs) {        this(context, attrs,0);    }    public MyGridView(Context context, AttributeSet attrs, int defStyleAttr) {        super(context, attrs, defStyleAttr);        mVibrator = (Vibrator) getContext().getSystemService(Context.VIBRATOR_SERVICE);        mWindowManager = (WindowManager)getContext().getSystemService(Context.WINDOW_SERVICE);        mHandler = new Handler();        paddingTop = getPaddingTop();        paddingBottom = getPaddingBottom();    }    @Override    public void setNumColumns(int numColumns) {        super.setNumColumns(numColumns);        this.mNumColumns = numColumns;    }    private Runnable mLongClickRunnable = new Runnable() {        @Override        public void run() {            isDrag = true;            mVibrator.vibrate(50);            mStartDragItemView.setVisibility(View.INVISIBLE);            itemHeight = mStartDragItemView.getHeight();            createDragImage(mDragBitmap, mDownX, mDownY);        }    };    @Override    public boolean dispatchTouchEvent(MotionEvent ev) {        switch (ev.getAction()) {            case MotionEvent.ACTION_DOWN:                normalMove = false;                mDownX = (int)ev.getX();                mDownY = (int)ev.getY();                mDragPosition = pointToPosition(mDownX,mDownY);                if(mDragPosition == INVALID_POSITION)                {                    return super.dispatchTouchEvent(ev);                }                mHandler.postDelayed(mLongClickRunnable,dragResponseMS);                mStartDragItemView = getChildAt(mDragPosition - getFirstVisiblePosition());                mStartDragItemView.setDrawingCacheEnabled(true);                mDragBitmap = Bitmap.createBitmap(mStartDragItemView.getDrawingCache());                mStartDragItemView.destroyDrawingCache();                mPoint2ItemTop = mDownY - mStartDragItemView.getTop();                mPoint2ItemLeft = mDownX - mStartDragItemView.getLeft();                break;            case MotionEvent.ACTION_MOVE:                int moveX = (int)ev.getX();                int moveY = (int) ev.getY();                if(!isTouchInItem( moveX, moveY)){                    normalMove = true;                    mHandler.removeCallbacks(mLongClickRunnable);                }                break;            case MotionEvent.ACTION_UP:                mHandler.removeCallbacks(mLongClickRunnable);                break;        }        return super.dispatchTouchEvent(ev);    }    @Override    public boolean onTouchEvent(MotionEvent ev) {        Log.i(tag,"onTouchEvent");        if(isDrag && mDragImageView != null){            switch(ev.getAction()){                case MotionEvent.ACTION_MOVE:                    onDragItem((int)ev.getX(),(int)ev.getY());                    break;                case MotionEvent.ACTION_UP:                    onStopDrag();                    break;            }            return true;        }        return super.onTouchEvent(ev);    }    private void onStopDrag(){        View view = getChildAt(mDragPosition - getFirstVisiblePosition());        if(view != null){            view.setVisibility(View.VISIBLE);        }        removeDragImage();        isDrag = false;        if(onChangeListener != null)        {            onChangeListener.onStop();        }    }    private void createDragImage(Bitmap bitmap, int downX , int downY)    {        mWindowLayoutParams = new WindowManager.LayoutParams();        mWindowLayoutParams.format = PixelFormat.TRANSLUCENT;        mWindowLayoutParams.gravity = Gravity.TOP | Gravity.LEFT;        mWindowLayoutParams.x = downX - mPoint2ItemLeft + getLeft();        mWindowLayoutParams.y = downY - mPoint2ItemTop + getTop();        mWindowLayoutParams.alpha = 0.55f;        mWindowLayoutParams.width = WindowManager.LayoutParams.WRAP_CONTENT;        mWindowLayoutParams.height = WindowManager.LayoutParams.WRAP_CONTENT;        mWindowLayoutParams.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE  | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE ;        mDragImageView = new ImageView(getContext());        mDragImageView.setImageBitmap(bitmap);        mWindowManager.addView(mDragImageView, mWindowLayoutParams);    }    private boolean isTouchInItem(int x, int y){        if(isDrag || normalMove)        {            return true;        }        int disX = Math.abs(x - mDownX);        int disY = Math.abs(y - mDownY);        if(disX > 1 || disY > 1)        {            return false;        }        return true;    }    private void removeDragImage(){        if(mDragImageView != null){            mWindowManager.removeView(mDragImageView);            mDragImageView = null;        }    }    private void onDragItem(int moveX, int moveY){        mWindowLayoutParams.x = (moveX - mPoint2ItemLeft + getLeft());        mWindowLayoutParams.y = (moveY - mPoint2ItemTop + getTop());        int trans = itemHeight/4;        if((getBottom()-mWindowLayoutParams.y - paddingBottom) <= (itemHeight+trans))        {            smoothScrollBy(itemHeight,1500);        }        else if((mWindowLayoutParams.y - trans) <= (getTop() + paddingTop))        {            smoothScrollBy(-itemHeight,1500);        }        else  {            smoothScrollBy(0,0);        }        mWindowManager.updateViewLayout(mDragImageView, mWindowLayoutParams);        final int newPosition = pointToPosition(moveX,moveY);        if(newPosition != mDragPosition && newPosition != INVALID_POSITION && mAnimationEnd)        {            if(onChangeListener != null) {                onChangeListener.onChange(mDragPosition, newPosition);            }            final ViewTreeObserver observer = getViewTreeObserver();            observer.addOnPreDrawListener(new ViewTreeObserver.OnPreDrawListener() {                @Override                public boolean onPreDraw() {                    observer.removeOnPreDrawListener(this);                    animateReorder(mDragPosition, newPosition);                    mDragPosition = newPosition;                    return true;                }            } );        }    }    private void animateReorder(final int oldPosition, final int newPosition) {        boolean isForward = newPosition > oldPosition;        List<Animator> resultList = new LinkedList<Animator>();        if (isForward) {            for (int pos = oldPosition; pos < newPosition; pos++) {                View view = getChildAt(pos - getFirstVisiblePosition());                if ((pos + 1) % mNumColumns == 0) {                    resultList.add(createTranslationAnimations(view,                            - (view.getWidth() ) * (mNumColumns - 1), 0,                            view.getHeight() , 0));                } else {                    resultList.add(createTranslationAnimations(view,                            view.getWidth() , 0, 0, 0));                }            }        } else {            for (int pos = oldPosition; pos > newPosition; pos--) {                View view = getChildAt(pos - getFirstVisiblePosition());                if ((pos) % mNumColumns == 0) {                    resultList.add(createTranslationAnimations(view,                            (view.getWidth() ) * (mNumColumns - 1), 0,                            -view.getHeight() , 0));                } else {                    resultList.add(createTranslationAnimations(view,                            -view.getWidth() , 0, 0, 0));                }            }        }        AnimatorSet resultSet = new AnimatorSet();        resultSet.playTogether(resultList);        resultSet.setDuration(300);        resultSet.setInterpolator(new AccelerateDecelerateInterpolator());        resultSet.addListener(new AnimatorListenerAdapter() {            @Override            public void onAnimationStart(Animator animation) {                mAnimationEnd = false;            }            @Override            public void onAnimationEnd(Animator animation) {                mAnimationEnd = true;            }        });        resultSet.start();    }    private AnimatorSet createTranslationAnimations(View view, float startX,                                                    float endX, float startY, float endY) {        ObjectAnimator animX = ObjectAnimator.ofFloat(view, "translationX",                startX, endX);        ObjectAnimator animY = ObjectAnimator.ofFloat(view, "translationY",                startY, endY);        AnimatorSet animSetXY = new AnimatorSet();        animSetXY.playTogether(animX, animY);        return animSetXY;    }    private OnChangeListener onChangeListener;    public void setOnChangeListener(OnChangeListener onChangeListener) {        this.onChangeListener = onChangeListener;    }    interface OnChangeListener    {        void onChange(int drayPosition,int swapPosition);        void onStop();    }// @Override // public void onChange(int drayPosition, int swapPosition) { // mHidePosition = swapPosition; // Integer integer = list.get(drayPosition); // list.remove(drayPosition); // list.add(swapPosition,integer); // notifyDataSetChanged(); // } // // @Override // public void onStop() { // mHidePosition = -1; // } }

更多相关文章

  1. 代码中设置drawableleft
  2. android 3.0 隐藏 系统标题栏
  3. Android开发中activity切换动画的实现
  4. Android(安卓)学习 笔记_05. 文件下载
  5. Android中直播视频技术探究之—摄像头Camera视频源数据采集解析
  6. 技术博客汇总
  7. android 2.3 wifi (一)
  8. AndRoid Notification的清空和修改
  9. Android中的Chronometer

随机推荐

  1. Android笔记---点击事件的四种写法
  2. 【Android】移动端接入Cronet实践
  3. Android加载网络图片并保存到系统相册
  4. Android用自己的app替换Launcher
  5. 看完这篇。再也不怕被问 HandlerThread
  6. 《转》完美解决微信video视频隐藏控件和
  7. Android(安卓)通过软引用实现图片缓存,防
  8. 更改cocos2d-x android 项目的cocos2d-x
  9. android studio配置retrolambda
  10. Android中的前置服务