可缩放性ImageView(可以放大缩小)

您所在的位置:网站首页 缩小放大图片的软件叫什么 可缩放性ImageView(可以放大缩小)

可缩放性ImageView(可以放大缩小)

2024-07-07 03:36| 来源: 网络整理| 查看: 265

由于项目需求的原因,最近一直在研究可缩放性ImageView,用本文来记录一下最近所学:

该ImageView的实现功能有:

1)初步打开时,图片按比例满屏(填充ImageView)显示。

2)在放大缩小过程中,可以控制最大放大比例和最小缩小比例。

3)在缩放过程中,若图片的宽或高小于ImageView,则在图片在宽或高居中显示。

4)在放大后,可以移动图片,并且限制好移动的边界,不会超出图片。

5)实现双击放大或缩小的功能。(若当前图片显示为最大的比例则缩小为最小比例,若不是最小比例则放大了最大比例)

在讲代码之前,首先应该说说一个类,Matrix。因为我们在处理图片的过程中,需要图片的位移,缩放等等,而Matrix刚好就是帮我们封装好了这些数据,具体的,大家可以看看这篇文章:android 从matrix获取处理过的图片的实际宽度重点是了解Matrix里面数组的含义。

上代码,具体的说明代码都有一一介绍:

MyZoomImageView.java文件:

[java]  view plain  copy package com.xiaoyan.doubletouch;      import android.content.Context;   import android.graphics.Matrix;   import android.graphics.PointF;   import android.graphics.drawable.Drawable;   import android.util.AttributeSet;   import android.util.FloatMath;   import android.view.MotionEvent;   import android.view.View;   import android.view.ViewTreeObserver;   import android.view.ViewTreeObserver.OnGlobalLayoutListener;   import android.widget.ImageView;      /**   * 缩放ImageView   *    * @author xiejinxiong   *    */   public class MyZoomImageView extends ImageView {          /** ImageView高度 */       private int imgHeight;       /** ImageView宽度 */       private int imgWidth;       /** 图片高度 */       private int intrinsicHeight;       /** 图片宽度 */       private int intrinsicWidth;       /** 最大缩放级别 */       private float mMaxScale = 2.0f;       /** 最小缩放级别 */       private float mMinScale = 0.2f;       /** 用于记录拖拉图片移动的坐标位置 */       private Matrix matrix = new Matrix();       /** 用于记录图片要进行拖拉时候的坐标位置 */       private Matrix currentMatrix = new Matrix();       /** 记录第一次点击的时间 */       private long firstTouchTime = 0;       /** 时间点击的间隔 */       private int intervalTime = 250;       /** 第一次点完坐标 */       private PointF firstPointF;          public MyZoomImageView(Context context) {           super(context);           initUI();       }          public MyZoomImageView(Context context, AttributeSet attrs) {           super(context, attrs);           initUI();       }          public MyZoomImageView(Context context, AttributeSet attrs, int defStyle) {           super(context, attrs, defStyle);           // TODO Auto-generated constructor stub           initUI();       }          /**       * 初始化UI       */       private void initUI() {              this.setScaleType(ScaleType.FIT_CENTER);           this.setOnTouchListener(new TouchListener());              getImageViewWidthHeight();           getIntrinsicWidthHeight();       }          /**       * 获得图片内在宽高       */       private void getIntrinsicWidthHeight() {           Drawable drawable = this.getDrawable();              // 初始化bitmap的宽高           intrinsicHeight = drawable.getIntrinsicHeight();           intrinsicWidth = drawable.getIntrinsicWidth();       }          private final class TouchListener implements OnTouchListener {              /** 记录是拖拉照片模式还是放大缩小照片模式 */           private int mode = 0;// 初始状态           /** 拖拉照片模式 */           private static final int MODE_DRAG = 1;           /** 放大缩小照片模式 */           private static final int MODE_ZOOM = 2;           /** 用于记录开始时候的坐标位置 */           private PointF startPoint = new PointF();           /** 两个手指的开始距离 */           private float startDis;           /** 两个手指的中间点 */           private PointF midPoint;              public boolean onTouch(View v, MotionEvent event) {                  /** 通过与运算保留最后八位 MotionEvent.ACTION_MASK = 255 */               switch (event.getAction() & MotionEvent.ACTION_MASK) {// 单点监听和多点触碰监听               // 手指压下屏幕               case MotionEvent.ACTION_DOWN:                   mode = MODE_DRAG;                   // 记录ImageView当前的移动位置                   currentMatrix.set(getImageMatrix());                   startPoint.set(event.getX(), event.getY());                   matrix.set(currentMatrix);                   makeImageViewFit();                   break;               // 手指在屏幕上移动,改事件会被不断触发               case MotionEvent.ACTION_MOVE:                   // 拖拉图片                   if (mode == MODE_DRAG) {                       // System.out.println("ACTION_MOVE_____MODE_DRAG");                       float dx = event.getX() - startPoint.x; // 得到x轴的移动距离                       float dy = event.getY() - startPoint.y; // 得到x轴的移动距离                       // 在没有移动之前的位置上进行移动z                       matrix.set(currentMatrix);                       float[] values = new float[9];                       matrix.getValues(values);                       dx = checkDxBound(values, dx);                       dy = checkDyBound(values, dy);                       matrix.postTranslate(dx, dy);                      }                   // 放大缩小图片                   else if (mode == MODE_ZOOM) {                       float endDis = distance(event);// 结束距离                       if (endDis > 10f) { // 两个手指并拢在一起的时候像素大于10                           float scale = endDis / startDis;// 得到缩放倍数                           matrix.set(currentMatrix);                              float[] values = new float[9];                           matrix.getValues(values);                              scale = checkFitScale(scale, values);                              matrix.postScale(scale, scale, midPoint.x, midPoint.y);                          }                   }                   break;               // 手指离开屏幕               case MotionEvent.ACTION_UP:                   setDoubleTouchEvent(event);                  case MotionEvent.ACTION_POINTER_UP:                   // System.out.println("ACTION_POINTER_UP");                   mode = 0;                   // matrix.set(currentMatrix);                   float[] values = new float[9];                   matrix.getValues(values);                   makeImgCenter(values);                   break;               // 当屏幕上已经有触点(手指),再有一个触点压下屏幕               case MotionEvent.ACTION_POINTER_DOWN:                   // System.out.println("ACTION_POINTER_DOWN");                   mode = MODE_ZOOM;                   /** 计算两个手指间的距离 */                   startDis = distance(event);                   /** 计算两个手指间的中间点 */                   if (startDis > 10f) { // 两个手指并拢在一起的时候像素大于10                       midPoint = mid(event);                       // 记录当前ImageView的缩放倍数                       currentMatrix.set(getImageMatrix());                   }                   break;               }               setImageMatrix(matrix);               return true;           }              /** 计算两个手指间的距离 */           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);           }              /**           * 和当前矩阵对比,检验dy,使图像移动后不会超出ImageView边界           *            * @param values           * @param dy           * @return           */           private float checkDyBound(float[] values, float dy) {                  float height = imgHeight;               if (intrinsicHeight * values[Matrix.MSCALE_Y]  0)                   dy = -values[Matrix.MTRANS_Y];               else if (values[Matrix.MTRANS_Y] + dy 


【本文地址】


今日新闻


推荐新闻


CopyRight 2018-2019 办公设备维修网 版权所有 豫ICP备15022753号-3