拍照并使用图像 - 内存不足错误

时间:2013-08-27 12:32:40

标签: java android image bitmap camera

好的,我正在开发一个使用相机拍摄照片的Android应用程序,然后在ImageView中使用该图像。 我遇到的问题是,当我尝试加载图片时,我不断收到java.lang.OutOfMemoryError异常。

启动相机意图的代码:

button.setOnClickListener(new OnClickListener() {
    @Override
    public void onClick(View arg0) {
        AlertDialog.Builder builder = new AlertDialog.Builder(AddVehicleActivity.this);
        builder.setTitle("Select A Method");
        builder.setItems(R.array.array_PhotoMethods, new DialogInterface.OnClickListener() {
            @Override
            public void onClick(DialogInterface dialog, int which) {
                switch(which) {
                case 0 :
                    IMAGE_LOCATION = Utility.setFileName(_session); //Returns image path
                    Intent cameraIntent = new Intent(android.provider.MediaStore.ACTION_IMAGE_CAPTURE);
                    cameraIntent.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(new File(IMAGE_LOCATION)));
                    startActivityForResult(cameraIntent, CAMERA_PIC_REQUEST);
                    break;
                }
            }
        });
        builder.show();
    }
});

根据我的理解,这将允许以相机的全分辨率保存图像,我可以通过图库中的图像细节进行确认。使用我的三星SIII,我的图像大约是3.3MB。因此,我可以使用相机并将我使用相机拍摄的图像存储到我指定的路径中。尝试使用图像时会出现问题。

要加载图像,我使用以下内容:

public static Bitmap Shrink(String file, int width, int height) {
    BitmapFactory.Options bmpFactoryOptions = new BitmapFactory.Options();
    int heightRatio = (int)Math.ceil(bmpFactoryOptions.outHeight/(float)height);
    int widthRatio = (int)Math.ceil(bmpFactoryOptions.outWidth/(float)width);
    if (heightRatio > 1 || widthRatio > 1) {
        bmpFactoryOptions.inSampleSize = (heightRatio > widthRatio) ? heightRatio : widthRatio;
    }
    return BitmapFactory.decodeFile(file, bmpFactoryOptions);
}

我已经用几种不同的方式重写了这个函数,并发现有时,我在调用BitmapFactory.decodeFile时会出现内存错误

我的堆栈跟踪如下所示:

E/dalvikvm-heap(8355): Out of memory on a 31961104-byte allocation.
java.lang.OutOfMemoryError
    at android.graphics.BitmapFactory.nativeDecodeStream(Native Method)
    at android.graphics.BitmapFactory.decodeStream(BitmapFactory.java:619)
    at android.graphics.BitmapFactory.decodeFile(BitmapFactory.java:385)
    at com.autopilot.com.objects.Images.Shrink(Images.java:191)
    at com.autopilot.com.adapters.ImageAdapter.getView(ImageAdapter.java:90)
    at android.widget.AbsListView.obtainView(AbsListView.java:2437)
    at android.widget.GridView.onMeasure(GridView.java:1030)
    at android.view.View.measure(View.java:15395)
    at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:4826)
    at android.widget.LinearLayout.measureChildBeforeLayout(LinearLayout.java:1396)
    at android.widget.LinearLayout.measureHorizontal(LinearLayout.java:1038)
    at android.widget.LinearLayout.onMeasure(LinearLayout.java:576)
    at android.view.View.measure(View.java:15395)
    at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:4826)
    at android.widget.LinearLayout.measureChildBeforeLayout(LinearLayout.java:1396)
    at android.widget.LinearLayout.measureHorizontal(LinearLayout.java:1038)
    at android.widget.LinearLayout.onMeasure(LinearLayout.java:576)
    at android.view.View.measure(View.java:15395)
    at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:4826)
    at android.widget.LinearLayout.forceUniformWidth(LinearLayout.java:926)
    at android.widget.LinearLayout.measureVertical(LinearLayout.java:906)
    at android.widget.LinearLayout.onMeasure(LinearLayout.java:574)
    at android.view.View.measure(View.java:15395)
    at android.widget.RelativeLayout.measureChildHorizontal(RelativeLayout.java:617)
    at android.widget.RelativeLayout.onMeasure(RelativeLayout.java:399)
    at android.view.View.measure(View.java:15395)
    at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:4826)
    at android.widget.FrameLayout.onMeasure(FrameLayout.java:310)
    at android.view.View.measure(View.java:15395)
    at android.widget.LinearLayout.measureVertical(LinearLayout.java:833)
    at android.widget.LinearLayout.onMeasure(LinearLayout.java:574)
    at android.view.View.measure(View.java:15395)
    at android.view.ViewGroup.measureChildWithMargins(ViewGroup.java:4826)
    at android.widget.FrameLayout.onMeasure(FrameLayout.java:310)
    at com.android.internal.policy.impl.PhoneWindow$DecorView.onMeasure(PhoneWindow.java:2362)
    at android.view.View.measure(View.java:15395)
    at android.view.ViewRootImpl.performMeasure(ViewRootImpl.java:1985)
    at android.view.ViewRootImpl.measureHierarchy(ViewRootImpl.java:1226)
    at android.view.ViewRootImpl.performTraversals(ViewRootImpl.java:1399)
    at android.view.ViewRootImpl.doTraversal(ViewRootImpl.java:1119)
    at android.view.ViewRootImpl$TraversalRunnable.run(ViewRootImpl.java:4553)
    at android.view.Choreographer$CallbackRecord.run(Choreographer.java:725)
    at android.view.Choreographer.doCallbacks(Choreographer.java:555)
    at android.view.Choreographer.doFrame(Choreographer.java:525)
    at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:711)
    at android.os.Handler.handleCallback(Handler.java:615)
    at android.os.Handler.dispatchMessage(Handler.java:92)
    at android.os.Looper.loop(Looper.java:137)
    at android.app.ActivityThread.main(ActivityThread.java:4950)
    at java.lang.reflect.Method.invokeNative(Native Method)
    at java.lang.reflect.Method.invoke(Method.java:511)
    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1004)
    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:771)
    at dalvik.system.NativeStart.main(Native Method)

从跟踪此操作开始,只要加载原始位图,就会发生内存异常。我找不到设置保存图像大小的方法,当我尝试从意图附加内容中保存位图时,它通常不够大,通常是指甲大小。

非常感谢任何帮助!

1 个答案:

答案 0 :(得分:1)

好的,我找到了答案,谢谢你sunil!

public static Bitmap Shrink(String file, int width, int height) {
    final BitmapFactory.Options options = new BitmapFactory.Options();
    options.inJustDecodeBounds = true;
    BitmapFactory.decodeFile(file, options);
    options.inSampleSize = calcSize(options, width, height);
    options.inJustDecodeBounds = false;
    Bitmap bmp = BitmapFactory.decodeFile(file, options);
    return bmp;
}

public static int calcSize(BitmapFactory.Options options, int width, int height) {
    final int uHeight = options.outHeight;
    final int uWidth = options.outWidth;
    int inSampleSize = 1;
    if (uHeight > height || uWidth > width) {
        if (uWidth > uHeight) {
            inSampleSize = Math.round((float) uHeight / (float) height);
        } else {
            inSampleSize = Math.round((float) uWidth / (float) width);
        }
    }
    return inSampleSize;
}