Draw Rectangle Over ImageView para resaltar que puede ser zoom in-out en android

He sido referir este ejemplo de SO abajo son ellos.

1. Dibujar línea sobre ImageView

2. Dibujar imagen sobre ImageView

3.I tienen uso esta clase de ImageView para que mi imagen se convierta en acercamiento-hacia fuera imagen Pinch código del zumbido google .

Ahora lo que intento hacer es:

Quiero hacer zoom en pellizcar la pantalla y otro punto es que cuando hago solo toque un rectángulo debe ser dibujado sobre la vista de la imagen y también quiero que este rectángulo debe obtener zoom in & out con Zoom de imageView y Zoom Out y quiero para utilizarlo a través de la clase ScaleImageView .

La salida de esto debe verse como debajo de la imagen.

se puede ver cuando hago un solo toque sobre ImageViewit dibujará rectángulo como mostrar en la imagen

Y también sabía que esto se puede hacer usando el Relative Layout o puede ser mediante el uso de SurfaceView en android, pero soy nuevo para el uso Vista de la superficie y también me preocupa si uso otra vista sobre imageView para dibujar y luego hacer esto tanto ver el trabajo para acercar y alejar. Si uso SurfaceView en ImageView, entonces Image puede ser capaz de acercar y alejar.

Mediante el uso de este pinch zoom in-out ejemplo de aquí. ejemplo que uso pinch zoom .

Ahora dibujo el rectángulo en el solo tacto por debajo del código en ese ejemplo.

 @Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); Log.v("Log_tag", "Draw Image View"); //Bitmap _scratch = BitmapFactory.decodeResource(getResources(), R.drawable.rect_image); //canvas.drawColor(Color.BLACK); //canvas.drawBitmap(_scratch, 10, 10, null); Drawable d = getDrawable(); //Bitmap bitmap = ((BitmapDrawable)d).getBitmap(); Bitmap bitmap = Bitmap.createBitmap(100, 100, Bitmap.Config.RGB_565); /*if(bitmap!=null){ if (x1 > 0 || x2 > 0 || y1 > 0 || y2 > 0){ Log.v("Log_tag", "ImageBitmap is draw"); //Canvas mCanvas=new Canvas(bitmap); //mCanvas.drawRect(x1, y1, x2, y2, mPaint); // canvas.clipRect(left, top, right, bottom); paint.setStyle(Paint.Style.FILL_AND_STROKE); paint.setStrokeWidth(1); paint.setColor(0xFF000000 + ((int)(PRESET_PRESSURE * pressure) <<16) + ((int)(PRESET_PRESSURE * pressure) << 8) + (int)(PRESET_PRESSURE * pressure)); //mCanvas.drawCircle(x1, y1, (PRESET_SIZE * size), paint); } }*/ //canvas.save(); //canvas.translate(mPosX, mPosY); // canvas.scale(mScaleFactor, mScaleFactor); mBitmapDrawable.draw(canvas); Paint myPaint = new Paint(); myPaint.setColor(Color.GREEN); myPaint.setStyle(Paint.Style.STROKE); myPaint.setStrokeWidth(1); Log.v("Log_tag", "Redraw with this point"); canvas.drawRect(rect_x1-30,rect_y1-30, rect_x1+30, rect_y1+30, myPaint); mCanvasMatrix=canvas.getMatrix(); mImageCanvas=canvas; canvas.setMatrix(mCanvasMatrix); //canvas.restore(); } 

ACTUALIZAR

