Android - noise in saved images - android

My Android application loads images, does some processing and saves the processed images on the SD card. I save temporary files to the SD card instead of using buffers. For example, reading a background, scrolling the image, drawing an annotation, merging background and annotation in a saved temp file to use as next background, and so forth. Typical snippets:
bitmap = Bitmap.createBitmap(imageSizeX, imageSizeY, Bitmap.Config.ARGB_8888);
bitmap = BitmapFactory.decodeFile(path, options);
bitmap.compress(Bitmap.CompressFormat.JPEG, 100, output);
Everything works fine but in some cases the saved images have added noise similar to that described in this post:
Bitmap resizing and rotating: linear noise
The author of the post cited solved the problem by subsampling, but I don't wish to do that.
I have tried the solutions suggested here:
http://www.curious-creature.org/2010/12/08/bitmap-quality-banding-and-dithering/#more-1218
which if I understand correctly should be achieved by setting:
getWindow().setFormat(PixelFormat.TRANSLUCENT);
to force 32 bit.
which does not change much. Setting or not setting the dither flag does not seem to change much either. Any other ideas?

In answer to my own question:
The noise disappears, or at least the result is way better, by compressing to .png instead of .jpg
bitmap.compress(Bitmap.CompressFormat.PNG, 100, output);
The same sky which looks like a carpet texture in .jpg looks smooth and clean in .png. Since the difference is much more evident than the usual difference between the same image compressed to .png and .jpg, I guess it depends on the Android implementation. Setting explicitly TRANSLUCENT and DITHER does not make much difference one way or another.

Related

Saving Bitmap Image without shrinking width and height

What im trying to do is to save an edited bitmap that is composed by 2 bitmaps overlayed. My application allows the user to draw on top of a picture and save it.
My problem is: when i save the result image, it gets smaller, even setting the quality to 100. So, if the user saves and edit the image multiple times, the image will get smaller and smaller.
I save the bitmap with this:
result.compress(Bitmap.CompressFormat.JPEG, 100, fos);
I debugged the code, and at this point the width and height are fine, but after saving, the image shrinks.
I've researched for questions about this, but the ones i've found had no answers that could help me.
What i need is a way to save a bitmap without shrinking it, but i need it to be in image format, like JPG, PNG, etc.
Thanks in advance.
I guess is not at the time when you are saving the image, the issue is when you are editing the image (creating layers). Check that mechanism, maybe you are setting the image size there.

Saving shapes on top of large images

I'm creating somekind of 2D image editor in Android and I have the big problem of big files don't fit in memory.
I need to zoom in/out the image put some shapes and then save it.
My question is:
How can I load the image and save it without getting out of memory?
I've been reading about bitmapregiondecode and the sample technic but there's must be another solution. How can I save the image if I always use regiondecode?
The images need good detail quality because it's architectural images... and the lines must be well defined.
I'm new to this, help me please.
Note two things while dealing with images:
tempBitmap = Bitmap.createBitmap(bit);
clone the bitmap which you are using for zoom and other operations but wont use the original because it looses its clarity when you save;
when done with bitmap give
bit.recycle();
to release the memory space

Large source ImageView animation

What's the best image file format for Android in terms of memory? PNG is recommended for iOS as xCode does some magic with it.. Is it the same for Android?
I'm currently developing a big app with multiple animations going on (sliding in screens, fading etc etc). All works well so far! However I have noticed the view animation where the view contains an ImageView with a (quite large) PNG as the source is a bit laggy.
Obviously I can make the PNG smaller, but is there anything extra I can do to reduce the amount of memory the ImageView takes up/makes the animation smooth? I know PNG has a much larger file size than JPEG, but I can't see this being a problem, the JPEG or PNG (I assume) is eventually stored as an array of colours, so they would both take up the same memory. PNG is probably better for loading due to less cycles uncompressing. Again I only assume, my knowledge of image file formats is null.
Alternatively is there anything else causing the lag? Is the bitmap scaled to fit the view each onDraw() during the animation so should I scale the bitmap in code before giving it to the ImageView?
Thanks,
The formats supported by Android are: PNG, JPG and GIF (also 9.png).
The recomendated is PNG as said in dev guide
All of them are stored in memory as a Bitmap, so the most important thing is the color deph, like this:
BitmapFactory.Options options = new BitmapFactory.Options();
options.inPreferredConfig = Bitmap.Config.RGB_565;
Bitmap bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.icon, options);
More info: stackoverflow
and add (after honeycomb):
<application
android:largeHeap="true"
...
to your manifest file :=)
thanks to my dear friend :)

Is it possible to chop a bitmap to small pieces without loading the entire thing into memory?

I'm working on an image processing application for Android that recognizes music notation from pictures taken of music sheets.
I tried to load the entire image into a Bitmap using the BitmapFactory.decodeFile(imgPath) method, but because my phone doesn't have enough memory I get a "VM heap size" error. To work around this, I'd like to chop the full image into smaller pieces, but I'm not sure how to do that.
I also saw that it was possible to reduce the memory size of the Bitmap by using the inSampleSize property of the BitmapFactory.Option class, but if I do that I won't get the high resolution image I need for the music notation recognition process.
Is there anyway to handle this without going to NDK?
Android 2.3.3 has a new API called android.graphics.BitmapRegionDecoder that lets you do exactly what you want.
You would for instance do the following:
BitmapRegionDecoder decoder = BitmapRegionDecoder.newInstance(myStream, false);
Bitmap region = decoder.decodeRegion(new Rect(10, 10, 50, 50), null);
Easy :)
If it's from a camera the image will likely be jpeg format. You could use an external jpeg library - either in java or via the NDK, whatever you can find - to give you better control and load it a piece at a time. If you need it as an android.graphics.Bitmap then I suspect you will then need to re-encode the subimage as PNG or JPEG and pass it to BitmapFactory.decodeByteArray(). (If memory is a concern then do be sure to forget your references to the pieces of the bitmap promptly so that the garbage collector can run effectively.)
The same technique will also work if the input graphic is PNG format, or just about anything else provided you can find suitable decode code for it.
I think that by loading the image piecewise you are setting yourself an algorithmic challenge in deciding what parts of it you are really interested in the full detail of. I notice that BitmapFactory.Options includes the option to subsample, that might be useful if you want to analyse an overview of the image to decide what regions to load in full detail.
If you're dealing with JPEG images, see my answer to this question as well as this example.
I don't know how possible it is to get libijg on Android, but if it is, then it's worth a shot.

Android Textures appear unclear/fuzzy

I'm having trouble making my texture rendered correctly in my applications.
the artwork I use is precise and already scaled and the right size but when I render it on phone suddenly my texture are not as clear/precise as the original artwork and I can't figure out why.
has anybody had this issue before?
This is because android will compress all resources that are not placed inside /res/raw/
http://developer.android.com/guide/topics/graphics/2d-graphics.html
Note: Image resources placed in res/drawable/ may be automatically optimized with lossless image compression by the aapt tool. For example, a true-color PNG that does not require more than 256 colors may be converted to an 8-bit PNG with a color palette. This will result in an image of equal quality but which requires less memory. So be aware that the image binaries placed in this directory can change during the build. If you plan on reading an image as a bit stream in order to convert it to a bitmap, put your images in the res/raw/ folder instead, where they will not be optimized.
This might also happen if you use linear filtering in your texture, make sure that texture filters are GL_NEAREST for GL_MIN_FILTER and GL_MAG_FILTER.
Ok I finally figured it out
the problem I was having was coming from the default compatibility mode of android
I had to add this to my manifest

Categories

Resources