Skip to content

Commit 892f2b9

Browse files
committed
v1.0.0
1 parent 7096898 commit 892f2b9

32 files changed

+903
-1
lines changed

.gitignore

+8
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
**.iml
2+
.idea
3+
.gradle
4+
/local.properties
5+
bintray.properties
6+
.DS_Store
7+
**/build
8+
/captures

FrescoBigImageViewer/.gitignore

+1
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
/build

FrescoBigImageViewer/build.gradle

+28
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
apply plugin: 'com.android.library'
2+
apply from: "https://raw.githubusercontent.com/Piasy/BintrayUploadScript/master/bintray.gradle"
3+
4+
android {
5+
compileSdkVersion rootProject.ext.androidCompileSdkVersion
6+
buildToolsVersion rootProject.ext.androidBuildToolsVersion
7+
8+
defaultConfig {
9+
minSdkVersion rootProject.ext.minSdkVersion
10+
targetSdkVersion rootProject.ext.targetSdkVersion
11+
versionCode rootProject.ext.releaseVersionCode
12+
versionName rootProject.ext.releaseVersionName
13+
}
14+
buildTypes {
15+
release {
16+
minifyEnabled false
17+
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
18+
}
19+
}
20+
}
21+
22+
dependencies {
23+
compile "com.android.support:support-annotations:$rootProject.ext.androidSupportSdkVersion"
24+
25+
compile "com.facebook.fresco:fresco:$rootProject.ext.frescoVersion"
26+
compile "com.davemorrissey.labs:subsampling-scale-image-view:$rootProject.ext.ssivVersion"
27+
compile "commons-io:commons-io:$rootProject.ext.commonsVersion"
28+
}
+17
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
# Add project specific ProGuard rules here.
2+
# By default, the flags in this file are appended to flags specified
3+
# in /Users/piasy/tools/android-sdk/tools/proguard/proguard-android.txt
4+
# You can edit the include path and order by changing the proguardFiles
5+
# directive in build.gradle.
6+
#
7+
# For more details, see
8+
# http://developer.android.com/guide/developing/tools/proguard.html
9+
10+
# Add any project specific keep options here:
11+
12+
# If your project uses WebView with JS, uncomment the following
13+
# and specify the fully qualified class name to the JavaScript interface
14+
# class:
15+
#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
16+
# public *;
17+
#}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
2+
package="com.github.piasy.fresco.bigimageviewer">
3+
4+
<uses-permission android:name="android.permission.INTERNET"/>
5+
6+
</manifest>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,165 @@
1+
/*
2+
* The MIT License (MIT)
3+
*
4+
* Copyright (c) 2016 Piasy
5+
*
6+
* Permission is hereby granted, free of charge, to any person obtaining a copy
7+
* of this software and associated documentation files (the "Software"), to deal
8+
* in the Software without restriction, including without limitation the rights
9+
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10+
* copies of the Software, and to permit persons to whom the Software is
11+
* furnished to do so, subject to the following conditions:
12+
*
13+
* The above copyright notice and this permission notice shall be included in all
14+
* copies or substantial portions of the Software.
15+
*
16+
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17+
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18+
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19+
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20+
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21+
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
22+
* SOFTWARE.
23+
*/
24+
25+
package com.github.piasy.fresco.bigimageviewer;
26+
27+
import android.content.Context;
28+
import android.net.Uri;
29+
import android.support.annotation.UiThread;
30+
import android.support.annotation.WorkerThread;
31+
import android.util.AttributeSet;
32+
import android.util.Log;
33+
import android.view.ViewGroup;
34+
import android.widget.FrameLayout;
35+
import com.davemorrissey.labs.subscaleview.ImageSource;
36+
import com.davemorrissey.labs.subscaleview.SubsamplingScaleImageView;
37+
import com.facebook.binaryresource.FileBinaryResource;
38+
import com.facebook.cache.common.CacheKey;
39+
import com.facebook.cache.disk.FileCache;
40+
import com.facebook.common.references.CloseableReference;
41+
import com.facebook.datasource.DataSource;
42+
import com.facebook.drawee.backends.pipeline.Fresco;
43+
import com.facebook.imagepipeline.cache.DefaultCacheKeyFactory;
44+
import com.facebook.imagepipeline.core.DefaultExecutorSupplier;
45+
import com.facebook.imagepipeline.core.ImagePipeline;
46+
import com.facebook.imagepipeline.core.ImagePipelineFactory;
47+
import com.facebook.imagepipeline.memory.PooledByteBuffer;
48+
import com.facebook.imagepipeline.request.ImageRequest;
49+
import java.io.File;
50+
import java.util.ArrayList;
51+
import java.util.List;
52+
53+
/**
54+
* Created by Piasy{github.com/Piasy} on 06/11/2016.
55+
*/
56+
57+
public class BigImageView extends FrameLayout {
58+
private final SubsamplingScaleImageView mImageView;
59+
60+
private final DefaultExecutorSupplier mExecutorSupplier;
61+
62+
private final List<DataSource<CloseableReference<PooledByteBuffer>>> mDownloadingImages;
63+
private final List<File> mTempImages;
64+
65+
public BigImageView(Context context) {
66+
this(context, null);
67+
}
68+
69+
public BigImageView(Context context, AttributeSet attrs) {
70+
this(context, attrs, 0);
71+
}
72+
73+
public BigImageView(Context context, AttributeSet attrs, int defStyleAttr) {
74+
super(context, attrs, defStyleAttr);
75+
76+
mImageView = new SubsamplingScaleImageView(context, attrs);
77+
addView(mImageView);
78+
LayoutParams params = new LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT,
79+
ViewGroup.LayoutParams.MATCH_PARENT);
80+
mImageView.setLayoutParams(params);
81+
mImageView.setMinimumTileDpi(160);
82+
83+
mExecutorSupplier = new DefaultExecutorSupplier(Runtime.getRuntime().availableProcessors());
84+
mDownloadingImages = new ArrayList<>();
85+
mTempImages = new ArrayList<>();
86+
}
87+
88+
@Override
89+
protected void onDetachedFromWindow() {
90+
super.onDetachedFromWindow();
91+
92+
for (int i = 0, size = mDownloadingImages.size(); i < size; i++) {
93+
mDownloadingImages.get(i).close();
94+
}
95+
mDownloadingImages.clear();
96+
for (int i = 0, size = mTempImages.size(); i < size; i++) {
97+
mTempImages.get(i).delete();
98+
}
99+
mTempImages.clear();
100+
}
101+
102+
public void showImage(Uri uri) {
103+
Log.d("FrescoBigImageViewer", "showImage " + uri);
104+
105+
ImageRequest request = ImageRequest.fromUri(uri);
106+
107+
File localCache = getCacheFile(request);
108+
if (localCache.exists()) {
109+
showCachedImage(localCache);
110+
} else {
111+
ImagePipeline pipeline = Fresco.getImagePipeline();
112+
DataSource<CloseableReference<PooledByteBuffer>> source =
113+
pipeline.fetchEncodedImage(request, true);
114+
mDownloadingImages.add(source);
115+
source.subscribe(new ImageDownloadSubscriber(getContext()) {
116+
@Override
117+
protected void onSuccess(File image) {
118+
mTempImages.add(image);
119+
showDownloadedImage(image);
120+
}
121+
122+
@Override
123+
protected void onFail(Throwable t) {
124+
t.printStackTrace();
125+
}
126+
}, mExecutorSupplier.forBackgroundTasks());
127+
}
128+
}
129+
130+
private File getCacheFile(final ImageRequest request) {
131+
FileCache mainFileCache = ImagePipelineFactory
132+
.getInstance()
133+
.getMainFileCache();
134+
final CacheKey cacheKey = DefaultCacheKeyFactory
135+
.getInstance()
136+
.getEncodedCacheKey(request, false); // we don't need context, but avoid null
137+
File cacheFile = request.getSourceFile();
138+
if (mainFileCache.hasKey(cacheKey)) {
139+
cacheFile = ((FileBinaryResource) mainFileCache.getResource(cacheKey)).getFile();
140+
}
141+
return cacheFile;
142+
}
143+
144+
@WorkerThread
145+
private void showDownloadedImage(final File image) {
146+
Log.d("FrescoBigImageViewer", "showDownloadedImage " + image);
147+
post(new Runnable() {
148+
@Override
149+
public void run() {
150+
doShowImage(image);
151+
}
152+
});
153+
}
154+
155+
@UiThread
156+
private void showCachedImage(File image) {
157+
Log.d("FrescoBigImageViewer", "showCachedImage " + image);
158+
doShowImage(image);
159+
}
160+
161+
@UiThread
162+
private void doShowImage(File image) {
163+
mImageView.setImage(ImageSource.uri(Uri.fromFile(image)));
164+
}
165+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
package com.github.piasy.fresco.bigimageviewer;
2+
3+
import android.content.Context;
4+
import android.net.Uri;
5+
import android.support.annotation.Nullable;
6+
import com.facebook.drawee.backends.pipeline.DraweeConfig;
7+
import com.facebook.drawee.backends.pipeline.Fresco;
8+
import com.facebook.imagepipeline.core.ImagePipeline;
9+
import com.facebook.imagepipeline.core.ImagePipelineConfig;
10+
import com.facebook.imagepipeline.request.ImageRequest;
11+
12+
/**
13+
* Created by Piasy{github.com/Piasy} on 06/11/2016.
14+
*/
15+
16+
public final class FrescoBigImageViewer {
17+
private FrescoBigImageViewer() {
18+
// no instance
19+
}
20+
21+
public static void initialize(Context context) {
22+
initialize(context, null, null);
23+
}
24+
25+
public static void initialize(Context context,
26+
@Nullable ImagePipelineConfig imagePipelineConfig) {
27+
initialize(context, imagePipelineConfig, null);
28+
}
29+
30+
public static void initialize(Context context,
31+
@Nullable ImagePipelineConfig imagePipelineConfig,
32+
@Nullable DraweeConfig draweeConfig) {
33+
Fresco.initialize(context, imagePipelineConfig, draweeConfig);
34+
}
35+
36+
public static void prefetch(Uri... uris) {
37+
if (uris == null) {
38+
return;
39+
}
40+
41+
ImagePipeline pipeline = Fresco.getImagePipeline();
42+
for (Uri uri : uris) {
43+
pipeline.prefetchToDiskCache(ImageRequest.fromUri(uri),
44+
false); // we don't need context, but avoid null
45+
}
46+
}
47+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,83 @@
1+
/*
2+
* The MIT License (MIT)
3+
*
4+
* Copyright (c) 2016 Piasy
5+
*
6+
* Permission is hereby granted, free of charge, to any person obtaining a copy
7+
* of this software and associated documentation files (the "Software"), to deal
8+
* in the Software without restriction, including without limitation the rights
9+
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10+
* copies of the Software, and to permit persons to whom the Software is
11+
* furnished to do so, subject to the following conditions:
12+
*
13+
* The above copyright notice and this permission notice shall be included in all
14+
* copies or substantial portions of the Software.
15+
*
16+
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17+
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18+
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19+
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20+
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21+
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
22+
* SOFTWARE.
23+
*/
24+
25+
package com.github.piasy.fresco.bigimageviewer;
26+
27+
import android.content.Context;
28+
import android.support.annotation.WorkerThread;
29+
import com.facebook.common.references.CloseableReference;
30+
import com.facebook.datasource.BaseDataSubscriber;
31+
import com.facebook.datasource.DataSource;
32+
import com.facebook.imagepipeline.memory.PooledByteBuffer;
33+
import com.facebook.imagepipeline.memory.PooledByteBufferInputStream;
34+
import java.io.File;
35+
import java.io.FileOutputStream;
36+
import java.io.IOException;
37+
import org.apache.commons.io.IOUtils;
38+
39+
/**
40+
* Created by Piasy{github.com/Piasy} on 06/11/2016.
41+
*/
42+
43+
public abstract class ImageDownloadSubscriber
44+
extends BaseDataSubscriber<CloseableReference<PooledByteBuffer>> {
45+
private final File mTempFile;
46+
47+
public ImageDownloadSubscriber(Context context) {
48+
mTempFile = new File(context.getCacheDir(), "" + System.currentTimeMillis() + ".png");
49+
}
50+
51+
@Override
52+
protected void onNewResultImpl(DataSource<CloseableReference<PooledByteBuffer>> dataSource) {
53+
if (!dataSource.isFinished() || dataSource.getResult() == null) {
54+
return;
55+
}
56+
57+
PooledByteBufferInputStream inputStream = null;
58+
FileOutputStream outputStream = null;
59+
try {
60+
inputStream = new PooledByteBufferInputStream(dataSource.getResult().get());
61+
outputStream = new FileOutputStream(mTempFile);
62+
IOUtils.copy(inputStream, outputStream);
63+
64+
onSuccess(mTempFile);
65+
} catch (IOException e) {
66+
onFail(e);
67+
} finally {
68+
IOUtils.closeQuietly(inputStream);
69+
IOUtils.closeQuietly(outputStream);
70+
}
71+
}
72+
73+
@Override
74+
protected void onFailureImpl(DataSource<CloseableReference<PooledByteBuffer>> dataSource) {
75+
onFail(new RuntimeException("onFailureImpl"));
76+
}
77+
78+
@WorkerThread
79+
protected abstract void onSuccess(File image);
80+
81+
@WorkerThread
82+
protected abstract void onFail(Throwable t);
83+
}

0 commit comments

Comments
 (0)