0

What am I doing wrong here? I'm trying to call the intent to get a picture in full size:

takePictureIntent

private void takePictureIntent(int request) {
    final Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);

    if (takePictureIntent.resolveActivity(activity.getPackageManager()) != null) {
        File file = null;

        try {
            file = createImageFile(request);
        } catch (Exception e) {
            showErrorDialog(getString(R.string.error), getString(R.string.error_saving_picture));
            Log.e(TAG, "Error while creating image file.");
        }

        if (file != null) {
            takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(file));
            startActivityForResult(takePictureIntent, request);
        } else {
            Log.e(TAG, "Error while creating image file.");
            showErrorDialog(getString(R.string.error), getString(R.string.error_saving_picture));
        }
    }
}

createImageFile

private File createImageFile(final int request) {
    final File storageDir = new File(activity.getExternalFilesDir(Environment.DIRECTORY_PICTURES), getString(R.string.app_name));

    if (!storageDir.exists()) {
        if (!storageDir.mkdirs()) {
            Log.e(TAG, "Cannot create parent folders.");
            return null;
        }
    }

    File file = null;

    try {
        file = File.createTempFile("test_", ".jpg", storageDir);
    } catch (Exception e) {
        Log.e(TAG, "Error while creating temp file.");
    }

    fileProduct = file;

    return file;
}

onActivityResult

@Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
    if (resultCode == Activity.RESULT_OK && requestCode == REQUEST_IMAGE_PRODUCT) {

    if (fileProduct == null ||!fileProduct.exists() ||fileProduct.length() == 0) {
        showErrorDialog(getString(R.string.error), getString(R.string.error_taking_product_picture));
        return;
    }
}

Sometimes (yes, sometimes) the length of the resulting file is 0. I know for sure that the folders in private app context exist and the image files as well (with length > 0). Could you please provide some help? I'm on 6.0 on Nexus 5X.

Jumpa
  • 4,319
  • 11
  • 52
  • 100

2 Answers2

1

I would start by getting rid of File.createTempFile(). You do not need it, it wastes time, and it might cause some camera apps to want to not store the photo in that file (since the file is already there). Just generate a unique filename yourself. This will incrementally help with your compatibility.

Also, you need to make sure that you are holding onto fileProduct in the saved instance state Bundle, as your app's process may be terminated while the camera app is in the foreground.

However, in general, ACTION_IMAGE_CAPTURE is not very reliable. You are delegating the work to one of hundreds of possible camera apps, and some of those apps have bugs. One such bug is ignoring EXTRA_OUTPUT. So, in onActivityResult(), if you determine that you have a valid fileProduct value, but there is no file there, call data.getData() and see if you have a Uri there. In that case, the camera app may have stored the photo at the location identified by that Uri, and you can use ContentResolver and DocumentFile to try to work with that Uri.

CommonsWare
  • 986,068
  • 189
  • 2,389
  • 2,491
  • Ok for 1 and 2, but I wouldn't expect such a bug on a Nexus camera app...This code is working fine on a Motorola Moto G 2014 with Lollipop. I'm calling startActivityForResult from a fragment if this could be helpful. What I'm not getting here, is that the image is there, filesystem has it...sob. – Jumpa Aug 30 '16 at 18:10
  • @Jumpa: Then your problem is not a zero-length file. My guess is that `fileProduct` is `null`, because your process was terminated in the background. – CommonsWare Aug 30 '16 at 18:14
  • I tested it file exists (i mean the method exists()) and is not null. – Jumpa Aug 30 '16 at 18:18
0

Using this:

final String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss").format(new Date());
file = new File(storageDir.getPath() + File.separator + "IMG_" + timeStamp + ".jpg");

instead of

File.createTempFile()

magically seems to fix the problem. Thanks to CommonsWare for (somehow) pointing me in the right direction.

Jumpa
  • 4,319
  • 11
  • 52
  • 100