I am doing a "Image Editor" like application. I used default camera intent to capture the image. I used to parse the URI and set that to the image view like the following:
imgCaptured.setImageURI(Uri.parse(filePath));
If I use this raw image, occasionally it is throwing me out of memory error! So I decided to decode the image using the following:
"Got from stackoverflow"
BitmapFactory.Options options = new BitmapFactory.Options();
options.inSampleSize = 8;
preview_bitmap = BitmapFactory.decodeStream(is, null, options);
private Bitmap decodeFile(File f) {
try {
// Decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeStream(new FileInputStream(f), null, o);
// The new size we want to scale to
final int REQUIRED_SIZE = 95;
// Find the correct scale value. It should be the power of 2.
int scale = 1;
while (o.outWidth / scale / 2 >= REQUIRED_SIZE
&& o.outHeight / scale / 2 >= REQUIRED_SIZE)
scale *= 2;
// Decode with inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
return BitmapFactory.decodeStream(new FileInputStream(f), null, o2);
} catch (FileNotFoundException e) {
}
return null;
}
If I use the decoded image, the output is not in good quality. Some how it seems to be blur. I want a good clear image! After setting it into the ImageView. I need to drag and drop another views.
How can I achieve the above?
What is a good way to do this?
what is the reason to divide by 2 in the loop ?
try this
while (o.outWidth / scale >= REQUIRED_SIZE
&& o.outHeight / scale >= REQUIRED_SIZE)
Probably You also would like to scale the image to the view's size with this method
http://developer.android.com/reference/android/graphics/Bitmap.html#createScaledBitmap(android.graphics.Bitmap, int, int, boolean)
change options.inSampleSize = 8 to options.inSampleSize = 4.
The method which you had used is not complete, you have to add few Math functions to, too maintain the quality of the image.
private static Bitmap decodeFile(File f) {
Bitmap b = null;
final int IMAGE_MAX_SIZE = 100;
try {
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
FileInputStream fis = new FileInputStream(f);
BitmapFactory.decodeStream(fis, null, o);
fis.close();
int scale = 1;
if (o.outHeight > IMAGE_MAX_SIZE || o.outWidth > IMAGE_MAX_SIZE) {
scale = (int) Math.pow(
2.0,
(int) Math.round(Math.log(IMAGE_MAX_SIZE
/ (double) Math.max(o.outHeight, o.outWidth))
/ Math.log(0.5)));
}
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
fis = new FileInputStream(f);
b = BitmapFactory.decodeStream(fis, null, o2);
fis.close();
} catch (Exception e) {
Log.v("Exception in decodeFile() ", e.toString() + "");
}
return b;
}
Please let me know, if it worked for you...!!!!:)
Related
I try show a bitmap from the gallery. this is my URL
file:///storage/emulated/0/DCIM/Camera/IMG_20161103_180603.jpg
I know how to get bitmap using onActivityResult(), but I don't know how to get a bitmap
this is my source
final ImageView imageView=(ImageView)findViewById(R.id.imageView);
BitmapFactory.Options options = new BitmapFactory.Options();
options.inPreferredConfig = Bitmap.Config.ARGB_8888;
final Bitmap bitmap = BitmapFactory.decodeFile("file:///storage/emulated/0/DCIM/Camera/IMG_20161103_180603.jpg", options);
runOnUiThread(new Runnable() {
#Override
public void run() {
imageView.setImageBitmap(bitmap);
}
});
How can I solve my problem?
please refer below code
BitmapFactory.Options options = new BitmapFactory.Options();
options.inPreferredConfig = Bitmap.Config.ARGB_8888;
//Get our saved file into a bitmap object:
File file = new File(Environment.getExternalStorageDirectory()+File.separator + "DCIM"+ File.separator + "Camera "+File.separator + "IMG_20161103_180603.jpg");
Bitmap bitmap = BitmapFactory.decodeFile(file.getAbsolutePath(), options);
imageView.setImageBitmap(bitmap);
I had the same problem caused by large image size which couldn't be processed at run time. Solved it using this.
// Decodes image and scales it to reduce memory consumption
public static Bitmap decodeFile(File f) {
try {
// Decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeStream(new FileInputStream(f), null, o);
// The new size we want to scale to
final int REQUIRED_SIZE = 200;
// Find the correct scale value. It should be the power of 2.
int scale = 1;
while (o.outWidth / scale / 2 >= REQUIRED_SIZE &&
o.outHeight / scale / 2 >= REQUIRED_SIZE) {
scale *= 2;
}
// Decode with inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
return BitmapFactory.decodeStream(new FileInputStream(f), null, o2);
} catch (FileNotFoundException e) {
e.printStackTrace();
}
return null;
}
where File f will be retrieved using https://stackoverflow.com/a/20559418/3758972
just put the size of thumbnail you want (typically the size of your imageview) in REQUIRED_SIZE and you are done. It will give you a scaled image which you can set to your imageview.
decodeFile( "file:///storage/emulated/0/DCIM/Camera/IMG_20161103_180603.jpg
Change to:
decodeFile( "/storage/emulated/0/DCIM/Camera/IMG_20161103_180603.jpg
I'm facing this problem since a month with no solution:
I need to convert a file into a bitmap and rescaling it.
I'm using the following method, taken from android guide: Loading Large Bitmaps Efficiently
public Bitmap decodeSampledBitmapFromFile(String path, int reqSize) {
// First decode with inJustDecodeBounds=true to check dimensions
BitmapFactory.Options options = new BitmapFactory.Options();
options.inJustDecodeBounds = true;
options.inMutable = true;
BitmapFactory.decodeFile(path, options);
// Calculate inSampleSize
double ratio = (double) options.outHeight / options.outWidth;
boolean portrait = true;
if (ratio < 1) {
portrait = false;
}
double floatSampleSize = options.outHeight / (double)reqSize;
options.inSampleSize = (int) Math.floor(floatSampleSize);
// Decode bitmap with inSampleSize set
options.inJustDecodeBounds = false;
Bitmap resultBitmap = BitmapFactory.decodeFile(path, options);
if(floatSampleSize % options.inSampleSize != 0){
if(portrait) {
resultBitmap = Bitmap.createScaledBitmap(resultBitmap, (int)(reqSize/ratio), reqSize, true);
} else {
resultBitmap = Bitmap.createScaledBitmap(resultBitmap, reqSize, (int)(ratio*reqSize), true);
}
}
return resultBitmap;
}
I've got the same NullPointerException but i can't reproduce it:
NullPointerException (#Utilities:decodeSampledBitmapFromFile:397) {AsyncTask #2}
NullPointerException (#Utilities:decodeSampledBitmapFromFile:399) {AsyncTask #3}
lines 397 and 399 are:
resultBitmap = Bitmap.createScaledBitmap(resultBitmap, (int)(reqSize/ratio), reqSize, true);
resultBitmap = Bitmap.createScaledBitmap(resultBitmap, reqSize, (int)(ratio*reqSize), true);
in this device models:
ST21a
U9500
M7
U8950-1
GT-I9305
Someone can help me to solve this?
is BitmapFactory.decodeFile returns null?
thank you so much
Try this hope works for you
public Bitmap decodeFile(String path, int reqSize) {
try {
// Decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeFile(path, o);
// The new size we want to scale to
final int REQUIRED_SIZE = reqSize;
// Find the correct scale value. It should be the power of 2.
int scale = 1;
while (o.outWidth / scale / 2 >= REQUIRED_SIZE && o.outHeight / scale / 2 >= REQUIRED_SIZE)
scale *= 2;
// Decode with inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
return BitmapFactory.decodeFile(path, o2);
} catch (Throwable e) {
e.printStackTrace();
}
return null;
}
I have problem with tracking mmemory leak in my app.
I'm using MAT to do this, but i'm also beginner in this feature so i need your help.
Dominator tree looks like this:
Obviously 23% for bitmap isn't normal...
Path to GC Root -> exclude weak references:
But I really don't know what to do next ... It is obvious that memory is leaking through the images.
I'm converting resources to Bitmaps and scale it like this:
private Bitmap getBitmapFromRes(int resId) {
Bitmap tmp = null;
Bitmap b = null;
try {
// Decode image size
final int REQUIRED_SIZE = 70;
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
int scale = 1;
while (o.outWidth / scale / 2 >= REQUIRED_SIZE
&& o.outHeight / scale / 2 >= REQUIRED_SIZE)
scale *= 2;
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
InputStream fis = context.getResources().openRawResource(resId);
b = BitmapFactory.decodeStream(fis, null, o2);
fis.close();
} catch (IOException e) {
e.printStackTrace();
} finally {
if (tmp != null) {
tmp.recycle();
tmp = null;
}
}
return b;
}
Thanks for help and sorry for my english...
I currently have a decode bitmap method to optimize the size of the image file, however the input file won’t be a bitmap and will decode to bitmap afterward. So my problem is, how can I resize it if my input is a bitmap already? Thanks.
private Bitmap compressFile(File f) {
int REQUIRED_SIZE = 80;
try {
// decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeStream(new FileInputStream(f), null, o);
// Find the correct scale value. It should be the power of 2.
int width_tmp = o.outWidth;// , height_tmp = o.outHeight;
int scale = 1;
while (REQUIRED_SIZE > 0) {
if (width_tmp <= REQUIRED_SIZE)
break;
width_tmp /= 2;
// height_tmp /= 2;
scale++;
}
// decode with inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
return BitmapFactory.decodeStream(new FileInputStream(f), null, o2);
} catch (FileNotFoundException e) {
}
return null;
}
What I would like to change to is compressFile (Bitmap f)
You may use this too
Bitmap b = BitmapFactory.decodeByteArray(imageAsBytes, 0, imageAsBytes.length)
profileImage.setImageBitmap(Bitmap.createScaledBitmap(b, 120, 120, false));
or are you asking for:
bitmap.compress(Bitmap.CompressFormat.PNG, quality, outStream);
check this link for more info
I want to resize an image on the sd card and send it to a Web service, the call is asynchronous and ParcelFileDescriptor and CountingInputStreamEntity use to display progress bar. What should I do to resize and send in the same way ! This is my current code:
ParcelFileDescriptor fileDescriptor = context.getContentResolver().openFileDescriptor(uri, "r");
InputStream in = context.getContentResolver().openInputStream(uri);
CountingInputStreamEntity entity = new CountingInputStreamEntity(in, fileDescriptor.getStatSize());
entity.setUploadListener(this);
entity.setContentType("application/octet-stream");
put.setEntity(entity);
Thanks in Advance.
The image can be re-sized by using BitmapFactory.Options
You need to create a new small width and height of the image like following:
private Bitmap decodeFile(File f){
Bitmap b = null;
try {
//Decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
FileInputStream fis = new FileInputStream(f);
BitmapFactory.decodeStream(fis, null, o);
fis.close();
int scale = 1;
if (o.outHeight > IMAGE_MAX_SIZE || o.outWidth > IMAGE_MAX_SIZE) {
scale = (int)Math.pow(2, (int) Math.round(Math.log(IMAGE_MAX_SIZE / (double) Math.max(o.outHeight, o.outWidth)) / Math.log(0.5)));
}
//Decode with inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
fis = new FileInputStream(f);
b = BitmapFactory.decodeStream(fis, null, o2);
fis.close();
} catch (IOException e) {
}
return b;
}
To resize the camera image you can use the following code in onActivitResult().
BitmapFactory.Options options = new BitmapFactory.Options();
options.inSampleSize = 8;
Bitmap receipt = BitmapFactory.decodeFile(photo.toString(),options);
In which the you can resize the image using options.inSampleSize and then pass that image to the web service by your style.
I hope it helps..