İt is classical question but i didn't find answer for me. I work bitmaps in my project . apply filter,crop.. Problem is out of memory. I need keep many bitmap (approximate 20-30 bitmap) on ram.
I use this method for get image consecutively in gallery, But it is not get orginal size.
public static Bitmap getImageWithoutOutOfMemory(String filePath,int requiredSize) {
// Decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
o.inMutable = true;
o.inPreferredConfig = Bitmap.Config.ARGB_8888;
BitmapFactory.decodeFile(filePath, o);
// The new size we want to scale to
final int REQUIRED_SIZE = requiredSize;
// 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 (true)
{
if (width_tmp < REQUIRED_SIZE && height_tmp < REQUIRED_SIZE)
break;
width_tmp /= 2;
height_tmp /= 2;
scale *= 2;
}
// Decode with inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
Bitmap img = BitmapFactory.decodeFile(filePath, o2);
return img;
}
so how can i get orginal image without out of memory exception.
u can try resize bitmap using decodeSampledBitmapFromResource method
The function in its current form chooses a size that ensures the image is scaled to be strictly smaller than a required size.
At lease change:
if (width_tmp < REQUIRED_SIZE && height_tmp < REQUIRED_SIZE) break;
to
if (width_tmp <= REQUIRED_SIZE && height_tmp <= REQUIRED_SIZE) break;
If the image is 'naturally' with the required size it will actually be returned half size.
If there are other problems please post a MVCE.
Related
In my app i am selecting a picture from storage or taking a picture using camera and it will set in to an image view.When doing this i got Out of memory Error ,to avoid this I used this method.But it is not working,can anyone help to solve this issue .Or can anyone suggest any other method to handle this issue.
public void decodeFile(String filePath) {
// Decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeFile(filePath, o);
// The new size we want to scale to
final int REQUIRED_SIZE = 1024;
// 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 (true) {
if (width_tmp < REQUIRED_SIZE && height_tmp < REQUIRED_SIZE)
break;
width_tmp /= 2;
height_tmp /= 2;
scale *= 2;
}
// Decode with inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
bitmap = BitmapFactory.decodeFile(filePath, o2);
imgView.setImageBitmap(bitmap);
}
I would suggest to use a library to handle the loading, caching and displaying of images.
They are easy to use and you dont have to take care of image downsizing etc.
In my projects i use the Universal Image Loader by nostra13.
It is pretty easy to implement and offers a lot of features like memory and disk caching. You should give it a try.
I want to let the user choose how much they want to reduce the image file size by, could be low, medium or high then upload the image to a server That part is easy.
Next part is the actual reduction of file size. I'm getting the image URI, I want to reduce the file image file size, the image type could be png, jpg or something else.
I'm aware of Bitmap.compress(), is this the only way to implement or is there an existing open source library?
Bitmap bitmap;
bitmap = MyBitmapFactory.decodeFile(PATHTOPICT, UPLOAD_REQUIRED_SIZE);
if (bitmap != null) {
bitmap.compress(Bitmap.CompressFormat.JPEG, 100, stream);
with the method (found with google):
public static Bitmap decodeFile(String filePath, final int REQUIRED_SIZE) {
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeFile(filePath, o);
int width_tmp = o.outWidth, height_tmp = o.outHeight;
int scale = 1;
while (true) {
if (width_tmp <= REQUIRED_SIZE && height_tmp <= REQUIRED_SIZE)
break;
width_tmp /= 2;
height_tmp /= 2;
scale *= 2;
}
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
Bitmap bitmap = BitmapFactory.decodeFile(filePath, o2);
return bitmap;
}
if something get NULL, its no image/.
scale by power 2 is recommended!!!
This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
Android: Strange out of memory issue while loading an image to a Bitmap object
I am new in android field. I don't known the how to reduce the memory consumption in android. In my application large number of image is drawn from the web and display into grid view. When running the application "out memory problem is occur".
Please help me
1) scale down and reduce the size of images
/**
* decodes image and scales it to reduce memory consumption
*
* #param file
* #param requiredSize
* #return
*/
public static Bitmap decodeFile(File file, int requiredSize) {
try {
// Decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeStream(new FileInputStream(file), null, o);
// The new size we want to scale to
// 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 (true) {
if (width_tmp / 2 < requiredSize
|| height_tmp / 2 < requiredSize)
break;
width_tmp /= 2;
height_tmp /= 2;
scale *= 2;
}
// Decode with inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
Bitmap bmp = BitmapFactory.decodeStream(new FileInputStream(file),
null, o2);
return bmp;
} catch (FileNotFoundException e) {
} finally {
}
return null;
}
2) use bitmap.Recycle();
3) use System.gc(); for indicating to the VM that it would be a good time to run the garbage collector
I am using android Camera. Also using auto focusing feature. After capturing image more then 10 times getting the following exception:
Caused by: java.lang.OutOfMemoryError: bitmap size exceeds VM budget
my source code is following:
PictureCallback jpegCallback = new PictureCallback() {
public void onPictureTaken(byte[] data, Camera camera) {
try {
// Bitmap bmp = BitmapFactory.decodeStream(new
// ByteArrayInputStream(data));
Utility.gc();
Bitmap bmp = decodeFile(data);
Utility.gc();
// BitmapFactory.decodeByteArray(data, 0,
// data.length, o);
// Bitmap bmpCompressed = rotateBitmap(bmp, 90, 320, 430);
Bitmap bmpCompressed = Bitmap.createScaledBitmap(bmp, 430, 320,
true);
bmp.recycle();
Utility.gc();
writeBmp(bmpCompressed);
bmpCompressed.recycle();
Utility.gc();
} catch (Exception e) {
Log.e(Constants.TAG, e.getMessage(), e);
} finally {
isImageCapture = true;
}
}
};
private Bitmap decodeFile(byte[] buffer) {
// Decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeStream(new ByteArrayInputStream(buffer), null, o);
// The new size we want to scale to
final int REQUIRED_SIZE = 70;
// 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 (true) {
if (width_tmp / 2 < REQUIRED_SIZE || height_tmp / 2 < REQUIRED_SIZE)
break;
width_tmp /= 2;
height_tmp /= 2;
scale *= 2;
}
// Decode with inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
return BitmapFactory.decodeStream(new ByteArrayInputStream(buffer),
null, o2);
}
how can i get rid from the above mention exception?
Use
Options.inSampleSize
// Decode image size
BitmapFactory.Options options = new BitmapFactory.Options();
//options.inJustDecodeBounds = true;
options.inSampleSize = 8;
BitmapFactory.decodeStream(new ByteArrayInputStream(buffer), null, options);
Take a look at this bug report:
http://code.google.com/p/android/issues/detail?id=8488
There's a known bug in Android relating to this error message, which doesn't seem to be accepted by Google. There are workarounds in the bug report if this is the problem you're having. I've used them to clear up similar issues.
You can try to do the scaling yourself using BitmapFactory.Options and BitmapFactory.decodeByteArray():
BitmapFactory.Options options = new BitmapFactory.Options;
options.inSampleSize = 4; // might try 8 also
BitmapFactory.decoderByteArray(data, 0, data.length, options);
There are also other options in BitmapFactory.Options to play around with.
You are probably running out of memory because you create a full decoded bitmap before you do the scaling.
Use less memory.
It definitely sounds like you have a memory leak somewhere if it works until the 10th picture is taken. Use the DDMS tools in Eclipse to track memory to try to see where it's happening.
I'm trying to make a basic application that displays an image from the camera, but I when I try to load the .jpg in from the sdcard with BitmapFactory.decodeFile, it returns null.
It doesn't give an out of memory error which I find strange, but the exact same code works fine on smaller images.
How does the generic gallery display huge pictures from the camera with so little memory?
Try to set the inSampleSize as shown in this example.
You can follow this amazing tutorial
http://developer.android.com/training/displaying-bitmaps/load-bitmap.html
Well after working a lot i found out that the problem was not with code but the ram size of emulator, editing avd and increasing ram size solves all problems and saves huges pics easily. thanks.
send:
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
BitmapFactory.decodeFile(filePath, o);
int REQUIRED_SIZE = 640;
int width_tmp = o.outWidth, height_tmp = o.outHeight;
int scale = 1;
while(true) {
if (width_tmp < REQUIRED_SIZE && height_tmp < REQUIRED_SIZE) break;
width_tmp /= 2;
height_tmp /= 2;
scale *= 2;
}
BitmapFactory.Options o2 = new BitmapFactory.Options();
o2.inSampleSize = scale;
Bitmap bitmap = BitmapFactory.decodeFile(filePath, o2);
ByteArrayOutputStream bs2 = new ByteArrayOutputStream();
bitmap.compress(Bitmap.CompressFormat.PNG, 90, bs2);
getIntent().putExtra("byte_picture", bs2.toByteArray());
recive:
Bitmap photo = BitmapFactory.decodeByteArray(data.getByteArrayExtra("byte_picture"),0,data.getByteArrayExtra("byte_picture").length);
Here is another solution that uses inSampleSize and dynamically determines the image resolution to use based on available memory:
http://bricolsoftconsulting.com/handling-large-images-on-android/