如何使用 ByteBuffer 在本机内存中保存位图图像并恢复它
How to save Bitmap image in Native memory using ByteBuffer and recover it
我正在从相机获取直接流,我需要将 Bitmap
保存到 ByteBuffer
中并恢复它。这是我的代码:
YuvImage yuv = new YuvImage(data.getExtractImageData(), previewFormat, width, height, null);
ByteArrayOutputStream out = new ByteArrayOutputStream();
yuv.compressToJpeg(new Rect(0, 0, width, height), 50, out);
byte[] bytes = out.toByteArray();
Bitmap image = BitmapFactory.decodeByteArray(bytes, 0, bytes.length);
Bitmap imageResult = RotateImage(image, 4 - rotation);
imageResult = cropBitmap(imageResult, data.getRect());
int nBytes = imageResult.getByteCount();
ByteBuffer buffer = ByteBuffer.allocateDirect(nBytes);
imageResult.copyPixelsToBuffer(buffer);
return buffer.array();
将 byte[]
转换回 Bitmap
的代码:
Bitmap bitmap = BitmapFactory.decodeByteArray(images.getImage(), 0, images.getImage().length);
但是,bitmap
转换后为Null...
知道哪里出了问题吗?
澄清一下:我需要将 byte[] image
保存在本机内存中,这就是我执行 ByteBuffer.allocateDirect
的原因。我需要在特定点裁剪图像,这就是为什么我需要 bitmap
.
decodeByteArray() decodes a compressed image (e.g. a JPEG or PNG) stored in a byte array. However copyPixelsToBuffer() 将 Bitmap 的内容复制到字节缓冲区 "as is"(即未压缩),因此无法通过 decodeByteArray() 进行解码。
如果您不想重新编码您的位图,您可以像现在一样使用 copyPixelsToBuffer(),并将您的第二个代码块更改为使用 copyPixelsFromBuffer() 而不是 decodeByteArray()。
Bitmap bitmap = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
bitmap.copyPixelsFromBuffer(ByteBuffer.wrap(images.getImage()));
您需要保存宽度和高度。还要确保 Bitmap.Config
相同。
基本上,如果您将其保存为压缩文件,则必须将其加载为压缩文件,如果您将其未压缩文件保存,则必须将其未压缩文件加载。
分配缓冲区时还应设置字节顺序,因为Java是大端,因此缓冲区默认是大端,android是小端,底层cpu 体系结构可能会有所不同,但大多是小端 wrt android:
buffer.order( ByteOrder.nativeOrder() );
我正在从相机获取直接流,我需要将 Bitmap
保存到 ByteBuffer
中并恢复它。这是我的代码:
YuvImage yuv = new YuvImage(data.getExtractImageData(), previewFormat, width, height, null);
ByteArrayOutputStream out = new ByteArrayOutputStream();
yuv.compressToJpeg(new Rect(0, 0, width, height), 50, out);
byte[] bytes = out.toByteArray();
Bitmap image = BitmapFactory.decodeByteArray(bytes, 0, bytes.length);
Bitmap imageResult = RotateImage(image, 4 - rotation);
imageResult = cropBitmap(imageResult, data.getRect());
int nBytes = imageResult.getByteCount();
ByteBuffer buffer = ByteBuffer.allocateDirect(nBytes);
imageResult.copyPixelsToBuffer(buffer);
return buffer.array();
将 byte[]
转换回 Bitmap
的代码:
Bitmap bitmap = BitmapFactory.decodeByteArray(images.getImage(), 0, images.getImage().length);
但是,bitmap
转换后为Null...
知道哪里出了问题吗?
澄清一下:我需要将 byte[] image
保存在本机内存中,这就是我执行 ByteBuffer.allocateDirect
的原因。我需要在特定点裁剪图像,这就是为什么我需要 bitmap
.
decodeByteArray() decodes a compressed image (e.g. a JPEG or PNG) stored in a byte array. However copyPixelsToBuffer() 将 Bitmap 的内容复制到字节缓冲区 "as is"(即未压缩),因此无法通过 decodeByteArray() 进行解码。
如果您不想重新编码您的位图,您可以像现在一样使用 copyPixelsToBuffer(),并将您的第二个代码块更改为使用 copyPixelsFromBuffer() 而不是 decodeByteArray()。
Bitmap bitmap = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
bitmap.copyPixelsFromBuffer(ByteBuffer.wrap(images.getImage()));
您需要保存宽度和高度。还要确保 Bitmap.Config
相同。
基本上,如果您将其保存为压缩文件,则必须将其加载为压缩文件,如果您将其未压缩文件保存,则必须将其未压缩文件加载。
分配缓冲区时还应设置字节顺序,因为Java是大端,因此缓冲区默认是大端,android是小端,底层cpu 体系结构可能会有所不同,但大多是小端 wrt android:
buffer.order( ByteOrder.nativeOrder() );