BitmapFactory 意外降低图像采样率
BitmapFactory downsamples unexpectedly image
在我的 android 应用程序中,我上传和下载 JPEG 图片。对于某些图像 BitmapFactory
对下载的图像进行下采样,我不明白为什么以及如何阻止它这样做。
我在上传和下载图像时记录位图对象大小:
Uploading image with size 3840x2160
Opening received image of size 2601584B degradation 0 decoded 384x216
所以这里我的图片宽和高经过BitmapFactory
解码后除以10。
对于另一张图片,我从 3480x4640 变为 217x290,所以除以 16。我首先认为这可能是由图像 dpi 元数据引起的,所以我在打开图像时尝试使用以下代码强制它:
BitmapFactory.Options opts = new BitmapFactory.Options();
opts.inSampleSize = 1 << degradation;
opts.inScaled = false;
opts.inDensity = 1;
opts.inTargetDensity = 1;
opts.inScreenDensity = 1;
final Bitmap original = BitmapFactory.decodeByteArray(data, 0, data.length, opts);
Log.d(Tags.IMAGES, "Opening received image of size " + data.length + " degradation " + degradation + " decoded " + original.getWidth() + "x" + original.getHeight());
如您所见,我给出的字节数 (2MB) BitmapFactory
与大图像一致,而不是与 300x200px 图像一致。所以我的上传代码和下载代码是正确的我在解码之前有正确的数据。
我强制所有密度避免缩放并且还禁用缩放并且我的样本大小为 1 因为我的降级为 0 所以我不强制任何子采样。我仍然以一个非常小的图像结束。 BitmapFactory.decodeByteArray
快速调用本机代码,所以我无法真正调试它。
我试过了:
- 将
BitmapFactory.Options
对象中的所有密度设置为 0 但这并没有改变任何事情。
- 上传前设置位图的密度,没有效果(原来这两张二次采样图的密度是420)
- 在完全解码之前读取位图的大小(通过justDecodeBounds),这样返回的大小也太小了。
- 没有将任何选项传递给
decodeByteArray
方法,图像仍然太小。
好的,经过更多调查,我发现了问题,这是由于代码的另一部分造成的。由于应用程序中的竞争条件,我同时将图像和它的缩影写入同一个文件。所以我最终得到了一个大图像文件,但它的开头被一个小图像覆盖了,这就是 BitmapFactory 创建这个小图像的原因。
抱歉,问题不在代码的这一部分,所以您找不到它。
在我的 android 应用程序中,我上传和下载 JPEG 图片。对于某些图像 BitmapFactory
对下载的图像进行下采样,我不明白为什么以及如何阻止它这样做。
我在上传和下载图像时记录位图对象大小:
Uploading image with size 3840x2160
Opening received image of size 2601584B degradation 0 decoded 384x216
所以这里我的图片宽和高经过BitmapFactory
解码后除以10。
对于另一张图片,我从 3480x4640 变为 217x290,所以除以 16。我首先认为这可能是由图像 dpi 元数据引起的,所以我在打开图像时尝试使用以下代码强制它:
BitmapFactory.Options opts = new BitmapFactory.Options();
opts.inSampleSize = 1 << degradation;
opts.inScaled = false;
opts.inDensity = 1;
opts.inTargetDensity = 1;
opts.inScreenDensity = 1;
final Bitmap original = BitmapFactory.decodeByteArray(data, 0, data.length, opts);
Log.d(Tags.IMAGES, "Opening received image of size " + data.length + " degradation " + degradation + " decoded " + original.getWidth() + "x" + original.getHeight());
如您所见,我给出的字节数 (2MB) BitmapFactory
与大图像一致,而不是与 300x200px 图像一致。所以我的上传代码和下载代码是正确的我在解码之前有正确的数据。
我强制所有密度避免缩放并且还禁用缩放并且我的样本大小为 1 因为我的降级为 0 所以我不强制任何子采样。我仍然以一个非常小的图像结束。 BitmapFactory.decodeByteArray
快速调用本机代码,所以我无法真正调试它。
我试过了:
- 将
BitmapFactory.Options
对象中的所有密度设置为 0 但这并没有改变任何事情。 - 上传前设置位图的密度,没有效果(原来这两张二次采样图的密度是420)
- 在完全解码之前读取位图的大小(通过justDecodeBounds),这样返回的大小也太小了。
- 没有将任何选项传递给
decodeByteArray
方法,图像仍然太小。
好的,经过更多调查,我发现了问题,这是由于代码的另一部分造成的。由于应用程序中的竞争条件,我同时将图像和它的缩影写入同一个文件。所以我最终得到了一个大图像文件,但它的开头被一个小图像覆盖了,这就是 BitmapFactory 创建这个小图像的原因。 抱歉,问题不在代码的这一部分,所以您找不到它。