Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Zoom listener for PhotoView

I'm using Chris Bane's PhotoView to display ImageViews in a ViewPager. I want to disable the ViewPager's scrolling when the user has zoomed into an image. I already found this Hacky ViewPager which can be used to enable/disable scrolling by calling toggleLock().

public class HackyViewPager extends ViewPager {

    private boolean isLocked;

    public HackyViewPager(Context context) {
        super(context);
        isLocked = false;
    }

    public HackyViewPager(Context context, AttributeSet attrs) {
        super(context, attrs);
        isLocked = false;
    }

    @Override
    public boolean onInterceptTouchEvent(MotionEvent ev) {
        if (!isLocked) {
            try {
                return super.onInterceptTouchEvent(ev);
            }
            catch (IllegalArgumentException e) {
                e.printStackTrace();
                return false;
            }
        }
        return false;
    }

    @Override
    public boolean onTouchEvent(MotionEvent event) {
        return !isLocked && super.onTouchEvent(event);
    }

    public void toggleLock() {
        isLocked = !isLocked;
    }

    public void setLocked(boolean isLocked) {
        this.isLocked = isLocked;
    }

    public boolean isLocked() {
        return isLocked;
    }

}

So my problem here is that I'm not sure at which point I have to call toogleLock(). I guess I have to implement a listener, but I'm not sure which one would be the best. Thanks in advance for helping me out!

EDIT: I figured it out on my own!

photoview.setOnMatrixChangeListener(new PhotoViewAttacher.OnMatrixChangedListener() {
            @Override
            public void onMatrixChanged(RectF rectF) {
                if (photoview.getScale() > 1) {
                    sPager.setLocked(true);
                } else {
                    sPager.setLocked(false);
                }
            }
        });
like image 831
T-Rex96 Avatar asked Jul 20 '15 17:07

T-Rex96


3 Answers

For me, photoview.getScale() == 1 always and I use the zoom.

The scaleFactor in setOnScaleChangeListener is only the scale at certain time independent of the previous value. We need to calculate the cumulative scaleFactor .

private float cumulScaleFactor = 1;

photoViewAttacher.setOnScaleChangeListener(new PhotoViewAttacher.OnScaleChangeListener() {
 @Override
 public void onScaleChange(final float scaleFactor, final float focusX, final float focusY) {
     cumulScaleFactor = cumulScaleFactor * scaleFactor;

     sPager.setLocked(isValueApproximate(1.0f, cumulScaleFactor));
 }
});


private boolean isValueApproximate(final float expectedValue, final float value) {
    final float errorMargin = 0.01f;
    return Math.abs(expectedValue - value) < errorMargin;
}
like image 90
Raymond Chenon Avatar answered Oct 17 '22 16:10

Raymond Chenon


Instead of using HackyViewPager I set photoview.setAllowParentInterceptOnEdge(true) , when photo Scale = 1.

photoView.setOnMatrixChangeListener(new PhotoViewAttacher.OnMatrixChangedListener() {
  @Override
  public void onMatrixChanged(RectF rect) {
    photoView.setAllowParentInterceptOnEdge(photoView.getScale() == 1);
  }
});
like image 36
Mashmori Avatar answered Oct 17 '22 15:10

Mashmori


I joined @Mashmori and @Raymond Chenon anwsers and you get:

photoView.setOnMatrixChangeListener {
        val isZoomedOut = isValueApproximate(photoView.scale, 1f)
        photoView.setAllowParentInterceptOnEdge(isZoomedOut)
    }

private fun isValueApproximate(expectedValue: Float, value: Float): Boolean {
    val errorMargin = 0.01f
    return abs(expectedValue - value) < errorMargin
}
like image 1
WinterChilly Avatar answered Oct 17 '22 16:10

WinterChilly