When i pick a picture the BitmapFactory.decodeFile returns null.
Here is my function:
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
// Here we need to check if the activity that was triggers was the Image Gallery.
// If it is the requestCode will match the LOAD_IMAGE_RESULTS value.
// If the resultCode is RESULT_OK and there is some data we know that an image was picked.
if (requestCode == SELECT_PHOTO && resultCode == RESULT_OK && data != null) {
// Let's read picked image data - its URI
Uri pickedImage = data.getData();
// Let's read picked image path using content resolver
String[] filePath = { MediaStore.Images.Media.DATA };
Cursor cursor = getContentResolver().query(pickedImage, filePath, null, null, null);
cursor.moveToFirst();
String imagePath = cursor.getString(cursor.getColumnIndex(filePath[0]));
BitmapFactory.Options options = new BitmapFactory.Options();
options.inPreferredConfig = Bitmap.Config.ARGB_8888;
Bitmap bitmap = BitmapFactory.decodeFile(imagePath,options);
//imageView.setImageBitmap(bitmap);
// Do something with the bitmap
// At the end remember to close the cursor or you will end with the RuntimeException!
cursor.close();
}
}
Can somebody tell me what is the issue?
String imagePath = cursor.getString(cursor.getColumnIndex(filePath[0]));
do you have the filePath in the variable imagePath ? or is imagePath value is null too ?
UPDATE
your BitmapFactory.decodeFile() is returning null because may be the imageSize is too big and its throwing some exception.
check your log and see if there is any outOfMemory Bitmap error is there . let me know
Related
I'm building an android application which allow user to pick Image from camera or From Gallery then display the image in a Imageview.My application working fine if the user take the picture from camera, but if the user pick the image from gallery my application only work on android 9 and bellow,BitmapFactory.decodeFile(ImageFilePath) always return null on android 10 with the imageFilePath = "/storage/emulated/0/DCIM/Camera/20200629_114552.jpg"(path is the same on android 9 and 10). I've requested for read external storage permission before open gallery and then get the image path from onActivityResult like bellow:
public void onActivityResult(int requestCode, int resultCode, Intent data) {
if (resultCode == Activity.RESULT_OK) {
switch (requestCode) {
case GALLERY_REQUEST_CODE:
Uri selectedImage = data.getData();
String[] filePathColumn = {MediaStore.Images.Media.DATA};
Cursor cursor = getActivity().getContentResolver().query(selectedImage,
filePathColumn, null, null, null);
cursor.moveToFirst();
int columnIndex = cursor.getColumnIndex(filePathColumn[0]);
String imgDecodableString = cursor.getString(columnIndex);
cursor.close();
if (!mNextImg) {
mBiomatrics_left_identity_img
.setImageBitmap(BitmapFactory.decodeFile(imgDecodableString));
} else {
mBiomatrics_right_identity_img
.setImageBitmap(BitmapFactory.decodeFile(imgDecodableString));
}
mNextImg = !mNextImg;
if (mBiomatrics_left_identity_img.getDrawable() != null
&& mBiomatrics_right_identity_img.getDrawable() != null) {
mBiomatrics_btn_confirm.setTextColor(getResources()
.getColor(R.color.mainTextColor));
} else {
mBiomatrics_btn_confirm.setTextColor(getResources()
.getColor(R.color.biometrics_btn_confirm_deactive_color));
}
break;
}
}
}
InputStream is = getContentResolver().openInputStream(data.getData());
Bitmap bitmap = BitmapFactory.decodeStream(is);
Use this for all Android versions.
Stop with trying to get a path for an uri.
Solution: for Android 10,
All you need is this line: (in manifests)
android:requestLegacyExternalStorage="true"
I'm trying to add Pick image with Crop feature by aspect 1:4, it's 2000 width, 500 height => 1:4, and i want the selected image by user to replace an image located in drawable/custom_image.jpg.
Note : the image "custom_image" isn't showed as imageview in the app.
I've searched Stackoverflow, and found the ways, but i'm having a problem with cropping it & replacing that selected image with "R.drawable.custom_image".
EDIT : Forgot the cropping, got problems in it, i just need the replace drawable code in OnActivityResult.
I've created a button, when pressed it calls a method, here's the code :
Button mSelectbutton = (Button) view.findViewById(R.id.selectimage);
mSelectbutton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
SelectImageActivity(v);
}
});
SelectImageActivity :
public void SelectImageActivity(View v) {
Intent selectintent = new Intent();
// Show only images, no videos or anything else
selectintent.setType("image/*");
selectintent.setAction(Intent.ACTION_GET_CONTENT);
// Always show the chooser (if there are multiple options available)
startActivityForResult(Intent.createChooser(selectintent, "Select Picture"), PICK_IMAGE_REQUEST);
}
And here's the method :
OnActivityResult Code :
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == PICK_IMAGE_REQUEST && resultCode == RESULT_OK && null != data) {
Uri selectedImage = data.getData();
String[] filePathColumn = { MediaStore.Images.Media.DATA };
Cursor cursor = getContentResolver().query(selectedImage, filePathColumn, null, null, null);
cursor.moveToFirst();
int columnIndex = cursor.getColumnIndex(filePathColumn[0]);
String picturePath = cursor.getString(columnIndex);
cursor.close();
Drawable imageView = (Drawable)findViewById(R.drawable.custom_header);
imageView.setImageDrawable(getDrawable(R.drawable.custom_header);
}
}
I have used this library to tackle this problem because keeping outputx etc.. is not working for some versions of android:
Add this library to gradle:
//image cropping library to show as square for android older versions to work
compile 'com.soundcloud.android:android-crop:1.0.1#aar'
this method performs cropping:
private void performCrop(Uri mImageCaptureUri) {
//this creates a new image file comment below if you want file creation code
Uri destinationUri = MediaUtils.getOutputMediaFileUri(GlobalConstants.CREATE_IMAGE);
Crop.of(mImageCaptureUri,destinationUri).asSquare().start(getActivity(),this);
}
In your on activity result you can get Cropped image catch it:
if(requestCode == Crop.REQUEST_CROP) {
Uri outPutImageUri = Crop.getOutput(data);
Comment below if you want any futher info
I tried that code and gave me error unable to decode stream filenotfoundException. So I found that the latest versions of Android Marshmallow and lollipop doesn't have the gallery application and the images uploaded to a server.
public String getPath(Uri uri) {
// just some safety built in
if( uri == null ) {
// TODO perform some logging or show user feedback
return null;
}
// try to retrieve the image from the media store first
// this will only work for images selected from gallery
String[] projection = { MediaStore.Images.Media.DATA };
Cursor cursor = managedQuery(uri, projection, null, null, null);
if( cursor != null ){
int column_index = cursor
.getColumnIndexOrThrow(MediaStore.Images.Media.DATA);
cursor.moveToFirst();
String picturePath = cursor.getString(column_index);
return picturePath;
}
// this is our fallback here
return uri.getPath();
}
public void onActivityResult(int requestCode, int resultCode, Intent data) {
if (resultCode == RESULT_OK) {
if (requestCode == SELECT_PICTURE) {
Uri selectedImageUri = data.getData();
selectedImagePath = getPath(selectedImageUri);
ImageView imageView = (ImageView) findViewById(R.id.profile_picture);
imageView.setImageBitmap(BitmapFactory.decodeFile(getPath(selectedImageUri)));
}
}
}
My intent code:
Intent intent = new Intent();
intent.setType("image/*");
intent.setAction(Intent.ACTION_GET_CONTENT);
startActivityForResult(Intent.createChooser(intent,"Select Picture"), SELECT_PICTURE);
Step #1: Get rid of getPath().
Step #2: Use an image-loading library, such as Picasso. Pass it the Uri you get from the Intent passed into onActivityResult(), and your ImageView. It will handle loading the image into the ImageView for you.
If you would prefer to load the image yourself, you will need to:
Use a ContentResolver and openInputStream() to get an InputStream for the data represented by the Uri
Use BitmapFactory.decodeStream() to load the data off the InputStream and decode it into a Bitmap
Do the above steps in a background thread, so you do not tie up the main application thread while doing that I/O (e.g., doInBackground() of an AsyncTask)
When the Bitmap is ready, put it in the ImageView while running on the main application thread (e.g., onPostExecute() of an AsyncTask)
i made an application that will allow the user to take a camera shot and edit it using my application. I own a samsung galaxy stellar and it works fine on it. I had my friend download the application and when she tested it on her phone, my application crashes whenever she takes a picture and hit "save". shes using a galaxy s3.
Heres my code when im taking a picture
case R.id.ibTakePic:
i = new Intent(android.provider.MediaStore.ACTION_IMAGE_CAPTURE);
File file = new File(Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES)+File.sep arator + fileName2 + ".jpg");
i.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(file));
rotatePic = true;
startActivityForResult(i,cameraData);
break;
and heres my result code..
#Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
// TODO Auto-generated method stub
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == RESULT_LOAD_IMAGE && resultCode == RESULT_OK && null != data) {
Uri selectedImage = data.getData();
String[] filePathColumn = { MediaStore.Images.Media.DATA };
pictake = true;
Cursor cursor = getContentResolver().query(selectedImage,
filePathColumn, null, null, null);
cursor.moveToFirst();
int columnIndex = cursor.getColumnIndex(filePathColumn[0]);
String picturePath = cursor.getString(columnIndex);
cursor.close();
rotatePic = false;
bmpReceive = rotate(picturePath);
bmpOriginal = bmpReceive;
picTaken.setImageBitmap(bmpReceive);
// ImageView imageView = (ImageView) findViewById(R.id.imgView);
// imageView.setImageBitmap(BitmapFactory.decodeFile(picturePath));
}
I had a similar problem so I switched to this:
Uri uri= data.getData();
InputStream in = context.getContentResolver().openInputStream(uri);
Bitmap b = BitmapFactory.decodeStream(in);
hope it helps
Well, Logs help. But here is my guess.
If you check the Documentation.
http://developer.android.com/reference/android/content/ContentResolver.html
A query can return a Cursor object or null.
In your code you are not checking for the null. I suggest you try with that. In any case you should always put null checks wherever there is a chance for a null to be returned.
If you can provide the logs then we can tell you the exact problem.
Maybe the bitmap is too big and you get an out of memory. Check that page to know how to deal with that situation:
http://developer.android.com/training/displaying-bitmaps/load-bitmap.html
I am new at this :)
I am trying to load a picture from the sdcard into an ImageView in this way:
b_picture.setOnClickListener(new OnClickListener() {
public void onClick(View v) {
Intent intent = new Intent(Intent.ACTION_PICK,
MediaStore.Images.Media.INTERNAL_CONTENT_URI);
startActivityForResult(intent, 0);
}
});
Here I am trying to retrive the picture and change the ImageView:
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
Bitmap bm = (Bitmap) data.getExtras().get("data");
iv_picture.setImageBitmap(bm);
}
And I get this from the logcat:
Failure delivering result ResultInfo {who=null, request=0, result=-1,
data=Intent { dat=content://media/external/images/media/2
I can't solve this problem. Can you help me? Thanks.
The data associated with your returned Intent is not a bitmap. It's a URI you can use to look up in the MediaStore ContentProvider to get back the image you want. :)
You can find a mostly-working example over at this question.
Edit: To expand:
When you go off and query the MediaStore for an image, it isn't returning you the actual image. It's returning you a URI that you can use to look up the image. The way you translate that URI into an actual image is this:
Your URI is content://media/external/images/media/2 as per the error message.
So, we'll basically create a query and run it on the MediaStore's ContentProvider, which is a database of images. Pass that URI into this function:
public Bitmap loadFullImage( Context context, Uri photoUri ) {
Cursor photoCursor = null;
try {
// Attempt to fetch asset filename for image
// DATA is the column name in the database for the filename of the image
String[] projection = { MediaStore.Images.Media.DATA };
// use the URI you were given in order to look up the right image,
// and get a Cursor object that will iterate over the matching rows in the
// database.
photoCursor = context.getContentResolver().query( photoUri,
projection, null, null, null );
// since we only care about one image...
if ( photoCursor != null && photoCursor.getCount() == 1 ) {
// go to the first row that was returned
photoCursor.moveToFirst();
// get the string in the DATA column at that row
String photoFilePath = photoCursor.getString(
photoCursor.getColumnIndex(MediaStore.Images.Media.DATA) );
// Load image from path
return BitmapFactory.decodeFile( photoFilePath, null );
}
} finally {
// close up the cursor
if ( photoCursor != null ) {
photoCursor.close();
}
}
return null;
}
// path ex: /sdcard/myimage.png
String imageInSD = "Your image path here";
BitmapFactory.Options bOptions = new BitmapFactory.Options();
bOptions.inTempStorage = new byte[16*1024];
bitmap = BitmapFactory.decodeFile(imageInSD,bOptions);
imageView.setImageBitmap(bitmap);