I have an activity that allows the user to select preview a photo that they select from the gallery or the camera. The problem I'm having is that the camera/gallery intent returns immediately, then shows the camera/gallery and returns nothing.
The basic flow of things is as follows: Fragment -> Application Subclass -> Top Activity -(startActivity)-> Photo Preview Activity -(in onCreate)-> Photo Chooser Intent
//In the application subclass
public static void launchImageSelector()
{
if(!(topActivity instanceof ImagePreviewActivity))
{
Intent i = new Intent(context, ImagePreviewActivity.class);
topActivity.startActivityForResult(i, kImageSelectorRequestCode);
}
}
///in ImagePreviewActivity class
#Override
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
Intent chooser = createChooserIntent(createCameraIntent());
chooser.putExtra(Intent.EXTRA_INTENT, createOpenableIntent("image/*"));
startActivityForResult(chooser, 1);
}
//intent creaters(from android src)
private Intent createChooserIntent(Intent... intents)
{
Intent chooser = new Intent(Intent.ACTION_CHOOSER);
chooser.putExtra(Intent.EXTRA_INITIAL_INTENTS, intents);
chooser.putExtra(Intent.EXTRA_TITLE, "Choose Photo");
return chooser;
}
private Intent createOpenableIntent(String type)
{
Intent i = new Intent(Intent.ACTION_GET_CONTENT);
// i.addCategory(Intent.CATEGORY_OPENABLE);
i.setType(type);
return i;
}
private Intent createCameraIntent()
{
Intent cameraIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
File externalDataDir = Environment.getExternalStoragePublicDirectory(
Environment.DIRECTORY_DCIM);
File cameraDataDir = new File(externalDataDir.getAbsolutePath() +
File.separator + "browser-photos");
cameraDataDir.mkdirs();
String mCameraFilePath = cameraDataDir.getAbsolutePath() + File.separator +
System.currentTimeMillis() + ".jpg";
photoFileUri = Uri.fromFile(new File(mCameraFilePath));
cameraIntent.putExtra(MediaStore.EXTRA_OUTPUT, photoFileUri);
return cameraIntent;
}
What am I doing wrong here? What would cause the Chooser Intent to return immediately but also continue? Am I doing something fundamentally wrong here?
Thanks for the help!!
After hours of debugging the problem was in the Manifest file. In android, you can't start an activity for a result if the launch mode is set to singleInstance or singleTop
Found the answer here: Android - startActivityForResult immediately triggering onActivityResult
Related
I am developing android app and my app have button to take camera. Previously i had fallen into a state where return data in onActivityResult after taking picture being null. This is camera expected behaviour whereby if we put EXTRA_OUTPUT in intent , it would return null. For that reason , I did null checking code and it went fine .
Now again after a few days and i tested . I still fallen into same issue again. But this time data is not null. data has empty intent such as intent and data.getData() become null.I fixed this by checking data.getData() == null and it works again. I don't why it is like that. Just curious about what was going on. For that reason i have to re-upload to production again. :-(
//camera intent
Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
takePictureIntent.putExtra("requestCode", Constants.REQUEST_IMAGE_CAPTURE);
Intent chooseImageIntent = new Intent(Intent.ACTION_PICK,MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
chooseImageIntent.setType("image/* video/*");
chooseImageIntent.putExtra(Intent.EXTRA_LOCAL_ONLY, true);
chooseImageIntent.putExtra("requestCode", Constants.REQUEST_CHOOSE_FROM);
//app can use camera
if (takePictureIntent.resolveActivity(mContext.getPackageManager()) != null) {
//add output file path which camera will save image to
takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT, Helpers.getOutputMediaFileUri());
//create choose
Intent chooser = Intent.createChooser(chooseImageIntent, "Select From");
//add take camera intent as first intent
chooser.putExtra(Intent.EXTRA_INITIAL_INTENTS,new Intent[]{takePictureIntent});
//open up dialog
((Activity) mContext).startActivityForResult(chooser, Constants.REQUEST_CHOOSE_FROM);
} else {
((Activity) mContext).startActivityForResult(chooseImageIntent, Constants.REQUEST_IMAGE_GALLERY);
}
EDITED
I know I how to fix the problem. What i don't understand is return data must be null if i put in EXTRA_OUTPUT. Mostly importantly the code I implemented few weeks back , i am quite sure that data return null and suddenly it is non null value again.
Actually the camera intent doesnot return the data in intent because after getting image it kill the activity.
so try this
void opencameraForPicture(int requestCode, Uri fileUri) {
checkPermissionForMarshMello(Manifest.permission.WRITE_EXTERNAL_STORAGE,Manifest.permission.READ_EXTERNAL_STORAGE);
Intent intent = new Intent(Constants.CAMERA_INTERNAL_CLASS);
intent.putExtra(MediaStore.EXTRA_OUTPUT, fileUri);
/* start activity for result pass intent as argument and request code */
startActivityForResult(intent, requestCode);
}
/**
* This method set the path for the captured image from camera for adding
* the new picture in the list
*/
private Uri getOutputMediaFile() {
File mediaStorageDir = new File(
Environment.getExternalStorageDirectory(), "."
+ Constants.CONTAINER);
// Create the storage directory if it does not exist
if (!mediaStorageDir.exists()) {
mediaStorageDir.mkdirs();
}
File mediaFile = new File(mediaStorageDir.getPath() + File.separator
+ "IMG_" + System.currentTimeMillis() + ".png");
Uri uri = null;
if (mediaFile != null) {
uri = Uri.fromFile(mediaFile);
}
return uri;
}
in #Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
String imagePath = fileUri.getPath();
//you can decode this path as bitmap
}
I am using following code to get picture from camera. Except samsung it is working fine in other mobiles. please let me know what i am doing wrong.
final File root = new File(Environment.getExternalStorageDirectory() + File.separator + "temp" + File.separator);
root.mkdir();
final String fname = "img_" + System.currentTimeMillis() + ".jpg";
final File sdImageMainDirectory = new File(root, fname);
outputFileUri = Uri.fromFile(sdImageMainDirectory);
// Camera.
final List<Intent> cameraIntents = new ArrayList<Intent>();
final Intent captureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
final PackageManager packageManager = cordova.getActivity().getPackageManager();
final List<ResolveInfo> listCam = packageManager.queryIntentActivities(captureIntent, 0);
for (ResolveInfo res : listCam){
final String packageName = res.activityInfo.packageName;
final Intent intent = new Intent(captureIntent);
intent.setComponent(new ComponentName(res.activityInfo.packageName, res.activityInfo.name));
intent.setPackage(packageName);
intent.putExtra(MediaStore.EXTRA_OUTPUT, outputFileUri);
cameraIntents.add(intent);
}
//FileSystem
final Intent galleryIntent = new Intent();
galleryIntent.setType("image/jpeg");
galleryIntent.setAction(Intent.ACTION_GET_CONTENT);
// Chooser of filesystem options.
final Intent chooserIntent = Intent.createChooser(galleryIntent, "Select Image Source");
// Add the camera options.
chooserIntent.putExtra(Intent.EXTRA_INITIAL_INTENTS, cameraIntents.toArray(new Parcelable[]{}));
startActivityForResult(chooserIntent, PICK_FILE_REQUEST);
And onActivityResult
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == PICK_FILE_REQUEST) {
if(data!=null){
Logv("Data","got some data");
}
}
}
Except samsung it is working fine in other mobiles
No, it is only working with the camera apps on the devices that you have tried. It generally will not work for ACTION_IMAGE_CAPTURE.
please let me know what i am doing wrong
You are assuming that ACTION_IMAGE_CAPTURE is supposed to return a result Intent. It is not required when you provide EXTRA_OUTPUT. You know where you asked for the image to be saved (the value you supplied to EXTRA_OUTPUT, so go look there for the image.
Note that there are some buggy camera apps that will ignore EXTRA_OUTPUT (storing the image where they want), so if the image from your ACTION_IMAGE_CAPTURE request is not in EXTRA_OUTPUT, you are out of luck.
I only want to call the system camera take picture not from the third-party. I can not get the result from the third-party or the method I can get result from the third party.
Below is my code;
Intent intent2 = new Intent();
Intent intent_camera = getPackageManager().getLaunchIntentForPackage("com.android.camera");
if (intent_camera != null) {
intent2.setPackage("com.android.camera");
}
intent2.addFlags(Intent.FLAG_ACTIVITY_REORDER_TO_FRONT);
Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
List<ResolveInfo> list = getPackageManager().queryIntentActivities(intent, PackageManager.MATCH_DEFAULT_ONLY);
for (ResolveInfo resolveInfo: list) {
if (resolveInfo.activityInfo.applicationInfo.
// update to account for unlikely camera app update:
flags & (ApplicationInfo.FLAG_SYSTEM | ApplicationInfo.FLAG_UPDATED_SYSTEM_APP))
// worse approach:
// sourceDir.startsWith("/system/app")) {
intent.setClassName(resolveInfo.activityInfo.applicationInfo.packageName, resolveInfo.activityInfo.name);
break;
}
}
startActivityForResult(intent, actionCode);
you have to do some thing like this. Implement onActivityResult to catch the result
String name = dateToString(new Date(), "yyyy-MM-dd-hh-mm-ss");
destination = new File(Environment
.getExternalStorageDirectory(), Filename + ".jpg");
Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
intent.putExtra(MediaStore.EXTRA_OUTPUT,
Uri.fromFile(destination));
startActivityForResult(intent, PICK_Camera_IMAGE);
so I have the code below working fine until android 4.4. I was able to get the path from the uri by intent.getData() in onActivityResult then do something special about the uri to get the path of the photo that was selected.
private Intent createPhotoIntent() {
Intent intent = new Intent(Intent.ACTION_GET_CONTENT);
intent.addCategory(Intent.CATEGORY_OPENABLE);
intent.setType("image/*");
Intent chooser = createPhotoChooserIntent(createPhotoFromCameraIntent());
chooser.putExtra(Intent.EXTRA_INTENT, intent);
return chooser;
}
private Intent createPhotoChooserIntent(Intent... intents) {
Intent chooser = new Intent(Intent.ACTION_CHOOSER);
chooser.putExtra(Intent.EXTRA_INITIAL_INTENTS, intents);
chooser.putExtra(Intent.EXTRA_TITLE, "Please Choose Your Image");
return chooser;
}
private Intent createPhotoFromCameraIntent() {
return new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
}
what I dont understand is why I'm not able to get anything from intent.getData() now?? I also insert a line break to check what I received from the intent in onActivityResult, and I see nothing related to the path. I was able to see content://media/external/images/media/1249 but not anymore now....what happen to android 4.4!!??
please help.
I am using the camera intent to launch the camera in my app but as soon as the intent gets fired the onActivityResult gets fired and I have not even taken a picture yet.
When I do take a picture, select it and return back to my activity the onActivityResult does not get called at all
here is how I launch the camera
PackageManager pm = getPackageManager();
if (pm.hasSystemFeature(PackageManager.FEATURE_CAMERA)) {
Intent camera = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
File tempDir = new File(Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES),"Mobile Map");
if (!tempDir.exists()) {
if (!tempDir.mkdir()) {
Toast.makeText(this,
"Please check SD card! Image shot is impossible!",
Toast.LENGTH_SHORT).show();
}
}
String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss",Locale.US).format(new Date());
File mediaFile = new File(tempDir.getPath() + File.separator+ "IMG_" + timeStamp + ".jpg");
photoUri = Uri.fromFile(mediaFile);
camera.putExtra(MediaStore.EXTRA_OUTPUT, photoUri);
startActivityForResult(camera, CAMERA_REQUEST);
} else {
Toast.makeText(this,"This device does not have a rear facing camera",Toast.LENGTH_SHORT).show();
}
Why is the onActivityResult only getting called after the camera intent launches?
The problem was that in my manifest I had the activity set to singleInstance and apparently startActivityForResultdoes not like that