Compress Bitmap from Camera

折月煮酒 提交于 2019-12-05 01:04:30

问题


I need to send an image taken from the Camera over network. The image is too large to create a bitmap needed to use bitmap.compress(); It looks like the Gmail application can attach images from the camera while maintaining their large pixel size but with a great reduction their file size.

This won't work because I getBitmap() will return an Image to large to allocate and I don't want to sub sample it down to a smaller size.

    ByteArrayOutputStream baos = new ByteArrayOutputStream();
    getBitmap().compress(Bitmap.CompressFormat.JPEG, 70, baos);

Any ideas on how I can do the same without exceeding my total memory?

Update:

For anyone coming back to this thread I followed Phil's answer and used Apache MultiPartEntity to get the job done easily. (It handles streaming files from disk to network for you) http://hc.apache.org/httpcomponents-client-ga/httpmime/apidocs/org/apache/http/entity/mime/MultipartEntity.html


回答1:


As you haven't defined quite what 'send over the network' means here, it's difficult to give specific advice.

However, if you want to send a lossless image (or with less loss than has already occurred), I don't think you'll be able to compress much more, as JPEG already compresses. It uses lossy compression, so if you increase the JPEG compression, you lose details (although maybe not ones you'd notice, as it's based on frequencies not pixels)

If you just need to send over the network, then why not just open an InputStream, and spool data directly to the network?

Hope this helps - if you can provide more details, I'll update the answer.

Best wishes,

Phil Lello




回答2:


Probably it'll make a sense to use zipping before sending over network? InflaterInputStream on a sender side and DeflaterOutputStream on receiving side looks like workable combination.

ADDENDUM Try to use another approach:

FileOutputStream fos = new FileOutputStream(file); //intermediate file to store compressed image
InputStream is=this.getStream(imageUri); //image uri taken from camera
BitmapFactory.Options options=new BitmapFactory.Options();
options.inSampleSize=2; //try to decrease decoded image
options.inPurgeable=true; //purgeable to disk
Bitmap bitmap=BitmapFactory.decodeStream(is, null, options);
bitmap.compress(Bitmap.CompressFormat.JPEG, 70, fos); //compressed bitmap to file



回答3:


You can use the lower version of the image i.e. of resolution 512x384 (mini thumbnail). Check this answer on how to get the mini thumbnails.

The thumbnails are already compressed to 80%.




回答4:


I think that you can only do this in native code, where you can allocate a lot more memory. This means that you would need to use and compile a native library such as libjpeg, or some full-fledged package such as ImageMagick in order to support reading from various images formats.

With this, you wouldn't use the Bitmap class at all for compressing. Your native code would take care of both reading and writing image files. If you manage to compile the library, your native code shouldn't be more than a few dozens lines.

Unless you know C and have already played with JNI and the Android NDK, this isn't going to be easy. Especially, compiling third-party libraries for Android can be tricky at times.

But I believe that going native is the only solution here.




回答5:


Probably, pre-splitting the image; compressing each individual one and restoring at the end sounds logical.

Here are few attempts,

http://kalanir.blogspot.com/2010/02/how-to-split-image-into-chunks-java.html

And

http://www.anddev.org/multimedia-problems-f28/chunk-of-a-big-big-image-t6211.html



来源:https://stackoverflow.com/questions/5494372/compress-bitmap-from-camera

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!