一个仿WIN8磁帖效果的ImageView

本文介绍了一个自定义的动态图像视图组件,通过触摸事件实现旋转、缩放等功能,提供灵活的图像操作体验。

    import android.content.Context;  
    import android.graphics.Camera;  
    import android.graphics.Canvas;  
    import android.graphics.Matrix;  
    import android.graphics.Paint;  
    import android.graphics.PaintFlagsDrawFilter;  
    import android.graphics.drawable.BitmapDrawable;  
    import android.graphics.drawable.Drawable;  
    import android.os.Handler;  
    import android.os.Message;  
    import android.util.AttributeSet;  
    import android.view.MotionEvent;  
    import android.widget.ImageView;  
      
    public class MyImageView extends ImageView {  
      
        private boolean onAnimation = true;  
        private int rotateDegree = 10;  
      
        private boolean isFirst = true;  
        private float minScale = 0.95f;  
        private int vWidth;  
        private int vHeight;  
        private boolean isFinish = true,isActionMove=false,isScale=false;  
        private Camera camera;  
      
        boolean XbigY = false;  
        float RolateX = 0;  
        float RolateY = 0;  
      
        OnViewClick onclick=null;  
          
        public MyImageView(Context context) {  
            super(context);  
            // TODO Auto-generated constructor stub  
            camera = new Camera();  
        }  
      
        public MyImageView(Context context, AttributeSet attrs) {  
            super(context, attrs);  
            // TODO Auto-generated constructor stub  
            camera = new Camera();  
        }  
      
        public void SetAnimationOnOff(boolean oo) {  
            onAnimation = oo;  
        }  
        public void setOnClickIntent(OnViewClick onclick){  
            this.onclick=onclick;  
        }  
        @Override  
        protected void onDraw(Canvas canvas) {  
            super.onDraw(canvas);  
            if (isFirst) {  
                isFirst = false;  
                init();  
            }  
            canvas.setDrawFilter(new PaintFlagsDrawFilter(0, Paint.ANTI_ALIAS_FLAG  
                    | Paint.FILTER_BITMAP_FLAG));  
        }  
      
        public void init() {  
            vWidth = getWidth() - getPaddingLeft() - getPaddingRight();  
            vHeight = getHeight() - getPaddingTop() - getPaddingBottom();  
            Drawable drawable = getDrawable();  
            BitmapDrawable bd = (BitmapDrawable) drawable;  
            bd.setAntiAlias(true);  
        }  
      
        @Override  
        public boolean onTouchEvent(MotionEvent event) {  
            super.onTouchEvent(event);  
            if (!onAnimation)  
                return true;  
      
              
            switch (event.getAction() & MotionEvent.ACTION_MASK) {  
            case MotionEvent.ACTION_DOWN:  
                float X = event.getX();  
                float Y = event.getY();  
                RolateX = vWidth / 2 - X;  
                RolateY = vHeight / 2 - Y;  
                XbigY = Math.abs(RolateX) > Math.abs(RolateY) ? true : false;  
      
                isScale = X > vWidth / 3 && X < vWidth * 2 / 3 && Y > vHeight / 3&& Y < vHeight * 2 / 3;  
                isActionMove=false;  
                  
                if (isScale) {  
                    handler.sendEmptyMessage(1);  
                } else {  
                    rolateHandler.sendEmptyMessage(1);  
                }  
                break;  
            case MotionEvent.ACTION_MOVE:  
                float x=event.getX();float y=event.getY();  
                if(x>vWidth || y>vHeight || x<0 || y<0){  
                    isActionMove=true;  
                }else{  
                    isActionMove=false;  
                }  
                  
                break;  
            case MotionEvent.ACTION_UP:  
                if (isScale) {  
                    handler.sendEmptyMessage(6);  
                } else {  
                    rolateHandler.sendEmptyMessage(6);  
                }  
                break;  
            }  
            return true;  
        }  
        public interface OnViewClick {  
            public void onClick();  
        }  
        private Handler rolateHandler = new Handler() {  
            private Matrix matrix = new Matrix();  
            private float count = 0;  
      
            @Override  
            public void handleMessage(Message msg) {  
                super.handleMessage(msg);  
                matrix.set(getImageMatrix());  
                switch (msg.what) {  
                case 1:  
                    count = 0;  
                    BeginRolate(matrix, (XbigY ? count : 0), (XbigY ? 0 : count));  
                    rolateHandler.sendEmptyMessage(2);  
                    break;  
                case 2:  
                    BeginRolate(matrix, (XbigY ? count : 0), (XbigY ? 0 : count));  
                    if (count < getDegree()) {  
                        rolateHandler.sendEmptyMessage(2);  
                    } else {  
                        isFinish = true;  
                    }  
                    count++;  
                    count++;  
                    break;  
                case 3:  
                    BeginRolate(matrix, (XbigY ? count : 0), (XbigY ? 0 : count));  
                    if (count > 0) {  
                        rolateHandler.sendEmptyMessage(3);  
                    } else {  
                        isFinish = true;  
                        if(!isActionMove&&onclick!=null){  
                            onclick.onClick();  
                        }  
                    }  
                    count--;  
                    count--;  
                    break;  
                case 6:  
                    count = getDegree();  
                    BeginRolate(matrix, (XbigY ? count : 0), (XbigY ? 0 : count));  
                    rolateHandler.sendEmptyMessage(3);  
                    break;  
                }  
            }  
        };  
      
        private synchronized void BeginRolate(Matrix matrix, float rolateX,  
                float rolateY) {  
            // Bitmap bm = getImageBitmap();  
            int scaleX = (int) (vWidth * 0.5f);  
            int scaleY = (int) (vHeight * 0.5f);  
            camera.save();  
            camera.rotateX(RolateY > 0 ? rolateY : -rolateY);  
            camera.rotateY(RolateX < 0 ? rolateX : -rolateX);  
            camera.getMatrix(matrix);  
            camera.restore();  
            // 控制中心点  
            if (RolateX > 0 && rolateX != 0) {  
                matrix.preTranslate(-vWidth, -scaleY);  
                matrix.postTranslate(vWidth, scaleY);  
            } else if (RolateY > 0 && rolateY != 0) {  
                matrix.preTranslate(-scaleX, -vHeight);  
                matrix.postTranslate(scaleX, vHeight);  
            } else if (RolateX < 0 && rolateX != 0) {  
                matrix.preTranslate(-0, -scaleY);  
                matrix.postTranslate(0, scaleY);  
            } else if (RolateY < 0 && rolateY != 0) {  
                matrix.preTranslate(-scaleX, -0);  
                matrix.postTranslate(scaleX, 0);  
            }  
            setImageMatrix(matrix);  
        }  
      
        private Handler handler = new Handler() {  
            private Matrix matrix = new Matrix();  
            private float s;  
            int count = 0;  
      
            @Override  
            public void handleMessage(Message msg) {  
                super.handleMessage(msg);  
                matrix.set(getImageMatrix());  
                switch (msg.what) {  
                case 1:  
                    if (!isFinish) {  
                        return;  
                    } else {  
                        isFinish = false;  
                        count = 0;  
                        s = (float) Math.sqrt(Math.sqrt(minScale));  
                        BeginScale(matrix, s);  
                        handler.sendEmptyMessage(2);  
                    }  
                    break;  
                case 2:  
                    BeginScale(matrix, s);  
                    if (count < 4) {  
                        handler.sendEmptyMessage(2);  
                    } else {  
                        isFinish = true;  
                        if(!isActionMove&&onclick!=null){  
                            onclick.onClick();  
                        }  
                    }  
                    count++;  
                    break;  
                case 6:  
                    if (!isFinish) {  
                        handler.sendEmptyMessage(6);  
                    } else {  
                        isFinish = false;  
                        count = 0;  
                        s = (float) Math.sqrt(Math.sqrt(1.0f / minScale));  
                        BeginScale(matrix, s);  
                        handler.sendEmptyMessage(2);  
                    }  
                    break;  
                }  
            }  
        };  
      
        private synchronized void BeginScale(Matrix matrix, float scale) {  
            int scaleX = (int) (vWidth * 0.5f);  
            int scaleY = (int) (vHeight * 0.5f);  
            matrix.postScale(scale, scale, scaleX, scaleY);  
            setImageMatrix(matrix);  
        }  
      
        public int getDegree() {  
            return rotateDegree;  
        }  
      
        public void setDegree(int degree) {  
            rotateDegree = degree;  
        }  
      
        public float getScale() {  
            return minScale;  
        }  
      
        public void setScale(float scale) {  
            minScale = scale;  
        }  
    }  

joke=(MyImageView) findViewById(R.id.c_joke);  
        joke.setOnClickIntent(new MyImageView.OnViewClick() {  
              
            @Override  
            public void onClick() {  
                // TODO Auto-generated method stub  
                Toast.makeText(TestRolateAnimActivity.this, "事件触发", 1000).show();  
                System.out.println("1");  
            }  
        });


评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值