0

我知道这一定是 SO 被问到最多的事情之一,但其他答案都没有给我一个解决方案。但是从阅读其他答案看来,我需要重新设计应用程序的工作方式。

就像这样,我们有一个 ScrollView,它会膨胀一些视图。在这种情况下不能使用 ListView,因为要按照我们想要的方式运行,就需要扩展 ListView,这是我们不想做的事情(尽管这似乎是我们当前方式的唯一解决方案显示项目,因为这个 OOM 异常)。列表每行可以有很多列,屏幕越大,它的列就越多。

每个膨胀视图都有一个布局,显示来自数据库的一些信息,包括一张图片。这张图片是通过字节数组存储的。这是使用设备相机拍摄的任何照片。目前每张照片(字节数组)占用 800kb 到 1mb,这对我来说似乎很多。现在该列表有 30 多个项目。一直拍到OOM,一共拍了6张(偶尔7张)。那将是 8mb-9mb 的数据。每次我去其他 Activity,然后回到 ScrollView 所在的 Activity 时,都需要重新填充列表。

这是 PopulateList 方法的片段:

if (item.getImg() != null) {

            if (App.debug) {

                Log.d(TAG, "Setting bmp.");
            }

            Bitmap bmp = App.byteArrayToBmp(item.getImg());

            imgV.setImageBitmap(bmp);
        }

每个膨胀视图都会打开一个“高级对话框”,其中包含其他信息。也许图像可能会出现在列表中(这意味着只有 1 个位图,因为每个膨胀的视图都共享相同的高级对话框)。或者我可以扩展 ListView 并从它的回收方法中受益(这不是一个好的解决方案,因为我会考虑屏幕上可以有 6 个以上的项目)。困扰我的另一件事是每张图片都有 800kb。对于 128x128 来说似乎很多。

这是尺寸的设置:

cameraParams.setPictureSize(App.pxToDpi(128), App.pxToDpi(128));
cameraParams.setPictureFormat(PixelFormat.JPEG);

camera.setParameters(cameraParams);

public static int pxToDpi(int px) {

    final int scale = app.getApplicationContext().getResources().getDisplayMetrics().densityDpi;

    int pixels = (int) px * (scale / 160);

    return pixels;
}

那么,您认为保留我的应用程序的当前模型是否可以解决我的问题,还是我需要重新制定?

编辑:位图方法:

public static Bitmap byteArrayToBmp(byte[] byteArray) {

    Bitmap img = null;

    BitmapFactory.Options opts = new BitmapFactory.Options();

    opts.inSampleSize = 2;

    img = BitmapFactory.decodeByteArray(byteArray, 0, byteArray.length, opts);

    return img;
}
4

1 回答 1

2

您可能想查看官方Android 培训文档,它们刚刚更新:

通过课程查看有效地显示位图:有效地加载大型位图

基本上,您可以使用 sampleSize 解码图像以将其解码为您想要的宽度和高度:

public static int calculateInSampleSize(
            BitmapFactory.Options options, int reqWidth, int reqHeight) {
    // Raw height and width of image
    final int height = options.outHeight;
    final int width = options.outWidth;
    int inSampleSize = 1;

    if (height > reqHeight || width > reqWidth) {
        if (width > height) {
            inSampleSize = Math.round((float)height / (float)reqHeight);
        } else {
            inSampleSize = Math.round((float)width / (float)reqWidth);
        }
    }
    return inSampleSize;
}

在上面的链接中进行了非常详细的解释

于 2012-06-14T21:29:21.450 回答