我的虚拟杂志中有数百张图片。图像为1241* 1754
像素,分辨率为150 pixels/inch
。滑动到这些页面的3/4
后,我得到了内存不足错误,如日志中所示。
12-04 10:20:50.781: E/AndroidRuntime(3236): java.lang.OutOfMemoryError
12-04 10:20:50.781: E/AndroidRuntime(3236): at android.graphics.BitmapFactory.nativeDecodeAsset(Native Method)
12-04 10:20:50.781: E/AndroidRuntime(3236): at android.graphics.BitmapFactory.decodeStream(BitmapFactory.java:572)
12-04 10:20:50.781: E/AndroidRuntime(3236): at android.graphics.BitmapFactory.decodeResourceStream(BitmapFactory.java:440)
12-04 10:20:50.781: E/AndroidRuntime(3236): at android.graphics.drawable.Drawable.createFromResourceStream(Drawable.java:773)
12-04 10:20:50.781: E/AndroidRuntime(3236): at android.content.res.Resources.loadDrawable(Resources.java:1974)
12-04 10:20:50.781: E/AndroidRuntime(3236): at android.content.res.Resources.getDrawable(Resources.java:677)
12-04 10:20:50.781: E/AndroidRuntime(3236): at fi.harism.curl.LPMagHome$PageProvider.loadBitmap(LPMagHome.java:192)
12-04 10:20:50.781: E/AndroidRuntime(3236): at fi.harism.curl.LPMagHome$PageProvider.updatePage(LPMagHome.java:266)
12-04 10:20:50.781: E/AndroidRuntime(3236): at fi.harism.curl.CurlView.updatePage(CurlView.java:713)
12-04 10:20:50.781: E/AndroidRuntime(3236): at fi.harism.curl.CurlView.startCurl(CurlView.java:554)
12-04 10:20:50.781: E/AndroidRuntime(3236): at fi.harism.curl.CurlView.onTouch(CurlView.java:280)
12-04 10:20:50.781: E/AndroidRuntime(3236): at android.view.View.dispatchTouchEvent(View.java:5583)
12-04 10:20:50.781: E/AndroidRuntime(3236): at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:1968)
12-04 10:20:50.781: E/AndroidRuntime(3236): at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:1695)
12-04 10:20:50.781: E/AndroidRuntime(3236): at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:1968)
12-04 10:20:50.781: E/AndroidRuntime(3236): at android.view.ViewGroup.dispatchTouchEvent(ViewGroup.java:1695)
12-04 10:20:50.781: E/AndroidRuntime(3236): at android.view.ViewGroup.dispatchTransformedTouchEvent(ViewGroup.java:1968)
*
以下是我加载位图图像的工作的一部分。有人可以帮助我如何处理这个内存不足的错误,通过一些研究我看到了这个博客java.lang.OutOfMemoryError BitmapFactory.nativeDecodeAsset(),但我无法将其应用于下面的方法loadBitmap。
private Bitmap loadBitmap(int width, int height, int index) {
Bitmap b = Bitmap.createBitmap(width, height,
Bitmap.Config.ARGB_8888);
b.eraseColor(0xFFFFFFFF);
c = new Canvas(b);
d = getResources().getDrawable(mBitmapIds[index]);
System.out.println("canvas width: "+c.getWidth());
int margin = 3;//7
int border = 3;//2
Rect r = new Rect(margin, margin, width - margin, height - margin);
int imageWidth = r.width() - (border * 2);
int imageHeight = imageWidth * d.getIntrinsicHeight()
/ d.getIntrinsicWidth();
if (imageHeight > r.height() - (border * 2)) {
imageHeight = r.height() - (border * 2);
imageWidth = imageHeight * d.getIntrinsicWidth()
/ d.getIntrinsicHeight();
}
Log.d("TAG", String.valueOf(imageHeight));
if (lp.getWindow().getWindowManager().getDefaultDisplay()
.getOrientation() == ActivityInfo.SCREEN_ORIENTATION_PORTRAIT) {
// portrait mode
r.left += ((r.width() - imageWidth) / 2) - border;
r.right = r.left + imageWidth + border + border;
} else if (lp.getWindow().getWindowManager().getDefaultDisplay()
.getOrientation() == ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE) {
// landscape
r.left += ((r.width() - imageWidth)) - border-122;
r.right = r.left + imageWidth + border + border+122;
}
r.top += ((r.height() - imageHeight) / 2) - border;
r.bottom = r.top + imageHeight + border + border;
Paint p = new Paint();
p.setColor(0xFFC0C0C0);
c.drawRect(r, p);
r.left += border;
r.right -= border;
r.top += border;
r.bottom -= border;
d.setBounds(r);
d.draw(c);
return b;
}*
更新:使用此方法滑动时页面会更新
@覆盖 public void updatePage(CurlPage page,int width,int height,int index){
DisplayMetrics displaymetrics = new DisplayMetrics();
getWindowManager().getDefaultDisplay().getMetrics(displaymetrics);
int wwidth = displaymetrics.widthPixels;
int hheight = displaymetrics.heightPixels;
if(wwidth > hheight){
System.out.println("index "+(index*2));
System.out.println("index2 "+(index*2)+1);
System.out.println("case landscape orientation...");
if (index >0){
front = loadBitmap(width, height, (index*2));
back = loadBitmap(width, height, (index*2)+1);
}else {
front = loadBitmap(width, height, (index));
back = loadBitmap(width, height, (index));
}
Matrix matrix = new Matrix();
matrix.preScale(-1.0f, 1.0f);
Bitmap mirroredBitmap = Bitmap.createBitmap(back, 0, 0, back.getWidth(), back.getHeight(), matrix, false);
page.setTexture(front, CurlPage.SIDE_FRONT);
page.setTexture(mirroredBitmap, CurlPage.SIDE_BACK);
} else {
System.out.println("case portrait orientation...");
Bitmap front = loadBitmap(width, height, index);
Bitmap back = loadBitmap(width, height, index);
System.out.println( "MyActivity.onCreate debug message "+String.valueOf(index));
page.setTexture(front, CurlPage.SIDE_FRONT);
page.setTexture(back, CurlPage.SIDE_BACK);
}
}
}
答案 0 :(得分:2)
你正在泄露记忆。通过删除对它的所有引用来检查您是否释放了内存以避免此问题。另外请记住,某些设备没有太多内存,因此您需要使用更少的内存。
另请参阅我对how to find memory leaks的回答。
答案 1 :(得分:2)
您可能需要调整位图的大小。我也遇到了这个问题并通过以下代码解决了这个问题:
public static Bitmap getResizedBitmap(Bitmap image, int newHeight, int newWidth) {
int width = image.getWidth();
int height = image.getHeight();
float scaleWidth = ((float) newWidth) / width;
float scaleHeight = ((float) newHeight) / height;
// create a matrix for the manipulation
Matrix matrix = new Matrix();
// resize the bit map
matrix.postScale(scaleWidth, scaleHeight);
// recreate the new Bitmap
Bitmap resizedBitmap = Bitmap.createBitmap(image, 0, 0, width, height,
matrix, false);
return resizedBitmap;
}
答案 2 :(得分:1)
在玩大量图片时这是一个普遍的问题。尼基塔我建议你使用一个api库,负责加载图像,清除图像不在时的缓存和其他必要的东西。 Here是github项目的链接,下载jar并将其添加到项目的libs文件夹中。
配置图像检查this。
答案 3 :(得分:1)
可能有内存泄漏。如果该位图没有进一步使用,您可以调用bitmap.recycle()来节省内存。此外,您可以尝试缩小位图:
Bitmap scale_down = Bitmap.createScaledBitmap(original_bmp, original_bmp.getWidth()/2, original_bmp.getHeight()/2, true);
答案 4 :(得分:0)
我没有看到你的所有代码,所以我只能假设你将所有图像都放入内存中。我可以把屏幕上显示的图像放到内存中,而另一个图像从内存释放,这种方式可以实现并减少占用的内存。请阅读:Strange out of memory issue while loading an image to a Bitmap object
我很抱歉我的英语不好!