【发布时间】:2019-01-10 02:27:37
【问题描述】:
在我的 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());
如您所见,我给BitmapFactory 的字节数(2MB)与大图像一致,而不是与 300x200px 图像一致。所以我的上传代码和下载代码是正确的,我在解码之前有正确的数据。
我强制所有密度以避免缩放,并且还禁用了缩放,并且我的样本大小为 1,因为我的降级为 0,因此我不强制进行任何二次采样。我仍然以一个非常小的图像结束。而BitmapFactory.decodeByteArray 快速调用本机代码,所以我无法真正调试它。
我试过了:
- 将
BitmapFactory.Options对象中的所有密度设置为0,但这并没有改变任何事情。 - 上传前设置位图的密度,没有效果(原来这两张二次采样的图像密度为420)。
- 在完全解码之前读取位图的大小(通过justDecodeBounds),这种方式返回的大小也太小了。
- 没有将任何选项传递给
decodeByteArray方法,图像仍然太小。
【问题讨论】:
-
在没有 BitmapFactory.Options 的情况下打开图像不会对其进行下采样。如果要将图像拟合到 ImageView 中,则应检查缩放类型。我打开 4k 图像并将其设置为可缩放 ImageView 的资源,它们不会被下采样。
-
您也可以使用 Glide、Picasso 或任何其他图片库打开图片。您可以毫不费力地获得完整尺寸的图像。以前用毕加索,现在用Glide打开图片,设置成ImageView
-
@Thracian 谢谢,但我只是尝试不使用选项参数并得到相同的结果。我不会用我所有的图像进行复制,所以这些下采样图像可能有一些特别之处
-
这很奇怪。您是否尝试过使用任何其他图片或图库应用打开这些图片?
-
@Thracian 当然,它们在 Gimp 中打开得很好,它给出了预期的像素大小。
标签: android android-bitmap bitmapfactory