Android M Camera Intent + permission bug?
I had the same issue and find this doc from google:
https://developer.android.com/reference/android/provider/MediaStore.html#ACTION_IMAGE_CAPTURE
"Note: if you app targets M and above and declares as using the CAMERA permission which is not granted, then atempting to use this action will result in a SecurityException."
This is really weird.
Don't make sense at all.
The app declares Camera permission using intent with action IMAGE_CAPTURE just run into SecurityException. But if your app doesn't declare Camera permission using intent with action IMAGE_CAPTURE can launch Camera app without issue.
The workaround would be check is the app has camera permission included in the manifest, if it's , request camera permission before launching intent.
Here is the way to check if the permission is included in the manifest, doesn't matter the permission is granted or not.
public boolean hasPermissionInManifest(Context context, String permissionName) {
final String packageName = context.getPackageName();
try {
final PackageInfo packageInfo = context.getPackageManager()
.getPackageInfo(packageName, PackageManager.GET_PERMISSIONS);
final String[] declaredPermisisons = packageInfo.requestedPermissions;
if (declaredPermisisons != null && declaredPermisisons.length > 0) {
for (String p : declaredPermisisons) {
if (p.equals(permissionName)) {
return true;
}
}
}
} catch (NameNotFoundException e) {
}
return false;
}
Android: Permission Error on Capture using Camera
If camera n external storage both are required for your app you should ||
them in if condition.
if (ActivityCompat.checkSelfPermission(activity, Manifest.permission.CAMERA) != PackageManager.PERMISSION_GRANTED || ActivityCompat.checkSelfPermission(activity, Manifest.permission.WRITE_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) {
ActivityCompat.requestPermissions(activity, new String[]{Manifest.permission.CAMERA, Manifest.permission.WRITE_EXTERNAL_STORAGE}, Constants.CAMERA_CAPTURE_PERMISSIONS_REQUEST_CODE);
} else {
Intent camera = new Intent(android.provider.MediaStore.ACTION_IMAGE_CAPTURE);
activity.startActivityForResult(camera, Constants.IMAGE_CAPTURE_CAMERA);
}
Camera intent permission, android, Why this do not work?
So, i think problem is in android permission.
CODE works well under or equal android 5.xx
But do not works on over or equal android 6.xx
For this you have to add Runtime Permission for Android 6.0 and up.
Example.
final private int REQUEST_CODE_ASK_PERMISSIONS_CAMERA = 100;
final private int REQUEST_CODE_ASK_PERMISSIONS_EXTERNAL_STORAGE = 200;
// For Check Camera Permission
if (Build.VERSION.SDK_INT >= 23) {
int hasPermission = ContextCompat.checkSelfPermission(getActivity(), Manifest.permission.CAMERA);
if (hasPermission != PackageManager.PERMISSION_GRANTED) {
if (shouldShowRequestPermissionRationale(Manifest.permission.CAMERA)) {
// Display UI and wait for user interaction
getErrorDialog("You need to allow Camera permission." +
"\nIf you disable this permission, You will not able to add attachment.", getActivity(), true).show();
} else {
requestPermissions(new String[]{Manifest.permission.CAMERA}, REQUEST_CODE_ASK_PERMISSIONS_CAMERA);
}
return;
}
}
// For Check Read External Permission.
if (Build.VERSION.SDK_INT >= 23) {
int hasPermission = ContextCompat.checkSelfPermission(getActivity(), Manifest.permission.READ_EXTERNAL_STORAGE);
if (hasPermission != PackageManager.PERMISSION_GRANTED) {
if (shouldShowRequestPermissionRationale(Manifest.permission.READ_EXTERNAL_STORAGE)) {
// Display UI and wait for user interaction
getErrorDialog("You need to allow Read External Storage permission." +
"\nIf you disable this permission, You will not able to add attachment.", getActivity(), false).show();
} else {
requestPermissions(new String[]{Manifest.permission.READ_EXTERNAL_STORAGE}, REQUEST_CODE_ASK_PERMISSIONS_EXTERNAL_STORAGE);
}
return;
}
}
@Override
public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
switch (requestCode) {
case REQUEST_CODE_ASK_PERMISSIONS_CAMERA:
if (grantResults[0] == PackageManager.PERMISSION_GRANTED) {
// Permission Granted
Toast.makeText(getActivity(), "Permission Grant", Toast.LENGTH_SHORT).show();
Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss").format(new Date());
String imageFileName = "JPEG_" + timeStamp + ".jpg";
File imageStorageDir = new File(Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DCIM), imageFileName);
uri = Uri.fromFile(imageStorageDir);
intent.putExtra(MediaStore.EXTRA_OUTPUT, uri);
startActivityForResult(intent, 1);
} else {
// Permission Denied
Toast.makeText(getActivity(), "Required permission is disable.", Toast.LENGTH_SHORT).show();
}
break;
case REQUEST_CODE_ASK_PERMISSIONS_EXTERNAL_STORAGE:
if (grantResults[0] == PackageManager.PERMISSION_GRANTED) {
// Permission Granted
Toast.makeText(getActivity(), "Permission Grant", Toast.LENGTH_SHORT).show();
Intent intent = new Intent(Intent.ACTION_PICK, android.provider.MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
intent.setType("image/*");
startActivityForResult(intent, 2);
} else {
// Permission Denied
Toast.makeText(getActivity(), "Required permission is disable.", Toast.LENGTH_SHORT).show();
}
break;
default:
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
}
}
public AlertDialog.Builder getErrorDialog(String message, Context context, final boolean isFromCamera) {
final AlertDialog.Builder alertDialog = new AlertDialog.Builder(context);
alertDialog.setTitle(getString(R.string.app_name)).setMessage(message);
alertDialog.setPositiveButton("Ok", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
dialog.dismiss();
if (Build.VERSION.SDK_INT >= 23) {
if(isFromCamera){
requestPermissions(new String[]{Manifest.permission.CAMERA},
REQUEST_CODE_ASK_PERMISSIONS_CAMERA);
}else {
requestPermissions(new String[]{Manifest.permission.READ_EXTERNAL_STORAGE},
REQUEST_CODE_ASK_PERMISSIONS_EXTERNAL_STORAGE);
}
}
}
});
return alertDialog;
}
Camera permissions are not requested but are still working
The reason this works is that your app is not getting access to any of:
- The camera itself
- The user's internal/external storage
- The user's existing photos
All you're getting is the opportunity to ask the user to take a photo and return that photo to you. Because the user needs to affirmatively consent as part of the process, no permission is required.
This model also has the benefit of allowing apps to capture photos even if the user would not entrust them with camera or storage permissions. They can rest assured that the app only got access to the single photo that the user took. The same principle applies when asking the user to select a photo as well.
Android: Permission Denial: starting Intent with revoked permission android.permission.CAMERA
Remove this permission
<uses-permission android:name="android.permission.CAMERA"/>
I faced this error executing my app in android 7. After tests I noticed user permission wasn't in project A but it was in project B, that I only tested in android 5 devices. So I remove that permission in project B in order to run it on other device that targets android 7 and it finally could open.
In adittion I added the fileprovider code that Android suggests here https://developer.android.com/training/camera/photobasics.html
Hope this helps.
Camera Intent not working with multiple camera apps
The problem was that in manifest I have option: android:launchMode="singleInstance"
for my activity.
<activity
android:name="MyActivity"
android:launchMode="singleInstance"
>
For solving above issue you should remove singleInstance
option from manifest file (or replace it within singleTask
option).
This is resolve the issue and onActivityResult
is properly working.
revoked permission android.permission.CAMERA
Here's how I solved this problem.
Contrary to what most answers say, REMOVE this from your Manifest file.
<uses-permission android:name="android.permission.CAMERA"/>
Why?
Starting Android M (API 23), if your app has CAMERA permission declared in the manifest, then, it needs that CAMERA permission to be GRANTED in order to access ACTION_IMAGE_CAPTURE
etc... too (which normally do not require the CAMERA permission on their own). If not, then it automatically raises a SecurityException.
╔═════════════════════════════════════════════════╦════════════════════╗
║ Usage ║ Permissions needed ║
╠═════════════════════════════════════════════════╬════════════════════╣
║ ACTION_IMAGE_CAPTURE ║ none ║
║ ACTION_VIDEO_CAPTURE ║ none ║
║ INTENT_ACTION_STILL_IMAGE_CAMERA ║ none ║
║ android.hardware.camera2 ║ CAMERA ║
║ android.hardware.camera2 + ACTION_IMAGE_CAPTURE ║ CAMERA ║
║ android.hardware.camera2 + ACTION_VIDEO_CAPTURE ║ CAMERA ║
║ ... ║ ... ║
╚═════════════════════════════════════════════════╩════════════════════╝
Above table is only for API 23+
tl;dr What to do?
Option 1- If you only use ACTION_IMAGE_CAPTURE
etc...
Remove the CAMERA
permission from manifest and you would be fine
Option 2- If you use other CAMERA
functions:
Check for CAMERA
permission at runtime and only start the intent when the permission is available
Android M - camera permissions issue
First, you are not calling your Camerapermission()
method, at least in terms of the code shown in your question.
Second, you are allowing the user to do something strange with a RadioButton
that triggers a call to openCamera()
, without checking to see that you have permission to use the camera. For example, you could use checkSelfPermission()
to see if you have permission, and only enable that RadioButton
if you do.
You may wish to read more about the runtime permission system.
Related Topics
What Is Meaning of Boolean Value Returned from an Event-Handling Method in Android
Visual Studio (2015) Emulator for Android Not Working - Xde.Exe - Exit Code 3
Intent.Resolveactivity Returns Null in API 30
How to Dismiss a Progress Bar Even If There Is No View to Populate in the Firebaselistadapter
Changing Overflow Icon in the Action Bar
Passing Argument to Dialogfragment
Using Seekbar to Control Volume in Android
How to Set a Font for the Options Menu
Google Places API Request Denied for Android Autocomplete, Even with the Right API Key
How to Get Cell Service Signal Strength in Android
New Intent() Starts New Instance with Android: Launchmode="Singletop"
Check If Battery Optimization Is Enabled or Not for an App
Googlesignatureverifier Signature Not Valid Message (Google Play Services 9.0.0)
Solving "Adb Server Version Doesn't Match This Client" Error
How to Get an Uri of an Image Resource in Android