开发者

Failed Binder Transaction when returning camera image

I get the Failed binder transaction error in the logcat when returning the image taken with the camera from the camera intent back to the parent intent (as a byte[] using putExtra). I don't understand why, its not like its a big bitmap or anything. It only happens when i take pictures with lots of light, because then the byte[] is bigger. The error occurs when leaving the camera intent. Does anyone see a mistake in my code?

Here is the code of the camera intent:

package example.imaging.ape;

import java.io.IOException;
import java.util.Iterator;
import java.util.Set;

import android.app.Activity;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.PixelFormat;
import android.hardware.Camera;
import android.hardware.Camera.AutoFocusCallback;
import android.os.Bundle;
import android.util.Log;
import android.view.MotionEvent;
import 开发者_如何转开发android.view.SurfaceHolder;
import android.view.SurfaceView;
import android.view.View;
import android.view.Window;
import android.view.WindowManager;
import android.view.View.OnTouchListener;

public class TakePicture extends Activity implements SurfaceHolder.Callback{
     Camera mCamera;
     Boolean mPreviewRunning = false;
     int imageLayoutHeight;
     int imageLayoutWidth;

     @Override
     public void onCreate(Bundle savedInstanceState) {
          super.onCreate(savedInstanceState);

          //setup camera surface
          getWindow().setFormat(PixelFormat.TRANSLUCENT);
          requestWindowFeature(Window.FEATURE_NO_TITLE);
          getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN);
          setContentView(R.layout.cameralayout);

          SurfaceView mSurfaceView = (SurfaceView) findViewById(R.id.hist_surface_camera);
          SurfaceHolder mSurfaceHolder = mSurfaceView.getHolder();
          mSurfaceHolder.addCallback(this);
          mSurfaceHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);
          Bundle extras = getIntent().getExtras();
          imageLayoutHeight = extras.getInt("layoutHeight");
          imageLayoutWidth = extras.getInt("layoutWidth");

          OnTouchListener touchListener = new View.OnTouchListener() {
               public boolean onTouch(View v, MotionEvent e) {

                    System.out.println("MAKING PICTURE");
                    mCamera.autoFocus(cb);             
                    return false;
               }
          };

          //setup touch listener
          mSurfaceView.setOnTouchListener(touchListener);

     }

     AutoFocusCallback cb = new AutoFocusCallback() {
          public void onAutoFocus(boolean success, Camera c) {
               c.takePicture(null, null, mPictureCallback);
          }   
     };

     Camera.PictureCallback mPictureCallback = new Camera.PictureCallback() {
          public void onPictureTaken(byte[] imageData, Camera c) {
               System.out.println("Picture taken, now returning");              
               Intent resultIntent = new Intent();
               resultIntent.putExtra("cameraImage", imageData);
               System.out.println("put Extra");
               setResult(Activity.RESULT_OK, resultIntent);
               finish();           
          }
     };

     //initialize camera
     public void surfaceCreated(SurfaceHolder holder) {
          mCamera = Camera.open();
     }

     public void surfaceChanged(SurfaceHolder holder, int format, int w, int h) {
          if (mPreviewRunning) {
               mCamera.stopPreview();
          }

          Camera.Parameters p = mCamera.getParameters();

          p.setPreviewSize(h, w);
          System.out.println("PreviewSize: " + h + "," + w);
          p.setPictureSize(h*3,w*3); // is around 1200x900
          p.set("rotation", 90);
          mCamera.setParameters(p);

          try {
               mCamera.setPreviewDisplay(holder);
          } catch (IOException e) {
               e.printStackTrace();
          }

          mCamera.startPreview();
          mPreviewRunning = true;
     }

     public void surfaceDestroyed(SurfaceHolder holder) {
          mCamera.stopPreview();
          mPreviewRunning = false;
          mCamera.release();
     }

}

And here is the code that calls the camera intent:

Intent intent = new Intent(Example.this, TakePicture.class);
intent.putExtra("layoutWidth",layoutWidth);
intent.putExtra("layoutHeight",layoutHeight);                   
startActivityForResult(intent,0);


For some reason, Android doesn't like when you try to pass the raw byte[] array or a Bitmap created from it. Some people have had success compressing the resulting Bitmap and passing that via Intent. I would recommend saving the image to a file first and sending it's path via the Intent.


During a remote procedure call, the arguments and the return value of the call are transferred as Parcel objects stored in the Binder transaction buffer. If the arguments or the return value are too large to fit in the transaction buffer, then the call will fail and TransactionTooLargeException will be thrown.

refer this link form android developer


Emulator loses memory load attributes in the intent, so the exception occurs

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