Matrix

一.Matrix讲解

Matrix讲解请移步以下博客:
Matrix01

个人总结:

  1. Matrix是一个3 * 3矩阵(Matrix矩阵 * 原矩阵 =最终的效果),矩阵中的每个数字有不同的含义;通过改变矩阵,可以控制:平移,缩放,错切,旋转
  2. Matrix混合:pre : 右乘, M‘ = M*A ; post : 左乘, M’ = A*M
  3. 面向对象方式理解Matrix: Matrix是一个对象,不仅有平移,缩放,错切,旋转等方法(api),还包含各种操作的方法和各种信息;
  4. 应用:Camare,Canvas,Shader,setPolyToPoly等等;

二.Matrix小练习

这里写图片描述

public class MatrixImageView extends ImageView {
    //缩放模式
    private static final int ZOOM = 1;
    //默认模式
    private static final int NONE = 2;
    //距离
    private static final float DISTANCE = 10F;
    private int mode = NONE;
    //缩放中心点
    private PointF midIndex;
    //前一步操作的Matrix对象
    private Matrix preMatrix;
    //当前操作的Matrix对象
    private Matrix currentMatrix;
    //存放Matrix信息的数组
    private float[] matrixArray;
    //两点间的距离
    private float distance;

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

    /**
     * 初始化
     */
    private void init() {
        preMatrix = new Matrix();
        currentMatrix = new Matrix();
        matrixArray = new float[9];

    }

    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
        midIndex = new PointF(getMeasuredWidth() / 2 , getMeasuredHeight() / 2);

        Bitmap bitmap = BitmapFactory.decodeResource(getResources() , R.drawable.meizi);
        bitmap = Bitmap.createScaledBitmap(bitmap, getMeasuredWidth(), getMeasuredHeight(), true);
        setImageBitmap(bitmap);
    }

    @Override
    public boolean onTouchEvent(MotionEvent event) {
        //支持多点触控
        switch (event.getAction() & MotionEvent.ACTION_MASK){
            case MotionEvent.ACTION_DOWN://单击

                return true;//事件分发
            case MotionEvent.ACTION_POINTER_DOWN://第二个点接触屏幕
                distance = pointDistance(event);
                if (distance > DISTANCE){
                    mode = ZOOM;
                }
                break;
            case MotionEvent.ACTION_UP://单点离开屏幕
                scaleXY();
                break;
            case MotionEvent.ACTION_POINTER_UP://第二个点离开屏幕

                break;
            case MotionEvent.ACTION_MOVE://滑动
                if (mode == ZOOM && event.getPointerCount() == 2){
                    float v = pointDistance(event);
                    if (v > DISTANCE){
                        float scale = v / distance;
                        currentMatrix.setScale(scale , scale , midIndex.x , midIndex.y);
                    }
                }
                break;
        }

        currentMatrix.getValues(matrixArray);
        setImageMatrix(currentMatrix);
        return super.onTouchEvent(event);
    }

    /**
     * 计算两个触摸点之间的距离
     * @param event
     * @return
     */
    private float pointDistance(MotionEvent event){
        float x = event.getX(0) - event.getX(1);
        float y = event.getY(0) - event.getY(1);
        return (float) Math.sqrt(x * x + y * y);
    }

    /**
     * 缩小
     */
    private void scaleXY(){
        float width = getWidth() * matrixArray[0];
        float height = getHeight() * matrixArray[4];
        PointF startPoint = new PointF(width, height);
        PointF endPoint = new PointF(getWidth(), getHeight());
        ValueAnimator valueAnimator = ValueAnimator.ofObject(new PointEvaluator(), startPoint, endPoint);
        valueAnimator.setDuration(500);
        valueAnimator.setInterpolator(new DecelerateInterpolator());
        valueAnimator.start();

        valueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
            @Override
            public void onAnimationUpdate(ValueAnimator animation) {
                PointF animatedValue = (PointF) animation.getAnimatedValue();

                currentMatrix.setScale(animatedValue.x / getWidth(), animatedValue.y / getHeight(), getWidth() / 2, getHeight() / 2);
                setImageMatrix(currentMatrix);
            }
        });
        valueAnimator.addListener(new AnimatorListenerAdapter() {
            @Override
            public void onAnimationEnd(Animator animation) {
                super.onAnimationEnd(animation);
                currentMatrix.reset();
                setImageMatrix(currentMatrix);
            }
        });
    }

    /**
     * 自定义估值器
     */
    class PointEvaluator implements TypeEvaluator<PointF> {

        @Override
        public PointF evaluate(float fraction, PointF startValue, PointF endValue) {
            float x = startValue.x + fraction * (endValue.x - startValue.x);
            float y = startValue.y + fraction * (endValue.y - startValue.y);
            PointF point = new PointF(x, y);
            return point;
        }
    }
}
<com.jiao.matrixdemo.MatrixImageView
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:scaleType="matrix" />

源码下载

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值