Use image picker to pick images for upload (#2278)

* Use image picker to pick images for upload

* Consolidate storage permissions in Upload activity

* With proper request codes for image upload

* Use constants for upload limits

* Check for request code while handling requests

* Let fragment initiate the camera/gallery instead of activity

* Delete unused external storage utils
This commit is contained in:
Vivek Maskara 2019-01-08 21:56:46 +05:30 committed by Josephine Lim
parent b05b302e65
commit 164ef9bcac
17 changed files with 339 additions and 637 deletions

View file

@ -1,46 +0,0 @@
package fr.free.nrw.commons.utils;
import android.Manifest;
import android.app.Activity;
import android.content.Context;
import android.content.pm.PackageManager;
import android.os.Build;
import android.support.v4.app.ActivityCompat;
import timber.log.Timber;
/**
* Created by root on 23.07.2018.
*/
public class ExternalStorageUtils {
/**
* Checks if external storage permission is granted
* @param context activity we are on
* @return true if permission is granted, false if not
*/
public static boolean isStoragePermissionGranted(Context context) {
if (Build.VERSION.SDK_INT >= 23) {
if (context.checkSelfPermission(android.Manifest.permission.WRITE_EXTERNAL_STORAGE) == PackageManager.PERMISSION_GRANTED) {
Timber.d("External storage permission granted, API >= 23");
return true;
} else {
Timber.d("External storage permission not granted, API >= 23");
return false;
}
} else { //permission is automatically granted on sdk<23 upon installation
Timber.d("External storage permission granted before, API < 23");
return true;
}
}
/**
* Requests external storage permission
* @param context activity we are on
*/
public static void requestExternalStoragePermission(Context context) {
Timber.d("External storage permission requested");
ActivityCompat.requestPermissions((Activity) context, new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE}, 1);
}
}

View file

@ -9,26 +9,6 @@ import timber.log.Timber;
public class FragmentUtils {
public static boolean addAndCommitFragmentWithImmediateExecution(
@NonNull FragmentManager fragmentManager,
@IdRes int containerViewId,
@NonNull Fragment fragment) {
if (fragment.isAdded()) {
Timber.w("Could not add fragment. The fragment is already added.");
return false;
}
try {
fragmentManager.beginTransaction()
.add(containerViewId, fragment)
.commitNow();
return true;
} catch (IllegalStateException e) {
Timber.e(e, "Could not add & commit fragment. "
+ "Did you mean to call commitAllowingStateLoss?");
}
return false;
}
/**
* Utility function to check whether the fragment UI is still active or not
* @param fragment

View file

@ -9,8 +9,8 @@ import android.graphics.Rect;
import android.net.Uri;
import android.support.annotation.IntDef;
import android.support.annotation.Nullable;
import android.util.Log;
import com.esafirm.imagepicker.model.Image;
import com.facebook.common.executors.CallerThreadExecutor;
import com.facebook.common.references.CloseableReference;
import com.facebook.datasource.DataSource;
@ -24,6 +24,8 @@ import com.facebook.imagepipeline.request.ImageRequestBuilder;
import java.io.IOException;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.util.ArrayList;
import java.util.List;
import fr.free.nrw.commons.R;
import fr.free.nrw.commons.location.LatLng;
@ -253,4 +255,15 @@ public class ImageUtils {
return errorMessage.toString();
}
public static ArrayList<Uri> getUriListFromImages(List<Image> imageList) {
ArrayList<Uri> uriList = new ArrayList<>();
for (Image imagePath : imageList) {
if (!StringUtils.isNullOrWhiteSpace(imagePath.getPath())) {
uriList.add(Uri.parse(imagePath.getPath()));
}
}
return uriList;
}
}

View file

@ -0,0 +1,41 @@
package fr.free.nrw.commons.utils;
import android.app.Activity;
import android.content.Intent;
import static fr.free.nrw.commons.contributions.ContributionController.BOOKMARK_CAMERA_UPLOAD_REQUEST_CODE;
import static fr.free.nrw.commons.contributions.ContributionController.BOOKMARK_GALLERY_UPLOAD_REQUEST_CODE;
import static fr.free.nrw.commons.contributions.ContributionController.CAMERA_UPLOAD_REQUEST_CODE;
import static fr.free.nrw.commons.contributions.ContributionController.GALLERY_UPLOAD_REQUEST_CODE;
import static fr.free.nrw.commons.contributions.ContributionController.NEARBY_CAMERA_UPLOAD_REQUEST_CODE;
import static fr.free.nrw.commons.contributions.ContributionController.NEARBY_GALLERY_UPLOAD_REQUEST_CODE;
public class IntentUtils {
/**
* Check if the intent should be handled by nearby list or map fragment
*/
public static boolean shouldNearbyHandle(int requestCode, int resultCode, Intent data) {
return resultCode == Activity.RESULT_OK
&& (requestCode == NEARBY_CAMERA_UPLOAD_REQUEST_CODE || requestCode == NEARBY_GALLERY_UPLOAD_REQUEST_CODE)
&& data != null;
}
/**
* Check if the intent should be handled by contributions list fragment
*/
public static boolean shouldContributionsListHandle(int requestCode, int resultCode, Intent data) {
return resultCode == Activity.RESULT_OK
&& (requestCode == GALLERY_UPLOAD_REQUEST_CODE || requestCode == CAMERA_UPLOAD_REQUEST_CODE)
&& data != null;
}
/**
* Check if the intent should be handled by contributions list fragment
*/
public static boolean shouldBookmarksHandle(int requestCode, int resultCode, Intent data) {
return resultCode == Activity.RESULT_OK
&& (requestCode == BOOKMARK_CAMERA_UPLOAD_REQUEST_CODE || requestCode == BOOKMARK_GALLERY_UPLOAD_REQUEST_CODE)
&& data != null;
}
}

