首页 文章

2018年有效裁剪和缩放位图?

提问于
浏览
0

我们的产品中的位图存在问题 . 我们的目标是快速拍照并立即显示/裁剪 . 问题是 - 图像必须质量好,必须快速裁剪 . 我亲自尝试了下面的代码,它确实减少了大约2-3倍的内存使用量 . 不过,我们想知道更有效的方式 . 我们是否应始终在我们的自定义帧处理(使用Fotoapparat库,因为它能够有效显示全屏摄像机视图)和ImageViews之间传输imageArray []而不是实际位图? We are open to use Glide or any other tool to crop, or load bitmap if that would be more efficient. 我们目前用于从cameraView帧检索图像的代码(这减少了2-3次使用量):

ByteArrayOutputStream out = new ByteArrayOutputStream();
        YuvImage yuvImage = new YuvImage(data, ImageFormat.NV21, width, height, null);
        yuvImage.compressToJpeg(new Rect(0, 0, width, height), 50, out);
        byte[] imageBytes = out.toByteArray();
        BitmapFactory.Options options = new BitmapFactory.Options();
        options.inJustDecodeBounds = true;
        BitmapFactory.decodeByteArray(imageBytes, 0, imageBytes.length, options);
        options.inSampleSize = calculateInSampleSize(options, (int)(width/1.5),(int)(height/1.5));
        options.inJustDecodeBounds = false;
        Bitmap bitmap = BitmapFactory.decodeByteArray(imageBytes, 0, imageBytes.length, options);

然后我们使用下面的方法裁剪此Bitmap(这在2018年似乎效率低下):

resizedbitmap = Bitmap.createBitmap(original, 0,0,width, height);

还有,线程怎么样?我们应该使用AsyncTask,Executors或任何其他方式来裁剪/显示位图吗?我个人总是使用RxJava,但我们的核心产品必须尽可能轻量级:)我真的很感谢你的支持,今后一定会保持联系/自助 .

1 回答

  • 1

    替代品

    如果你在API级别10,你也可以使用 BitmapRegionDecoder ,它可以在一步中进行裁剪和下采样,可能是原生的 .

    作为一种完全不同的方法,您还可以尝试将 data 直接转换为 Bitmap ,然后使用 Canvas 将原始位图的某些部分绘制到新的裁剪版本上,通过Canvas的变换矩阵进行缩放 .

    质量

    图像必须质量好,必须快速裁剪 .

    压缩到 quality=50 的第一步,你丢失了很多信息 . 然后,当您创建新的位图时,您会进行向上扩展,这也会影响质量;在我看来,如果生成的图像实际上更小,裁剪才有意义 .

    效率

    然后我们用下面的方法裁剪这个Bitmap(这在2018年似乎效率低下)

    考虑一下:你真的需要Bitmap是确切的大小吗?它's probably much better to leave the Bitmap as the cropped size, have the smaller Bitmap in memory, upload the smaller Bitmap to the GPU and let the GPU rendering do the scaling. It'可能 ViewBitmap 大小不匹配,所以无论如何都会发生这种情况 .

    滑翔

    Glide几乎与你的代码(YUV位除外)的核心相同 . 请参阅Downsampler,区别在于它适用于许多输入源,格式和API级别,因此大小不同 .

    我们的核心产品必须尽可能轻量级:)

    包括图像加载库并强制用户包含它也违背了这一点 . 但与此同时,您是否真的想重新发明轮子并编写自己的图像加载库?例如,Glide有很多可以替换自定义行为的部分 .

    在我的应用程序中,我有一个摄像头 - >用户裁剪选择 - >裁剪较小的位图流程 . 我做了类似于你的事情,除了使用磁盘而不是 ByteArrayOutputStream ,因为输入可能是巨大的,它需要适合两次内存,这是无法保证的 .

相关问题