自定义viewpager,实现图片多指触控,双击,放大或缩小,和viewpager的冲突

//在main中的布局


//在ViewPager的item中的布局


//自定义ImageView
import android.R.bool;
import android.content.Context;
import android.graphics.Matrix;
import android.graphics.RectF;
import android.graphics.drawable.Drawable;
import android.support.v4.view.ViewPager;
import android.util.AttributeSet;
import android.view.GestureDetector;
import android.view.MotionEvent;
import android.view.ScaleGestureDetector;
import android.view.ScaleGestureDetector.OnScaleGestureListener;
import android.view.View;
import android.view.ViewConfiguration;
import android.view.ViewTreeObserver.OnGlobalLayoutListener;
import android.widget.ImageView;
import android.view.View.OnTouchListener;

public class ZoomImageView extends ImageView implements OnGlobalLayoutListener, OnScaleGestureListener,OnTouchListener{

	private boolean mOnce = false;
	//初始化缩放的值
	private float mInitScale;
	//双击放大值到达的值
	private float mMidScale;
	//放大的最大值
	private float mMaxScale;
	private Matrix mScaleMatrix;
	//捕获用户多指触控时缩放的比例‘
	private ScaleGestureDetector mScaleGestureDetector;
	
	//====================图片自由移动
	private int mLastPointerCount;//记录上一次多点触控的数量
	private float mLastX;
	private float mLastY;//记录最后一次x,y的坐标
	private int mTouchSlop;//获取系统的值
	private boolean isCanDrag;
	//判断 控件左右,上下是否超出
	private  boolean isCheckLeftAndRight;
	private  boolean isCheckTopAndBottom;
	