View file

@ -5,9 +5,18 @@ import android.content.Intent;
import android.content.pm.PackageManager;
import android.net.Uri;
import android.provider.Settings;
import android.support.annotation.StringRes;
import android.support.v4.content.ContextCompat;
import com.karumi.dexter.Dexter;
import com.karumi.dexter.PermissionToken;
import com.karumi.dexter.listener.PermissionDeniedResponse;
import com.karumi.dexter.listener.PermissionGrantedResponse;
import com.karumi.dexter.listener.PermissionRequest;
import com.karumi.dexter.listener.single.BasePermissionListener;
import fr.free.nrw.commons.CommonsApplication;
import fr.free.nrw.commons.R;
public class PermissionUtils {
@ -17,8 +26,7 @@ public class PermissionUtils {
It open the app settings from where the user can manually give us the required permission.
* @param activity
*/
public static void askUserToManuallyEnablePermissionFromSettings(
Activity activity) {
public static void askUserToManuallyEnablePermissionFromSettings(Activity activity) {
Intent intent = new Intent(Settings.ACTION_APPLICATION_DETAILS_SETTINGS);
Uri uri = Uri.fromParts("package", activity.getPackageName(), null);
intent.setData(uri);
@ -36,4 +44,62 @@ public class PermissionUtils {
return ContextCompat.checkSelfPermission(activity, permission) == PackageManager.PERMISSION_GRANTED;
}
/**
* Checks for a particular permission and runs the runnable to perform an action when the permission is granted
* Also, it shows a rationale if needed
*
* Sample usage:
*
* PermissionUtils.checkPermissionsAndPerformAction(activity,
* Manifest.permission.WRITE_EXTERNAL_STORAGE,
* () -> initiateCameraUpload(activity),
* R.string.storage_permission_title,
* R.string.write_storage_permission_rationale);
*
*
* @param activity activity requesting permissions
* @param permission the permission being requests
* @param onPermissionGranted the runnable to be executed when the permission is granted
* @param rationaleTitle rationale title to be displayed when permission was denied
* @param rationaleMessage rationale message to be displayed when permission was denied
*/
public static void checkPermissionsAndPerformAction(Activity activity,
String permission,
Runnable onPermissionGranted,
@StringRes int rationaleTitle,
@StringRes int rationaleMessage) {
Dexter.withActivity(activity)
.withPermission(permission)
.withListener(new BasePermissionListener() {
@Override
public void onPermissionGranted(PermissionGrantedResponse response) {
onPermissionGranted.run();
}
@Override
public void onPermissionDenied(PermissionDeniedResponse response) {
if (response.isPermanentlyDenied()) {
DialogUtil.showAlertDialog(activity,
activity.getString(rationaleTitle),
activity.getString(rationaleMessage),
activity.getString(R.string.navigation_item_settings),
null,
() -> askUserToManuallyEnablePermissionFromSettings(activity),
null);
}
}
@Override
public void onPermissionRationaleShouldBeShown(PermissionRequest permission, PermissionToken token) {
DialogUtil.showAlertDialog(activity,
activity.getString(rationaleTitle),
activity.getString(rationaleMessage),
activity.getString(android.R.string.ok),
activity.getString(android.R.string.cancel),
token::continuePermissionRequest,
token::cancelPermissionRequest);
}
}).check();
}
}