A continuación se muestra mi clase utilizada para el zoom de pellizcar ImageView.

 public class ImageViewScale extends ImageView implements OnTouchListener { @Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); //canvas.save(); //canvas.scale(mScale, mScale); mCanvasMatrix=canvas.getMatrix(); Paint myPaint = new Paint(); myPaint.setColor(Color.GREEN); myPaint.setStyle(Paint.Style.STROKE); myPaint.setStrokeWidth(1); if(mCanvasMatrix!=null){ if(orignalRect!=null) mCanvasMatrix.mapRect(orignalRect); } if(orignalRect!=null){ canvas.drawRect(orignalRect,myPaint); } //canvas.drawRect(rect_x1-30,rect_y1-30, rect_x1+30, rect_y1+30, myPaint); int canavs_width=canvas.getWidth(); int canavs_height=canvas.getHeight(); canvas.setMatrix(mCanvasMatrix); //canvas.setMatrix(mMatrix); if(mDrawable!=null){ //mDrawable.draw(canvas); Log.v("Log_tag", "draw with Canvas is done W:"+ canavs_width+"H:"+ canavs_height); } //canvas.restore(); } private float MAX_SCALE = 2f; private int DOUBLE_TAP_SECOND = 400; private float CANVAS_MAX_SCALE=2f; float rect_x1=50; float rect_y1=150; private Matrix mMatrix; private Matrix mCanvasMatrix; private final float[] mCanvasMatrixValues=new float[9]; private final float[] mMatrixValues = new float[9]; RectF orignalRect; private Drawable mDrawable; private ImageView mImageView; // display width height. private int mWidth; private int mHeight; private int mIntrinsicWidth; private int mIntrinsicHeight; private int mCanvasWidth; private int mCanvasHeight; private float mScale; private float mMinScale; private float mCanvasMinScale; // double tap for determining private long mLastTime = 0; private boolean isDoubleTap; private int mDoubleTapX; private int mDoubleTapY; private float mPrevDistance; private boolean isScaling; private int mPrevMoveX; private int mPrevMoveY; String TAG = "ScaleImageView"; public ImageViewScale(Context context, AttributeSet attr) { super(context, attr); initialize(); } public ImageViewScale(Context context) { super(context); initialize(); } @Override public void setImageBitmap(Bitmap bm) { super.setImageBitmap(bm); this.initialize(); } private void initialize() { this.setScaleType(ScaleType.MATRIX); this.mMatrix = new Matrix(); Drawable d = getDrawable(); mDrawable=d; if (d != null) { mIntrinsicWidth = d.getIntrinsicWidth(); mIntrinsicHeight = d.getIntrinsicHeight(); setOnTouchListener(this); } } @Override protected boolean setFrame(int l, int t, int r, int b) { Log.v("Log_tag", "Size are here "+ l + t + r+ b); mWidth = r - l; mHeight = b - t; mMatrix.reset(); mScale = (float) r / (float) mIntrinsicWidth; int paddingHeight = 0; int paddingWidth = 0; // scaling vertical if (mScale * mIntrinsicHeight > mHeight) { mScale = (float) mHeight / (float) mIntrinsicHeight; mMatrix.postScale(mScale, mScale); paddingWidth = (r - mWidth) / 2; paddingHeight = 0; // scaling horizontal } else { mMatrix.postScale(mScale, mScale); paddingHeight = (b - mHeight) / 2; paddingWidth = 0; } mMatrix.postTranslate(paddingWidth, paddingHeight); setImageMatrix(mMatrix); mMinScale = mScale; zoomTo(mScale, mWidth / 2, mHeight / 2); cutting(); return super.setFrame(l, t, r, b); } protected float getValue(Matrix matrix, int whichValue) { matrix.getValues(mMatrixValues); return mMatrixValues[whichValue]; } //New Added protected float getCanvasValue(Matrix matrix,int whichvalues){ mCanvasMatrix.getValues(mCanvasMatrixValues); return mCanvasMatrixValues[whichvalues]; } protected float getScale() { return getValue(mMatrix, Matrix.MSCALE_X); } //New added Method protected float getCanvasScale(){ return getCanvasValue(mCanvasMatrix, Matrix.MSCALE_X); } protected float getTranslateX() { return getValue(mMatrix, Matrix.MTRANS_X); } //New added Method protected float getCanvasTranslateX(){ return getCanvasValue(mCanvasMatrix, Matrix.MTRANS_X); } protected float getTranslateY() { return getValue(mMatrix, Matrix.MTRANS_Y); } //New Added Method protected float getCanvasTranslateY(){ return getCanvasValue(mCanvasMatrix, Matrix.MTRANS_Y); } protected void maxZoomTo(int x, int y) { if (mMinScale != getScale() && (getScale() - mMinScale) > 0.1f) { // threshold 0.1f float scale = mMinScale / getScale(); zoomTo(scale, x, y); } else { float scale = MAX_SCALE / getScale(); zoomTo(scale, x, y); } } protected void zoomTo(float scale, int x, int y) { if (getScale() * scale < mMinScale) { return; } if (scale >= 1 && getScale() * scale > MAX_SCALE) { return; } mMatrix.postScale(scale, scale); // move to center mMatrix.postTranslate(-(mWidth * scale - mWidth) / 2, -(mHeight * scale - mHeight) / 2); // move x and y distance mMatrix.postTranslate(-(x - (mWidth / 2)) * scale, 0); mMatrix.postTranslate(0, -(y - (mHeight / 2)) * scale); setImageMatrix(mMatrix); } protected void zoomToCanvas(float scale,int x,int y){ if(getCanvasScale()* scale<mCanvasMinScale){ return; } if(scale>=1 && getCanvasScale()*scale> CANVAS_MAX_SCALE){ return; } mCanvasMatrix.postScale(scale, scale); } public void cutting() { int width = (int) (mIntrinsicWidth * getScale()); int height = (int) (mIntrinsicHeight * getScale()); if (getTranslateX() < -(width - mWidth)) { mMatrix.postTranslate(-(getTranslateX() + width - mWidth), 0); } if (getTranslateX() > 0) { mMatrix.postTranslate(-getTranslateX(), 0); } if (getTranslateY() < -(height - mHeight)) { mMatrix.postTranslate(0, -(getTranslateY() + height - mHeight)); } if (getTranslateY() > 0) { mMatrix.postTranslate(0, -getTranslateY()); } if (width < mWidth) { mMatrix.postTranslate((mWidth - width) / 2, 0); } if (height < mHeight) { mMatrix.postTranslate(0, (mHeight - height) / 2); } setImageMatrix(mMatrix); } private float distance(float x0, float x1, float y0, float y1) { float x = x0 - x1; float y = y0 - y1; return FloatMath.sqrt(x * x + y * y); } private float dispDistance() { return FloatMath.sqrt(mWidth * mWidth + mHeight * mHeight); } @Override public boolean onTouchEvent(MotionEvent event) { int touchCount = event.getPointerCount(); switch (event.getAction()) { case MotionEvent.ACTION_DOWN: case MotionEvent.ACTION_POINTER_1_DOWN: case MotionEvent.ACTION_POINTER_2_DOWN: if (touchCount >= 2) { float distance = distance(event.getX(0), event.getX(1), event.getY(0), event.getY(1)); mPrevDistance = distance; isScaling = true; } else { if (System.currentTimeMillis() <= mLastTime + DOUBLE_TAP_SECOND) { if (30 > Math.abs(mPrevMoveX - event.getX()) + Math.abs(mPrevMoveY - event.getY())) { isDoubleTap = true; mDoubleTapX = (int) event.getX(); mDoubleTapY = (int) event.getY(); } } mLastTime = System.currentTimeMillis(); mPrevMoveX = (int) event.getX(); mPrevMoveY = (int) event.getY(); } break; case MotionEvent.ACTION_MOVE: if (touchCount >= 2 && isScaling) { float dist = distance(event.getX(0), event.getX(1), event.getY(0), event.getY(1)); float scale = (dist - mPrevDistance) / dispDistance(); mPrevDistance = dist; scale += 1; scale = scale * scale; zoomTo(scale, mWidth / 2, mHeight / 2); cutting(); } else if (!isScaling) { int distanceX = mPrevMoveX - (int) event.getX(); int distanceY = mPrevMoveY - (int) event.getY(); mPrevMoveX = (int) event.getX(); mPrevMoveY = (int) event.getY(); mMatrix.postTranslate(-distanceX, -distanceY); cutting(); } break; case MotionEvent.ACTION_UP: case MotionEvent.ACTION_POINTER_UP: case MotionEvent.ACTION_POINTER_2_UP: if (event.getPointerCount() <= 1) { isScaling = false; if (isDoubleTap) { if (30 > Math.abs(mDoubleTapX - event.getX()) + Math.abs(mDoubleTapY - event.getY())) { maxZoomTo(mDoubleTapX, mDoubleTapY); cutting(); } } } isDoubleTap = false; break; } return true; } @Override public boolean onTouch(View v, MotionEvent event) { int count_touch=event.getPointerCount(); switch(event.getAction()){ case MotionEvent.ACTION_UP: float point_x=event.getX(); float point_y=event.getY(); rect_x1=point_x; rect_y1=point_y; if(count_touch==1){ orignalRect=new RectF(rect_x1-30, rect_y1-30, rect_x1+30, rect_y1+30); invalidate(); } break; } return super.onTouchEvent(event); } } 

