Reputation: 241
Hello I was just writing a little Android application which takes an image from the camera und was wondering what the camera Parameter Method setPictureFormat() actually does and what influence it has. As far as I know camera.takePicture() actually only provides data in the JPEG callback. So I would think that data array that arrives in onPictureTaken() is a JPEG data anyway? So why should I set this parameter to PixelFormat.RGB_565 for example? And is there any way to directly interpret the data array directly in onPictureTaken() whithout for example BitmapFactory.decodeByteArray? What I find rather strange is that I have an resulting Image with a resolution of 2448*3264 corresponds to a total of 7990272 pixels. However the underlying data aray that created this image only has a length of about 2000000 pixel. If anyone could clarify that for me it would be much appreciated.
Upvotes: 2
Views: 3982
Reputation: 63303
The setPictureFormat()
method applies the pixel format for the bytes arrays returned in the raw and postView callbacks that you pass to takePicture()
. As the docs mention, these callbacks MAY not even happen on hardware that doesn't have the buffers to support it, but if they do happen, the data will be formatted according to this setting. You are correct that the JPEG callback passes data back already compressed into the JPEG format.
In your example, the size of the raw byte array would vary based on the selected pixel format. You are right, that 2448 * 3264 = 7,990,272 pixels, but each pixel is represented by a number of bytes in the array. For example, formats like NV16 or RGB_565 have 16 bits (2 bytes) to represent each pixel. This means the actual raw byte array length would be 15,980,554 (~15MB), which is a very large amount of data to store in memory at once (that's almost the entire heap size of the original G1). This is why not all devices buffer and return the raw image data.
When you inspect the length of the data returned in the JPEG callback, you are looking at the compressed JPEG image data, which is no longer a raw bitmapped image. For this reason, the result will be much smaller. If you were to inflate this JPEG image data back into a Bitmap (using BitmapFactory, for instance) the size would balloon again. Keep this in mind, as an image that size, loaded into memory as an ARGB_8888 Bitmap (4 bytes per pixel) would consume ~32MB. That's an easy road towards an OutOfMemoryException in your code.
Hope that Helps!
Upvotes: 10