	//==========双击放大与缩小
	private GestureDetector mGestureDetector;
	private boolean  isAutoScale;
	public ZoomImageView(Context context) {
		super(context); 
	}
	public ZoomImageView(Context context, AttributeSet attrs) {
		super(context, attrs); 
		mScaleMatrix = new Matrix();
		mScaleGestureDetector = new ScaleGestureDetector(context, this);
	    setOnTouchListener(this);
	    //图片自由移动时,获取的系统的值
	    mTouchSlop = ViewConfiguration.get(context).getScaledTouchSlop();
	    mGestureDetector = new GestureDetector(context, 
	    		new GestureDetector.SimpleOnGestureListener(){
	    	public boolean onDoubleTap(MotionEvent e) {
	    		//如果用户已经点击过了,并且此时正在放大或者缩小,就不让点击
	    		if(isAutoScale)
					return true;
	    		
	    		//当前点击的x,y的坐标,已点击的点为屏幕的中心点
	    		float x = e.getX();
	    		float y = e.getY();
	    		
	    		if(getScale()mTargetScale){//缩小
				tmpScale = SMALL;
			}
			
		}

		public void run() {
			//进行缩放
			mScaleMatrix.postScale(tmpScale, tmpScale, x, y);
			checkBorderAndCenterWhenScale();
			setImageMatrix(mScaleMatrix);
			
			float currentScale = getScale();
			
			if(tmpScale >1.0f&¤tScalemTargetScale){
				//每16毫秒执行一次这个方法
				postDelayed(this, 50);
			}else{//设置为我们的目标值
				float scale = mTargetScale/currentScale;
				mScaleMatrix.postScale(scale, scale, x, y);
				checkBorderAndCenterWhenScale();
				setImageMatrix(mScaleMatrix);
				isAutoScale = false;
			}
		}
		
	}

	//全局布局完成之后,会执行这样一个方法
	//获得ImagerView加载完成的图片
	public void onGlobalLayout() {
		//保证只会进行一次的比较
		if(!mOnce){
			//获得控件的宽高
			//一般控件的宽高,就是屏幕的宽高
			int wight = getWidth();
			int height = getHeight();
			//得到我们的图片,以及宽和高
			Drawable d = getDrawable();
			if(d == null){
				return ;
			}
			int dw = d.getIntrinsicWidth();
			int dh = d.getIntrinsicHeight();
			
			//设置一个缩放值
			float scale = 1.0f;
			
			//如果图片的宽度大于控件的宽度,高度小于控件的宽高,那么将其缩放
			if(dw>wight && dhheight){
				scale = height*1.0f/dh;
			}
			
			//宽高均小于控件宽高,宽高均大于控件宽高,将其缩放或扩大
			if((dw>wight && dh>height)||(dw1.0f)||(scale>mInitScale&&scaleFactor<1.0f)){
			//当你想缩的特别小时,我们就将mInitScale设置给你
			if(scale*scaleFactor < mInitScale){
				scaleFactor = mInitScale/scale;
			}
			//当你想放的特别大时,我们就将mMaxScale设置给你
			if(scale*scaleFactor > mMaxScale){
				scaleFactor = mMaxScale/scale;
			}
			
			//缩放中心点
			mScaleMatrix.postScale(scaleFactor, scaleFactor,detector.getFocusX(),detector.getFocusY());
			//在缩放的时候,进行边界的控制,以及我们的位置的控制
			checkBorderAndCenterWhenScale();
			setImageMatrix(mScaleMatrix);
			 
		}
		return true;
	}
	
	public boolean onScaleBegin(ScaleGestureDetector detector) {
		//必须将返回值改为true;
		return true;
	}

	public void onScaleEnd(ScaleGestureDetector detector) {
	}
   
	//RectF是一个矩形,里边所有的值是浮点型
	//获得图片放大缩小以后的宽和高,以及left,right,top,buttom
	private RectF getMatrixRectF(){
		Matrix matrix = mScaleMatrix;
		RectF rectF = new RectF();
		Drawable d = getDrawable();
		if(d != null){
			rectF.set(0, 0, d.getIntrinsicWidth(), d.getIntrinsicHeight());
		    matrix.mapRect(rectF);
		}
		return rectF;
	}
	
	//在缩放的时候,进行边界的控制,以及我们的位置的控制
	private void checkBorderAndCenterWhenScale() {
		//调用 getMatrixRectF()获得RectF
		RectF rect = getMatrixRectF();
		
		//左边和右边的差值
		float deltaX = 0;
		float deltaY = 0;
		
		//宽高
		int width = getWidth();
		int height = getHeight();
		//缩放时,进行边界测试,放置出现白边
		//rect.width()是通过放大缩小之后的图片的宽度
		//水平方向上的控制
		if(rect.width() >= width){
			 if(rect.left>0){
				 deltaX = -rect.left;
			 }
			 if(rect.right=height){
			if(rect.top>0){
				deltaY = -rect.top;
			}
			if(rect.bottomgetWidth()+0.01||rectF1.height()>getHeight()+0.01){
				getParent().requestDisallowInterceptTouchEvent(true);
			}
		
		case MotionEvent.ACTION_MOVE:
			if(rectF1.width()>getWidth()+0.01||rectF1.height()>getHeight()+0.01){
				getParent().requestDisallowInterceptTouchEvent(true);
			}
			//记录x,y的偏移量(这次的中心点坐标减去上次中心点的坐标)
			float dx = x-mLastX;
			float dy = y-mLastY;
			
			//在手指触控的个数发生变化,但是又想移动图片时,去判断,移动的偏移量是否足以触发移动
			if(!isCanDrag){
				isCanDrag = isMoveAction(dx, dy);
			}
			
			//移动过程的一个操作
			if(isCanDrag){
				RectF rectF = getMatrixRectF();
				if(getDrawable() != null){
					//每次都去检测图片
					isCheckLeftAndRight = isCheckTopAndBottom = true;
					//如果宽度小于控件宽度 ,不允许横向移动(说明此图片横向上已完全显示)
					if(rectF.width()0 && isCheckTopAndBottom){
			deltaY = -rectF.top;
		}
		
		//底部不能出现 白边
		if(rectF.bottom0 && isCheckLeftAndRight){
			deltaX = -rectF.left;
		}
		
		//右边不能出现白边
		if(rectF.rightmTouchSlop;
	}
	
}

//在mainAcitity中
import com.example.view.ZoomImageView;

import android.os.Bundle;
import android.app.Activity;
import android.support.v4.view.PagerAdapter;
import android.support.v4.view.ViewPager;
import android.view.Menu;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ZoomButton;

public class MainActivity extends Activity {

    private ViewPager mViewPager;
    private int [] mImgs = new int[]{R.drawable.af,R.drawable.ae,R.drawable.ah};

	protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        mViewPager = (ViewPager) findViewById(R.id.view_pager);
        mViewPager.setAdapter(new PagerAdapter() {
			
			public boolean isViewFromObject(View arg0, Object arg1) {
				return arg0 == arg1;
			}
			
			public int getCount() {
				return mImgs.length;
			}
			
			public void destroyItem(ViewGroup container, int position,
					Object object) {
			    container.removeView((View)object);
			}
			
			public Object instantiateItem(ViewGroup container, int position) {
				View view = View.inflate(MainActivity.this, R.layout.vp, null);
				ZoomImageView imageView = (ZoomImageView) view.findViewById(R.id.zv);
				imageView.setImageResource(mImgs[position]);
				container.addView(view);
				return view;
			}
			
		});
        
    }
    
}


你可能感兴趣的:(自定义viewpager,实现图片多指触控,双击,放大或缩小,和viewpager的冲突)