Es posible que desee comprobar Matrix.mapRect . Utilice este método para transformar el rectángulo en la misma cantidad que la imagen en la vista de imagen.

 boolean onTouch(MotionEvent ev) { .... // this rect dimensions should be initial values and should be a member. mOriginalRect = new RectF(rect_x1-30, rect_y1-30, rect_x1+30, rect_y1+30); ..... } @Override protected void onDraw(Canvas canvas) { .... mCanvasMatrix = canvas.getMatrix(); ///matrix should have scale values.. mCanvasMatrix.mapRect(tempRect, mOriginalRect); // mOriginalRect is src canvas.drawRect(tempRect, myPaint); // draw tempRect.. .... } 

Probablemente quiera extender ImageView, en las vistas onDraw (Canvas) que dibujaría el rectángulo.

Extender ImageView una vez para hacer en pinch-to-zoom (que debe utilizar el Matrix en la vista de imagen para implementar el zoom pinch)

Extenderlo de nuevo para tomar un rectángulo, transformarlo con la matriz de imagen y dibujarlo después de la llamada super.draw ().

@ Herry – He hecho un pequeño POC sobre este tipo de problema y encontró que tenemos que transformar exactamente el lienzo como estamos transformando la imagen.

Ejemplo:

 @Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); Resources res = this.getResources(); Bitmap mBitmap = BitmapFactory.decodeResource(res, R.drawable.circlered); canvas.save(); canvas.translate(1f, 1f); canvas.restore(); canvas.save(); canvas.concat(mMatrix); canvas.drawBitmap(mBitmap, 100, 150, null); } 

