安卓运用matrix进行图片的拖动和缩放

  • Post author:
  • Post category:其他



1.matrix讲解



Matrix的对图像的处理可分为四类基本变换:



Translate           平移变换



Rotate                旋转变换



Scale                  缩放变换



Skew                  错切变换



针对每种变换,Android提供了pre、set和post三种操作方式。其中



set用于设置Matrix中的值。



pre是先乘,因为矩阵的乘法不满足交换律,因此先乘、后乘必须要严格区分。先乘相当于矩阵运算中的右乘。



post是后乘,因为矩阵的乘法不满足交换律,因此先乘、后乘必须要严格区分。后乘相当于矩阵运算中的左乘。



除平移变换(Translate)外,旋转变换(Rotate)、缩放变换(Scale)和错切变换(Skew)都可以围绕一个中心点来进行,如果不指定,在默认情况下是围绕(0, 0)来进行相应的变换的。




2.多点触摸



首先需要继承OnTouchListener



在处理单点触摸中,我们一般会用到MotionEvent.ACTION_DOWN、ACTION_UP、ACTION_MOVE,然后可以用一个

switch(event.getAction() )

语句来分别进行处理。ACTION_DOWN和ACTION_UP就是单点触摸屏幕,按下去和放开的操作,ACTION_MOVE就是手指在屏幕上移动的操作。



在处理多点触摸的过程中,我们还需要用到MotionEvent.ACTION_MASK。一般使用

switch(event.getAction() & MotionEvent.ACTION_MASK)

就可以处理处理多点触摸的ACTION_POINTER_DOWN和ACTION_POINTER_UP事件。代码调用这个“与”操作以后,当第二个手指按下或者放开,就会触发

ACTION_POINTER_DOWN

或者

ACTION_POINTER_UP

事件。




3.代码如下,是照着一个网上的例子写的




package com.example.imagedrag;

import android.os.Bundle;
import android.animation.FloatEvaluator;
import android.app.Activity;
import android.graphics.Matrix;
import android.graphics.PointF;
import android.util.FloatMath;
import android.util.Log;
import android.view.Menu;
import android.view.MotionEvent;
import android.view.View;
import android.view.View.OnTouchListener;
import android.widget.ImageView;

public class MainActivity extends Activity {
	private static final String LOG_TAG = "MY_LOG_TAG";
	private ImageView imageView;
	private float x0;
	private float y0;
	private float x1;
	private float y1;
	private PointF midPoint;
	private float d0;
	private float d1;
	private Matrix matrix = new Matrix();
	private Matrix myMatrix = new Matrix();
	/** 记录是拖拉照片模式还是放大缩小照片模式 */
	private int mode = 0;// 初始状态
	/** 拖拉照片模式 */
	private static final int MODE_DRAG = 1;
	/** 放大缩小照片模式 */
	private static final int MODE_ZOOM = 2;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);

		imageView = (ImageView) findViewById(R.id.image_view);
		imageView.setOnTouchListener(new OnTouchListener() {
			/** 计算两个手指间的距离 */
			private float distance(MotionEvent event) {
				float dx = event.getX(1) - event.getX(0);
				float dy = event.getY(1) - event.getY(0);
				/** 使用勾股定理返回两点之间的距离 */
				return FloatMath.sqrt(dx * dx + dy * dy);
			}

			/** 计算两个手指间的中间点 */
			private PointF mid(MotionEvent event) {
				float midX = (event.getX(1) + event.getX(0)) / 2;
				float midY = (event.getY(1) + event.getY(0)) / 2;
				return new PointF(midX, midY);
			}

			@Override
			public boolean onTouch(View v, MotionEvent event) {
				// TODO Auto-generated method stub
				switch (event.getAction() & MotionEvent.ACTION_MASK) {
				case MotionEvent.ACTION_DOWN:
					mode = MODE_DRAG;
					x0 = event.getRawX();
					y0 = event.getRawY();
					myMatrix.set(imageView.getImageMatrix());
					break;
				case MotionEvent.ACTION_POINTER_DOWN:
					Log.i(LOG_TAG, "ACTION_POINTER_DOWN");
					mode = MODE_ZOOM;
					/** 计算两个手指间的距离 */
					d0 = distance(event);
					/** 计算两个手指间的中间点 */
					midPoint = mid(event);
					myMatrix.set(imageView.getImageMatrix());

					break;
				case MotionEvent.ACTION_MOVE:
					if (mode == MODE_DRAG) {
						x1 = event.getRawX();
						y1 = event.getRawY();
						matrix.set(myMatrix);
						matrix.postTranslate(x1 - x0, y1 - y0);
					} else if (mode == MODE_ZOOM) {
						d1 = distance(event);
						float scale = d1 / d0;
						matrix.set(myMatrix);
						matrix.postScale(scale, scale, midPoint.x, midPoint.y);

					}
					break;
				case MotionEvent.ACTION_UP:
					break;
				case MotionEvent.ACTION_POINTER_UP:
					mode = 0;
					break;
				default:
					break;
				}
				imageView.setImageMatrix(matrix);
				return true;
			}
		});
	}

	@Override
	public boolean onCreateOptionsMenu(Menu menu) {
		// Inflate the menu; this adds items to the action bar if it is present.
		getMenuInflater().inflate(R.menu.main, menu);
		return true;
	}

}

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".MainActivity" >

    <ImageView android:id="@+id/image_view"
        android:layout_width="fill_parent"
        android:layout_height="fill_parent"
        android:src="@drawable/bb"
        android:scaleType="matrix" />

</RelativeLayout>

















版权声明:本文为u010335298原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。