diff --git a/photoview/src/main/java/com/github/chrisbanes/photoview/PhotoViewAttacher.java b/photoview/src/main/java/com/github/chrisbanes/photoview/PhotoViewAttacher.java
index 67042c18..d9596dc3 100644
--- a/photoview/src/main/java/com/github/chrisbanes/photoview/PhotoViewAttacher.java
+++ b/photoview/src/main/java/com/github/chrisbanes/photoview/PhotoViewAttacher.java
@@ -598,7 +598,7 @@ private void checkAndDisplayMatrix() {
* @param matrix - Matrix to map Drawable against
* @return RectF - Displayed Rectangle
*/
- private RectF getDisplayRect(Matrix matrix) {
+ protected RectF getDisplayRect(Matrix matrix) {
Drawable d = mImageView.getDrawable();
if (d != null) {
mDisplayRect.set(0, 0, d.getIntrinsicWidth(),
diff --git a/sample/build.gradle b/sample/build.gradle
index 51f3e044..802cbf7c 100755
--- a/sample/build.gradle
+++ b/sample/build.gradle
@@ -21,4 +21,6 @@ dependencies {
implementation "com.android.support:recyclerview-v7:$supportLibVersion"
implementation 'com.squareup.picasso:picasso:2.5.2'
implementation project(':photoview')
+
+ implementation 'com.facebook.fresco:fresco:1.3.0'
}
diff --git a/sample/src/main/AndroidManifest.xml b/sample/src/main/AndroidManifest.xml
index bd813a3f..d6e0ac10 100755
--- a/sample/src/main/AndroidManifest.xml
+++ b/sample/src/main/AndroidManifest.xml
@@ -31,6 +31,9 @@
+
+
+
diff --git a/sample/src/main/java/com/github/chrisbanes/photoview/sample/FrescoSampleActivity.java b/sample/src/main/java/com/github/chrisbanes/photoview/sample/FrescoSampleActivity.java
new file mode 100755
index 00000000..9af6d397
--- /dev/null
+++ b/sample/src/main/java/com/github/chrisbanes/photoview/sample/FrescoSampleActivity.java
@@ -0,0 +1,180 @@
+/*******************************************************************************
+ * Copyright 2011, 2012 Chris Banes.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *******************************************************************************/
+package com.github.chrisbanes.photoview.sample;
+
+import android.graphics.Matrix;
+import android.graphics.RectF;
+import android.net.Uri;
+import android.os.Bundle;
+import android.support.v7.app.AppCompatActivity;
+import android.support.v7.widget.Toolbar;
+import android.util.Log;
+import android.view.MenuItem;
+import android.view.MotionEvent;
+import android.view.View;
+import android.widget.ImageView;
+import android.widget.TextView;
+import android.widget.Toast;
+
+import com.facebook.drawee.drawable.ScalingUtils;
+import com.github.chrisbanes.photoview.OnMatrixChangedListener;
+import com.github.chrisbanes.photoview.OnPhotoTapListener;
+import com.github.chrisbanes.photoview.OnSingleFlingListener;
+import com.github.chrisbanes.photoview.sample.fresco.PhotoDraweeView;
+
+import java.util.Random;
+
+
+public class FrescoSampleActivity extends AppCompatActivity {
+
+ static final String PHOTO_TAP_TOAST_STRING = "Photo Tap! X: %.2f %% Y:%.2f %% ID: %d";
+ static final String SCALE_TOAST_STRING = "Scaled to: %.2ff";
+ static final String FLING_LOG_STRING = "Fling velocityX: %.2f, velocityY: %.2f";
+
+ private PhotoDraweeView mPhotoView;
+ private TextView mCurrMatrixTv;
+
+ private Toast mCurrentToast;
+
+ private Matrix mCurrentDisplayMatrix = null;
+
+ @Override
+ public void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+ setContentView(R.layout.activity_fresco_simple_sample);
+
+ Toolbar toolbar = findViewById(R.id.toolbar);
+ toolbar.setTitle("Simple Sample");
+ toolbar.setNavigationIcon(R.drawable.ic_arrow_back_white_24dp);
+ toolbar.setNavigationOnClickListener(new View.OnClickListener() {
+ @Override
+ public void onClick(View v) {
+ onBackPressed();
+ }
+ });
+ toolbar.inflateMenu(R.menu.main_menu);
+ toolbar.setOnMenuItemClickListener(new Toolbar.OnMenuItemClickListener() {
+ @Override
+ public boolean onMenuItemClick(MenuItem item) {
+ switch (item.getItemId()) {
+ case R.id.menu_zoom_toggle:
+ mPhotoView.setZoomable(!mPhotoView.isZoomEnabled());
+ item.setTitle(mPhotoView.isZoomEnabled() ? R.string.menu_zoom_disable : R.string.menu_zoom_enable);
+ return true;
+
+ case R.id.menu_scale_fit_center:
+ mPhotoView.getHierarchy().setActualImageScaleType(ScalingUtils.ScaleType.FIT_CENTER);
+ return true;
+
+ case R.id.menu_scale_fit_start:
+ mPhotoView.getHierarchy().setActualImageScaleType(ScalingUtils.ScaleType.FIT_START);
+ return true;
+
+ case R.id.menu_scale_fit_end:
+ mPhotoView.getHierarchy().setActualImageScaleType(ScalingUtils.ScaleType.FIT_END);
+ return true;
+
+ case R.id.menu_scale_fit_xy:
+ mPhotoView.getHierarchy().setActualImageScaleType(ScalingUtils.ScaleType.FIT_XY);
+ return true;
+
+ case R.id.menu_scale_scale_center:
+ mPhotoView.getHierarchy().setActualImageScaleType(ScalingUtils.ScaleType.CENTER);
+ return true;
+
+ case R.id.menu_scale_scale_center_crop:
+ mPhotoView.getHierarchy().setActualImageScaleType(ScalingUtils.ScaleType.CENTER_CROP);
+ return true;
+
+ case R.id.menu_scale_scale_center_inside:
+ mPhotoView.getHierarchy().setActualImageScaleType(ScalingUtils.ScaleType.CENTER_INSIDE);
+ return true;
+
+ case R.id.menu_scale_random_animate:
+ case R.id.menu_scale_random:
+ Random r = new Random();
+
+ float minScale = mPhotoView.getMinimumScale();
+ float maxScale = mPhotoView.getMaximumScale();
+ float randomScale = minScale + (r.nextFloat() * (maxScale - minScale));
+ mPhotoView.setScale(randomScale, item.getItemId() == R.id.menu_scale_random_animate);
+
+ showToast(String.format(SCALE_TOAST_STRING, randomScale));
+
+ return true;
+ case R.id.menu_matrix_restore:
+ if (mCurrentDisplayMatrix == null)
+ showToast("You need to capture display matrix first");
+ else
+ mPhotoView.setDisplayMatrix(mCurrentDisplayMatrix);
+ return true;
+ case R.id.menu_matrix_capture:
+ mCurrentDisplayMatrix = new Matrix();
+ mPhotoView.getDisplayMatrix(mCurrentDisplayMatrix);
+ return true;
+ }
+ return false;
+ }
+ });
+ mPhotoView = findViewById(R.id.iv_photo);
+ mCurrMatrixTv = findViewById(R.id.tv_current_matrix);
+
+// Drawable bitmap = ContextCompat.getDrawable(this, R.drawable.wallpaper);
+// mPhotoView.setImageDrawable(bitmap);
+ mPhotoView.setImageURI(Uri.parse("http://imgsrc.baidu.com/imgad/pic/item/7dd98d1001e93901cf713c2d71ec54e736d196b6.jpg"));
+ // Lets attach some listeners, not required though!
+ mPhotoView.setOnMatrixChangeListener(new MatrixChangeListener());
+ mPhotoView.setOnPhotoTapListener(new PhotoTapListener());
+ mPhotoView.setOnSingleFlingListener(new SingleFlingListener());
+ }
+
+ private class PhotoTapListener implements OnPhotoTapListener {
+
+ @Override
+ public void onPhotoTap(ImageView view, float x, float y) {
+ float xPercentage = x * 100f;
+ float yPercentage = y * 100f;
+
+ showToast(String.format(PHOTO_TAP_TOAST_STRING, xPercentage, yPercentage, view == null ? 0 : view.getId()));
+ }
+ }
+
+ private void showToast(CharSequence text) {
+ if (mCurrentToast != null) {
+ mCurrentToast.cancel();
+ }
+
+ mCurrentToast = Toast.makeText(FrescoSampleActivity.this, text, Toast.LENGTH_SHORT);
+ mCurrentToast.show();
+ }
+
+ private class MatrixChangeListener implements OnMatrixChangedListener {
+
+ @Override
+ public void onMatrixChanged(RectF rect) {
+ mCurrMatrixTv.setText(rect.toString());
+ }
+ }
+
+ private class SingleFlingListener implements OnSingleFlingListener {
+
+ @Override
+ public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
+ Log.d("PhotoView", String.format(FLING_LOG_STRING, velocityX, velocityY));
+ return true;
+ }
+ }
+}
diff --git a/sample/src/main/java/com/github/chrisbanes/photoview/sample/LauncherActivity.java b/sample/src/main/java/com/github/chrisbanes/photoview/sample/LauncherActivity.java
index 9732861a..5cca8c40 100755
--- a/sample/src/main/java/com/github/chrisbanes/photoview/sample/LauncherActivity.java
+++ b/sample/src/main/java/com/github/chrisbanes/photoview/sample/LauncherActivity.java
@@ -27,6 +27,8 @@
import android.view.ViewGroup;
import android.widget.TextView;
+import com.facebook.drawee.backends.pipeline.Fresco;
+
public class LauncherActivity extends AppCompatActivity {
public static final String[] options = {
@@ -35,13 +37,17 @@ public class LauncherActivity extends AppCompatActivity {
"Rotation Sample",
"Picasso Sample",
"Activity Transition Sample",
- "Immersive Sample"
+ "Immersive Sample",
+ "Fresco Sample"
};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_launcher);
+
+ Fresco.initialize(getApplicationContext());
+
Toolbar toolbar = findViewById(R.id.toolbar);
toolbar.setTitle(R.string.app_name);
RecyclerView recyclerView = findViewById(R.id.list);
@@ -78,6 +84,8 @@ public void onClick(View v) {
break;
case 5:
clazz = ImmersiveActivity.class;
+ case 6:
+ clazz = FrescoSampleActivity.class;
}
Context context = holder.itemView.getContext();
diff --git a/sample/src/main/java/com/github/chrisbanes/photoview/sample/fresco/DraweeViewAttacher.java b/sample/src/main/java/com/github/chrisbanes/photoview/sample/fresco/DraweeViewAttacher.java
new file mode 100644
index 00000000..9d36064d
--- /dev/null
+++ b/sample/src/main/java/com/github/chrisbanes/photoview/sample/fresco/DraweeViewAttacher.java
@@ -0,0 +1,32 @@
+package com.github.chrisbanes.photoview.sample.fresco;
+
+import android.graphics.Matrix;
+import android.graphics.RectF;
+
+import com.facebook.drawee.view.GenericDraweeView;
+import com.github.chrisbanes.photoview.PhotoViewAttacher;
+
+/*******************************************************************************
+ * Description: Extend PhotoViewAttacher to support Fresco.
+ *
+ * Author: Freeman
+ *
+ * Date: 2018/9/7
+ *******************************************************************************/
+public class DraweeViewAttacher extends PhotoViewAttacher {
+
+ private GenericDraweeView imageView;
+
+ public DraweeViewAttacher(GenericDraweeView image) {
+ super(image);
+ this.imageView = image;
+ }
+
+ @Override
+ protected RectF getDisplayRect(Matrix matrix) {
+ RectF displayRect = new RectF();
+ imageView.getHierarchy().getActualImageBounds(displayRect);
+ matrix.mapRect(displayRect);
+ return displayRect;
+ }
+}
diff --git a/sample/src/main/java/com/github/chrisbanes/photoview/sample/fresco/PhotoDraweeView.java b/sample/src/main/java/com/github/chrisbanes/photoview/sample/fresco/PhotoDraweeView.java
new file mode 100644
index 00000000..17ab6232
--- /dev/null
+++ b/sample/src/main/java/com/github/chrisbanes/photoview/sample/fresco/PhotoDraweeView.java
@@ -0,0 +1,269 @@
+package com.github.chrisbanes.photoview.sample.fresco;
+
+import android.content.Context;
+import android.graphics.Canvas;
+import android.graphics.Matrix;
+import android.graphics.RectF;
+import android.graphics.drawable.Drawable;
+import android.net.Uri;
+import android.util.AttributeSet;
+import android.view.GestureDetector;
+import android.view.View;
+import android.widget.ImageView;
+
+import com.facebook.drawee.drawable.ScalingUtils;
+import com.facebook.drawee.view.SimpleDraweeView;
+import com.github.chrisbanes.photoview.OnMatrixChangedListener;
+import com.github.chrisbanes.photoview.OnOutsidePhotoTapListener;
+import com.github.chrisbanes.photoview.OnPhotoTapListener;
+import com.github.chrisbanes.photoview.OnScaleChangedListener;
+import com.github.chrisbanes.photoview.OnSingleFlingListener;
+import com.github.chrisbanes.photoview.OnViewDragListener;
+import com.github.chrisbanes.photoview.OnViewTapListener;
+import com.github.chrisbanes.photoview.PhotoViewAttacher;
+
+/*******************************************************************************
+ * Description: Create PhotoDraweeView to support Fresco.
+ *
+ * Compare to PhotoView, just added onDraw and used PhotoViewAttacher.
+ *
+ * Author: Freeman
+ *
+ * Date: 2018/9/7
+ *******************************************************************************/
+public class PhotoDraweeView extends SimpleDraweeView {
+
+ private PhotoViewAttacher attacher;
+ private ImageView.ScaleType pendingScaleType;
+
+ public PhotoDraweeView(Context context) {
+ this(context, null);
+ }
+
+ public PhotoDraweeView(Context context, AttributeSet attr) {
+ this(context, attr, 0);
+ }
+
+ public PhotoDraweeView(Context context, AttributeSet attr, int defStyle) {
+ super(context, attr, defStyle);
+ init();
+ }
+
+ private void init() {
+ attacher = new DraweeViewAttacher(this);
+ getHierarchy().setActualImageScaleType(ScalingUtils.ScaleType.FIT_CENTER);
+ //We always pose as a Matrix scale type, though we can change to another scale type
+ //via the attacher
+ super.setScaleType(ImageView.ScaleType.MATRIX);
+ //apply the previously applied scale type
+ if (pendingScaleType != null) {
+ setScaleType(pendingScaleType);
+ pendingScaleType = null;
+ }
+ }
+
+ @Override
+ protected void onDraw(Canvas canvas) {
+ canvas.concat(attacher.getImageMatrix());
+ super.onDraw(canvas);
+ }
+
+ /**
+ * Get the current {@link PhotoViewAttacher} for this view. Be wary of holding on to references
+ * to this attacher, as it has a reference to this view, which, if a reference is held in the
+ * wrong place, can cause memory leaks.
+ *
+ * @return the attacher.
+ */
+ public PhotoViewAttacher getAttacher() {
+ return attacher;
+ }
+
+ @Override
+ public ImageView.ScaleType getScaleType() {
+ return attacher.getScaleType();
+ }
+
+ @Override
+ public Matrix getImageMatrix() {
+ return attacher.getImageMatrix();
+ }
+
+ @Override
+ public void setOnLongClickListener(View.OnLongClickListener l) {
+ attacher.setOnLongClickListener(l);
+ }
+
+ @Override
+ public void setOnClickListener(View.OnClickListener l) {
+ attacher.setOnClickListener(l);
+ }
+
+ @Override
+ public void setScaleType(ImageView.ScaleType scaleType) {
+ if (attacher == null) {
+ pendingScaleType = scaleType;
+ } else {
+ attacher.setScaleType(scaleType);
+ }
+ }
+
+ @Override
+ public void setImageDrawable(Drawable drawable) {
+ super.setImageDrawable(drawable);
+ // setImageBitmap calls through to this method
+ if (attacher != null) {
+ attacher.update();
+ }
+ }
+
+ @Override
+ public void setImageResource(int resId) {
+ super.setImageResource(resId);
+ if (attacher != null) {
+ attacher.update();
+ }
+ }
+
+ @Override
+ public void setImageURI(Uri uri) {
+ super.setImageURI(uri);
+ if (attacher != null) {
+ attacher.update();
+ }
+ }
+
+ @Override
+ protected boolean setFrame(int l, int t, int r, int b) {
+ boolean changed = super.setFrame(l, t, r, b);
+ if (changed) {
+ attacher.update();
+ }
+ return changed;
+ }
+
+ public void setRotationTo(float rotationDegree) {
+ attacher.setRotationTo(rotationDegree);
+ }
+
+ public void setRotationBy(float rotationDegree) {
+ attacher.setRotationBy(rotationDegree);
+ }
+
+ @Deprecated
+ public boolean isZoomEnabled() {
+ return attacher.isZoomEnabled();
+ }
+
+ public boolean isZoomable() {
+ return attacher.isZoomable();
+ }
+
+ public void setZoomable(boolean zoomable) {
+ attacher.setZoomable(zoomable);
+ }
+
+ public RectF getDisplayRect() {
+ return attacher.getDisplayRect();
+ }
+
+ public void getDisplayMatrix(Matrix matrix) {
+ attacher.getDisplayMatrix(matrix);
+ }
+
+ public boolean setDisplayMatrix(Matrix finalRectangle) {
+ return attacher.setDisplayMatrix(finalRectangle);
+ }
+
+ public void getSuppMatrix(Matrix matrix) {
+ attacher.getSuppMatrix(matrix);
+ }
+
+ public boolean setSuppMatrix(Matrix matrix) {
+ return attacher.setDisplayMatrix(matrix);
+ }
+
+ public float getMinimumScale() {
+ return attacher.getMinimumScale();
+ }
+
+ public float getMediumScale() {
+ return attacher.getMediumScale();
+ }
+
+ public float getMaximumScale() {
+ return attacher.getMaximumScale();
+ }
+
+ public float getScale() {
+ return attacher.getScale();
+ }
+
+ public void setAllowParentInterceptOnEdge(boolean allow) {
+ attacher.setAllowParentInterceptOnEdge(allow);
+ }
+
+ public void setMinimumScale(float minimumScale) {
+ attacher.setMinimumScale(minimumScale);
+ }
+
+ public void setMediumScale(float mediumScale) {
+ attacher.setMediumScale(mediumScale);
+ }
+
+ public void setMaximumScale(float maximumScale) {
+ attacher.setMaximumScale(maximumScale);
+ }
+
+ public void setScaleLevels(float minimumScale, float mediumScale, float maximumScale) {
+ attacher.setScaleLevels(minimumScale, mediumScale, maximumScale);
+ }
+
+ public void setOnMatrixChangeListener(OnMatrixChangedListener listener) {
+ attacher.setOnMatrixChangeListener(listener);
+ }
+
+ public void setOnPhotoTapListener(OnPhotoTapListener listener) {
+ attacher.setOnPhotoTapListener(listener);
+ }
+
+ public void setOnOutsidePhotoTapListener(OnOutsidePhotoTapListener listener) {
+ attacher.setOnOutsidePhotoTapListener(listener);
+ }
+
+ public void setOnViewTapListener(OnViewTapListener listener) {
+ attacher.setOnViewTapListener(listener);
+ }
+
+ public void setOnViewDragListener(OnViewDragListener listener) {
+ attacher.setOnViewDragListener(listener);
+ }
+
+ public void setScale(float scale) {
+ attacher.setScale(scale);
+ }
+
+ public void setScale(float scale, boolean animate) {
+ attacher.setScale(scale, animate);
+ }
+
+ public void setScale(float scale, float focalX, float focalY, boolean animate) {
+ attacher.setScale(scale, focalX, focalY, animate);
+ }
+
+ public void setZoomTransitionDuration(int milliseconds) {
+ attacher.setZoomTransitionDuration(milliseconds);
+ }
+
+ public void setOnDoubleTapListener(GestureDetector.OnDoubleTapListener onDoubleTapListener) {
+ attacher.setOnDoubleTapListener(onDoubleTapListener);
+ }
+
+ public void setOnScaleChangeListener(OnScaleChangedListener onScaleChangedListener) {
+ attacher.setOnScaleChangeListener(onScaleChangedListener);
+ }
+
+ public void setOnSingleFlingListener(OnSingleFlingListener onSingleFlingListener) {
+ attacher.setOnSingleFlingListener(onSingleFlingListener);
+ }
+}
diff --git a/sample/src/main/res/layout/activity_fresco_simple_sample.xml b/sample/src/main/res/layout/activity_fresco_simple_sample.xml
new file mode 100755
index 00000000..b6ce8310
--- /dev/null
+++ b/sample/src/main/res/layout/activity_fresco_simple_sample.xml
@@ -0,0 +1,33 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file