¡Prueba esto! y déjame saber.

Dibujar Ractangle imageview

  public class RactangleImageView extends ImageView { private static final int strockwidth = 6; private Paint paintBorder; private Bitmap bitmap; private int strokeWidthPx; private RectF rectF; private RadialGradient radialGradient; public RactangleImageView(Context context) { super(context); init(); } private void init() { bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.imageicon); strokeWidthPx = (int) (strockwidth * getResources().getDisplayMetrics().density); int halfStrokeWidthPx = strokeWidthPx / 2; paintBorder = new Paint(); paintBorder.setStyle(Paint.Style.FILL); int totalWidth = bitmap.getWidth() + strokeWidthPx * 2; int totalHeight = bitmap.getHeight() + strokeWidthPx * 2; radialGradient = new RadialGradient(totalWidth /2, totalHeight /2, totalWidth /2, new int[] {Color.BLACK, Color.GREEN}, null, Shader.TileMode.MIRROR); paintBorder.setShader(radialGradient); setImageBitmap(Bitmap.createBitmap(totalWidth, totalHeight, Bitmap.Config.ARGB_8888)); rectF = new RectF(halfStrokeWidthPx, halfStrokeWidthPx, totalWidth - halfStrokeWidthPx, totalHeight - halfStrokeWidthPx); } @Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); canvas.drawRoundRect(rectF, 40, 40, paintBorder); canvas.drawBitmap(bitmap,strokeWidthPx, strokeWidthPx, null); } } 
FlipAndroid es un fan de Google para Android, Todo sobre Android Phones, Android Wear, Android Dev y Aplicaciones para Android Aplicaciones.