我按照official docs在我的应用中执行相机意图。 它适用于5.0多种设备,但不适用于Jellybean。
在4.1(JB)到4.4(KK)中,原生相机应用程序在捕获图像后显示“不幸的是,相机已停止错误”。在我的应用程序的onActivityResult中,返回的结果始终是RESULT.CANCELLED。我做错了什么?
P.S。如果我不使用fileprovider并使用Uri.fromFile(file)获取uri,则相机意图在JB中正常工作。
以下是我的代码
// MainActivity.java
File f = PhotoHelper.createImageFile(this);
photoPath = "file:" + f.getAbsolutePath();
Uri photoURI = FileProvider.getUriForFile(this, "com.myapp.fileprovider", f);
Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT, photoURI);
startActivityForResult(takePictureIntent, Constants.NEW_TOPIC_VIA_PHOTO);
// PhotoHelper.java
public static File createImageFile(Context context) throws IOException {
String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss", Locale.US).format(new Date());
String imageFileName = JPEG_FILE_PREFIX + timeStamp + "_";
File storageDir = context.getExternalFilesDir(Environment.DIRECTORY_PICTURES);
return File.createTempFile(imageFileName, JPEG_FILE_SUFFIX, storageDir);
}
// AndroidManifest.xml
<provider
android:name="android.support.v4.content.FileProvider"
android:authorities="com.myapp.fileprovider"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/file_paths"/>
</provider>
// file_paths.xml
<paths>
<external-path
name="App_Images"
path="Android/data/com.myapp/files/Pictures"/>
</paths>
答案 0 :(得分:1)
您必须通过授予每个网址权限在代码中执行此操作。
https://medium.com/google-developers/sharing-content-between-android-apps-2e6db9d1368b#.4ip8b7yqe
官方文件:请看第4节 https://developer.android.com/reference/android/support/v4/content/FileProvider.html
更多示例: https://thinkandroid.wordpress.com/2012/08/07/granting-content-provider-uri-permissions/
答案 1 :(得分:0)
我这样做是针对Android 4.3 Jelly Bean和Android 8 Oreo:
void startCamera() {
try {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
dispatchTakePictureIntent();
}
else
{
boolean focus = getPackageManager().hasSystemFeature( "android.hardware.camera.autofocus");
//displayMsg(context, "In startCamera AutoFocus = " + focus);
dispatchTakePictureIntent4();
}
} catch (IOException e) {
displayMsg(context, "In startCamera " + e.toString());
}
}
public void dispatchTakePictureIntent() throws IOException {
try {
Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
// Ensure that there's a camera activity to handle the intent
if (takePictureIntent.resolveActivity(getPackageManager()) != null) {
// Create the File where the photo should go
File photoFile = null;
try {
photoFile = createImageFile();
} catch (IOException ex) {
// Error occurred while creating the File
displayMsg(context, "Error occurred while creating the File " + ex.toString());
return;
}
// Continue only if the File was successfully created
if (photoFile != null) {
//rww OLD here
//Uri photoURI = Uri.fromFile(createImageFile());
Uri photoURI = FileProvider.getUriForFile(TellYourStoryActivity.this,
BuildConfig.APPLICATION_ID + ".provider",
createImageFile());
takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT, photoURI);
takePictureIntent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);//added RWW
startActivityForResult(takePictureIntent, REQUEST_TAKE_PHOTO);
}
}
} catch (Exception e) {
displayMsg(context, "dispatchTakePictureIntent " + e.toString());
}
}
public void dispatchTakePictureIntent4() throws IOException {
try {
// MainActivity.java
File f = this.createImageFile4(this);
if (f == null)
{
displayMsg(context, "dispatchTakePictureIntent 444" + " file f is null");
return;
}
String photoPath = "file:" + f.getAbsolutePath();
mCurrentPhotoPath = "file:" + f.getAbsolutePath();
mCurrentAbsolutePhotoPath = f.getAbsolutePath();
//displayMsg(context, "dispatchTakePictureIntent 444 photopath\n" + photoPath);
//Uri photoURI = FileProvider.getUriForFile(this, "com.myapp.fileprovider", f);
Uri photoURI = Uri.fromFile(f);
//displayMsg(context, "dispatchTakePictureIntent 444 uri" + photoURI.toString());
Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT, photoURI);
startActivityForResult(takePictureIntent, NEW_TOPIC_VIA_PHOTO);
} catch (Exception e) {
displayMsg(context, "dispatchTakePictureIntent 444" + e.toString());
}
}
// PhotoHelper.java
public File createImageFile4(Context context) throws IOException {
try {
String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss", Locale.US).format(new Date());
String imageFileName = JPEG_FILE_PREFIX + timeStamp + "_";
File storageDir = context.getExternalFilesDir(Environment.DIRECTORY_PICTURES);
return File.createTempFile(imageFileName, JPEG_FILE_SUFFIX, storageDir);
} catch (Exception e) {
displayMsg(context, "createImageFile4 444" + e.toString());
}
return null;
}
public File createImageFile() throws IOException {
// Create an image file name
File image = null;
//displayMsg(context, "In createImageFile ");
try {
String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss").format(new Date());
String imageFileName = "JPEG_" + timeStamp + "_";
File storageDir = new File(Environment.getExternalStoragePublicDirectory(
Environment.DIRECTORY_DCIM), "Camera");
image = File.createTempFile(
imageFileName, /* prefix */
".jpg", /* suffix */
storageDir /* directory */
);
// Save a file: path for use with ACTION_VIEW intents
mCurrentPhotoPath = "file:" + image.getAbsolutePath();
RWWmCurrentPhotoPath = "content:/" + image.getAbsolutePath();
mCurrentAbsolutePhotoPath = image.getAbsolutePath();
} catch (Exception e) {
displayMsg(context, "In createImageFile " + e.toString());
}
return image;
}