diff --git a/README.md b/README.md
index 628189f16..59d330b48 100644
--- a/README.md
+++ b/README.md
@@ -18,7 +18,7 @@
```
allprojects {
repositories {
- jcenter()
+ ...
maven { url "https://jitpack.io" }
}
}
diff --git a/build.gradle b/build.gradle
index cbd5640a7..9bb4e6090 100644
--- a/build.gradle
+++ b/build.gradle
@@ -1,9 +1,9 @@
buildscript {
ext {
- androidx_appcompat_version = "1.1.0"
+ androidx_appcompat_version = "1.3.0"
androidx_core_version = "1.1.0"
- androidx_exifinterface_version = "1.1.0-beta01"
- androidx_transition_version = "1.2.0-rc01"
+ androidx_exifinterface_version = "1.3.2"
+ androidx_transition_version = "1.4.1"
constraintlayout_version = "1.1.3"
}
diff --git a/sample/src/main/java/com/yalantis/ucrop/sample/ResultActivity.java b/sample/src/main/java/com/yalantis/ucrop/sample/ResultActivity.java
index 75228cbf2..55fb1f832 100755
--- a/sample/src/main/java/com/yalantis/ucrop/sample/ResultActivity.java
+++ b/sample/src/main/java/com/yalantis/ucrop/sample/ResultActivity.java
@@ -22,6 +22,14 @@
import android.widget.TextView;
import android.widget.Toast;
+import androidx.annotation.NonNull;
+import androidx.appcompat.app.ActionBar;
+import androidx.appcompat.widget.Toolbar;
+import androidx.core.app.ActivityCompat;
+import androidx.core.app.NotificationCompat;
+import androidx.core.content.FileProvider;
+
+import com.yalantis.ucrop.util.BitmapLoadUtils;
import com.yalantis.ucrop.view.UCropView;
import java.io.File;
@@ -34,13 +42,6 @@
import java.util.Calendar;
import java.util.List;
-import androidx.annotation.NonNull;
-import androidx.appcompat.app.ActionBar;
-import androidx.appcompat.widget.Toolbar;
-import androidx.core.app.ActivityCompat;
-import androidx.core.app.NotificationCompat;
-import androidx.core.content.FileProvider;
-
import static android.content.Intent.FLAG_GRANT_READ_URI_PERMISSION;
import static android.content.Intent.FLAG_GRANT_WRITE_URI_PERMISSION;
@@ -167,6 +168,9 @@ private void saveCroppedImage() {
Toast.makeText(ResultActivity.this, e.getMessage(), Toast.LENGTH_SHORT).show();
Log.e(TAG, imageUri.toString(), e);
}
+ } else if (BitmapLoadUtils.hasContentScheme(imageUri)){
+ Toast.makeText(ResultActivity.this, getString(R.string.toast_already_saved), Toast.LENGTH_SHORT).show();
+ finish();
} else {
Toast.makeText(ResultActivity.this, getString(R.string.toast_unexpected_error), Toast.LENGTH_SHORT).show();
}
diff --git a/sample/src/main/res/values/strings.xml b/sample/src/main/res/values/strings.xml
index 5b23bf711..0b6ceeed0 100644
--- a/sample/src/main/res/values/strings.xml
+++ b/sample/src/main/res/values/strings.xml
@@ -42,6 +42,7 @@
Cannot retrieve selected image
Cannot retrieve cropped image
Unexpected error
+ Your image is already saved
com.yalantis.ucrop.provider
ucrop_chanel
diff --git a/ucrop/src/main/java/com/yalantis/ucrop/task/BitmapCropTask.java b/ucrop/src/main/java/com/yalantis/ucrop/task/BitmapCropTask.java
index ff0ca2e94..c2f34d511 100644
--- a/ucrop/src/main/java/com/yalantis/ucrop/task/BitmapCropTask.java
+++ b/ucrop/src/main/java/com/yalantis/ucrop/task/BitmapCropTask.java
@@ -164,27 +164,7 @@ private boolean crop() throws IOException {
if (shouldCrop) {
saveImage(Bitmap.createBitmap(mViewBitmap, cropOffsetX, cropOffsetY, mCroppedImageWidth, mCroppedImageHeight));
if (mCompressFormat.equals(Bitmap.CompressFormat.JPEG)) {
- boolean hasImageInputUriContentSchema = hasContentScheme(mImageInputUri);
- boolean hasImageOutputUriContentSchema = hasContentScheme(mImageOutputUri);
- if (hasImageInputUriContentSchema && hasImageOutputUriContentSchema) {
- if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
- ImageHeaderParser.copyExif(context, mCroppedImageWidth, mCroppedImageHeight, mImageInputUri, mImageOutputUri);
- } else {
- Log.e(TAG, "It is not possible to write exif info into file represented by \"content\" Uri if Android < LOLLIPOP");
- }
- } else if (hasImageInputUriContentSchema) {
- ImageHeaderParser.copyExif(context, mCroppedImageWidth, mCroppedImageHeight, mImageInputUri, mImageOutputPath);
- } else if (hasImageOutputUriContentSchema) {
- if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
- ExifInterface originalExif = new ExifInterface(mImageInputPath);
- ImageHeaderParser.copyExif(context, originalExif, mCroppedImageWidth, mCroppedImageHeight, mImageOutputUri);
- } else {
- Log.e(TAG, "It is not possible to write exif info into file represented by \"content\" Uri if Android < LOLLIPOP");
- }
- } else {
- ExifInterface originalExif = new ExifInterface(mImageInputPath);
- ImageHeaderParser.copyExif(originalExif, mCroppedImageWidth, mCroppedImageHeight, mImageOutputPath);
- }
+ copyExifForOutputFile(context);
}
return true;
} else {
@@ -193,8 +173,35 @@ private boolean crop() throws IOException {
}
}
- private boolean hasContentScheme(Uri uri) {
- return uri != null && CONTENT_SCHEME.equals(uri.getScheme());
+ private void copyExifForOutputFile(Context context) throws IOException {
+ boolean hasImageInputUriContentSchema = BitmapLoadUtils.hasContentScheme(mImageInputUri);
+ boolean hasImageOutputUriContentSchema = BitmapLoadUtils.hasContentScheme(mImageOutputUri);
+ /*
+ * ImageHeaderParser.copyExif with output uri as a parameter
+ * uses ExifInterface constructor with FileDescriptor param for overriding output file exif info,
+ * which doesn't support ExitInterface.saveAttributes call for SDK lower than 21.
+ *
+ * See documentation for ImageHeaderParser.copyExif and ExifInterface.saveAttributes implementation.
+ */
+ if (hasImageInputUriContentSchema && hasImageOutputUriContentSchema) {
+ if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
+ ImageHeaderParser.copyExif(context, mCroppedImageWidth, mCroppedImageHeight, mImageInputUri, mImageOutputUri);
+ } else {
+ Log.e(TAG, "It is not possible to write exif info into file represented by \"content\" Uri if Android < LOLLIPOP");
+ }
+ } else if (hasImageInputUriContentSchema) {
+ ImageHeaderParser.copyExif(context, mCroppedImageWidth, mCroppedImageHeight, mImageInputUri, mImageOutputPath);
+ } else if (hasImageOutputUriContentSchema) {
+ if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
+ ExifInterface originalExif = new ExifInterface(mImageInputPath);
+ ImageHeaderParser.copyExif(context, originalExif, mCroppedImageWidth, mCroppedImageHeight, mImageOutputUri);
+ } else {
+ Log.e(TAG, "It is not possible to write exif info into file represented by \"content\" Uri if Android < LOLLIPOP");
+ }
+ } else {
+ ExifInterface originalExif = new ExifInterface(mImageInputPath);
+ ImageHeaderParser.copyExif(originalExif, mCroppedImageWidth, mCroppedImageHeight, mImageOutputPath);
+ }
}
private void saveImage(@NonNull Bitmap croppedBitmap) {
@@ -244,7 +251,7 @@ protected void onPostExecute(@Nullable Throwable t) {
if (t == null) {
Uri uri;
- if (hasContentScheme(mImageOutputUri)) {
+ if (BitmapLoadUtils.hasContentScheme(mImageOutputUri)) {
uri = mImageOutputUri;
} else {
uri = Uri.fromFile(new File(mImageOutputPath));
diff --git a/ucrop/src/main/java/com/yalantis/ucrop/util/BitmapLoadUtils.java b/ucrop/src/main/java/com/yalantis/ucrop/util/BitmapLoadUtils.java
index 467ad43a4..136bc145a 100755
--- a/ucrop/src/main/java/com/yalantis/ucrop/util/BitmapLoadUtils.java
+++ b/ucrop/src/main/java/com/yalantis/ucrop/util/BitmapLoadUtils.java
@@ -12,6 +12,10 @@
import android.view.Display;
import android.view.WindowManager;
+import androidx.annotation.NonNull;
+import androidx.annotation.Nullable;
+import androidx.exifinterface.media.ExifInterface;
+
import com.yalantis.ucrop.callback.BitmapLoadCallback;
import com.yalantis.ucrop.task.BitmapLoadTask;
@@ -19,15 +23,13 @@
import java.io.IOException;
import java.io.InputStream;
-import androidx.annotation.NonNull;
-import androidx.annotation.Nullable;
-import androidx.exifinterface.media.ExifInterface;
-
/**
* Created by Oleksii Shliama (https://github.com/shliama).
*/
public class BitmapLoadUtils {
+ private static final String CONTENT_SCHEME = "content";
+
private static final String TAG = "BitmapLoadUtils";
public static void decodeBitmapInBackground(@NonNull Context context,
@@ -171,4 +173,8 @@ public static void close(@Nullable Closeable c) {
}
}
+ public static boolean hasContentScheme(Uri uri) {
+ return uri != null && CONTENT_SCHEME.equals(uri.getScheme());
+ }
+
}
\ No newline at end of file