Android Activity之间的私有变量

时间:2013-12-19 09:53:02

标签: android variables android-activity nullpointerexception

我希望我的应用拍照(不是有意)。 我希望我的活动A.class拍照并给其他活动B.class我的图片的absolutePath()在意图的putExtra中调用B.Class。

这是我的代码

ANDROID CODE

public class A extends Activity  {
    private SurfaceHolder previewHolder=null;
    private Camera camera=null;
    private boolean inPreview=false;
    private boolean cameraConfigured=false;
    protected static final String TAG = "DEBUG_TAG";
    protected Throwable e;
    private File pictureFile;
    private String picturePath;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.capture);
        SurfaceView preview=(SurfaceView)findViewById(R.id.SurfaceView_camera);
        previewHolder=preview.getHolder();
        previewHolder.addCallback(surfaceCallback);
        TextView capturer = (TextView)findViewById(R.id.TextView_capturer);
        capturer.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                camera.takePicture(null, null, mPicture);
(L.88)          call_next_activity(v);
            }
        });
    }

    @Override
    public void onPause() {
        if (inPreview) {
            camera.stopPreview();
        }
        camera.release();
        camera=null;
        inPreview=false;
        super.onPause();
    }

    @Override
    public void onResume() {
        super.onResume();
        camera=Camera.open();
        startPreview();
    }

    private void initPreview(int width, int height) {
        if (camera!=null && previewHolder.getSurface()!=null) {
            try {
                camera.setPreviewDisplay(previewHolder);
            } catch (Throwable t) {
                Log.e("PreviewDemo-surfaceCallback", "Exception in setPreviewDisplay()", t);
                Toast.makeText(capture.this, t.getMessage(), Toast.LENGTH_LONG).show();
            }

            if (!cameraConfigured) {
                Camera.Parameters parameters=camera.getParameters();
                camera.setDisplayOrientation(90);
                parameters.set("rotation", 90);
                Camera.Size Previewsize=getBestPreviewSize(width, height, parameters);
                parameters.setPreviewSize(Previewsize.width, Previewsize.height);
                Camera.Size PictureSize = getBestPictureSize(width, height, parameters);
                parameters.setPictureSize(PictureSize.width, PictureSize.height);
                parameters.setJpegQuality(100);
                camera.setParameters(parameters);
                cameraConfigured=true;
            }
        }
    }

    private Camera.Size getBestPreviewSize(int width, int height, Camera.Parameters parameters) {
        Camera.Size result = null;
        for (Camera.Size size : parameters.getSupportedPreviewSizes()) {
            if (size.width<=width && size.height<=height) {
                if (result==null) {
                    result=size;
                } else {
                    int resultArea=result.width*result.height;
                    int newArea=size.width*size.height;
                    if (newArea>resultArea) {
                        result=size;
                    }
                }
            }
        }
        return(result);
    }

    private Camera.Size getBestPictureSize(int width, int height, Camera.Parameters parameters) {
        Camera.Size result = null;
        for (Camera.Size size : parameters.getSupportedPictureSizes()) {
            if (size.width>=width && size.height>=height) {
                if (result==null) {
                    result=size;
                } else {
                    int resultArea=result.width*result.height;
                    int newArea=size.width*size.height;
                    if (newArea>resultArea) {
                        result=size;
                    }
                }
            }
        }
        return(result);
    }

    private void startPreview() {
        if (cameraConfigured && camera!=null) {
            camera.startPreview();
            inPreview=true;
        }
    }

    private static File getOutputMediaFile(){
        String NewFolder = "/TEST";
        String StorageDirectory;
        StorageDirectory = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES).toString();
        File mediaStorageDir = new File(StorageDirectory + NewFolder);
        if (!mediaStorageDir.exists()){
            if (!mediaStorageDir.mkdirs()){
                Log.d("Jours de Chefs", "failed to create directory");
                return null;
            } else {
                mediaStorageDir.mkdir();
            }
        }

        String date = new SimpleDateFormat("yyyy-MM-dd_HH:mm:ss", Locale.FRANCE).format(new Date());

        File photo = new File(StorageDirectory + NewFolder, "Full_TEST_" + date + ".jpg");
        return photo;       
    }

    public void call_next_activity(View v) {

        // ----- HERE I HAVE EXCEPTION -----//
        // When i want to call picturePath or pictureFile, i get Exception :
        // NullPointerException
(L.246) if (!picturePath.isEmpty()) {
            Toast.makeText(capture.this, "CA MARCHE !!!!", Toast.LENGTH_LONG).show();
        } else {
            Toast.makeText(capture.this, "CA MARCHE PAS", Toast.LENGTH_LONG).show();
        }
    }

    private PictureCallback mPicture = new PictureCallback() {
        @Override
        public void onPictureTaken(byte[] data, Camera camera) {
            pictureFile = getOutputMediaFile();
            chemin_acces_photo = pictureFile.getPath();
            if (pictureFile == null){
                Log.d(TAG, "Error creating media file, check storage permissions: " + e.getMessage());
                return;
            }

            // ----- HERE TOAST SHOW ME RIGHT PATH ----- //
            // NO EXCEPTION, NO BUG, EVERYTHING IS OKAY
            Toast.makeText(capture.this, pictureFile.getAbsolutePath(), Toast.LENGTH_LONG).show();          

            try {
                FileOutputStream fos = new FileOutputStream(pictureFile);
                fos.write(data);
                fos.close();
            } catch (FileNotFoundException e) {
                Log.d(TAG, "File not found: " + e.getMessage());
            } catch (IOException e) {
                Log.d(TAG, "Error accessing file: " + e.getMessage());
            }
        }
    };

    SurfaceHolder.Callback surfaceCallback=new SurfaceHolder.Callback() {
        public void surfaceCreated(SurfaceHolder holder) {
            // no-op -- wait until surfaceChanged()
        }

        public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
            initPreview(width, height);
            startPreview();
        }

        public void surfaceDestroyed(SurfaceHolder holder) {
            // no-op
        }
    };  
}

一切都很好,但是当我想调用pictureFile.getAbsolutePath()时,我有这个错误:

LOGCAT代码

E/AndroidRuntime(14165): FATAL EXCEPTION: main
E/AndroidRuntime(14165): java.lang.NullPointerException
E/AndroidRuntime(14165):    at XXXXXXXXXXXXXX.capture.call_next_activity(capture.java:246)
E/AndroidRuntime(14165):    at XXXXXXXXXXXXXX.capture$3.onClick(capture.java:88)
E/AndroidRuntime(14165):    at android.view.View.performClick(View.java)
E/AndroidRuntime(14165):    at android.view.View$PerformClick.run(View.java)
E/AndroidRuntime(14165):    at android.os.Handler.handleCallback(Handler.java)
E/AndroidRuntime(14165):    at android.os.Handler.dispatchMessage(Handler.java)
E/AndroidRuntime(14165):    at android.os.Looper.loop(Looper.java)
E/AndroidRuntime(14165):    at android.app.ActivityThread.main(ActivityThread.java)
E/AndroidRuntime(14165):    at java.lang.reflect.Method.invokeNative(Native Method)
E/AndroidRuntime(14165):    at java.lang.reflect.Method.invoke(Method.java:511)
E/AndroidRuntime(14165):    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java)
E/AndroidRuntime(14165):    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java)
E/AndroidRuntime(14165):    at dalvik.system.NativeStart.main(Native Method)

有人能解释我为什么我的pictureFile == NULL?


编辑1 : Melquiades回答

  

这是因为camera.takePicture()是异步的。你有:

@Override
public void onClick(View v) {
    camera.takePicture(null, null, mPicture);
    call_next_activity(v); //<----------here picturePath is not yet initialised
}
  

因此,当您调用上面的takePicture()时,它会立即返回并且call_next_activity()是&gt;已调用,但picturePath尚未设置。

     

将你的call_next_activity()代码移动到你的mPicture()回调中,在设置了picturePath之后。

很好的解释,但现在我遇到了新的问题: 我的call_next_activity(v)代码是一个例子,在这个函数中,我想改变活动,然后我的真实代码如果:

ANDROID CODE

public void call_next_activity(v) {
    Intent intent = new Intent (this, next_activity.class);
    intent.putExtra("image_path", picturePath);
    startActivity(intent);
}

我无法将call_next_activity()代码放入mPicture回调中,因为我的这个不是我的视图,而是 Camera.PictureCallback(){}

有什么想法吗?


编辑2 答案 关注Melquiades Edit,只需删除call_next_activity(v)函数, 在onPictureTaken()函数的末尾写下call_next_activity代码:

public void onPictureTaken(byte[] data, Camera camera) {
    pictureFile = getOutputMediaFile();
    if (pictureFile == null){
        Log.d(TAG, "Error creating media file, check storage permissions: " + e.getMessage());
        return;
    }

    Toast.makeText(capture.this, pictureFile.getAbsolutePath(), Toast.LENGTH_LONG).show();          

    try {
        FileOutputStream fos = new FileOutputStream(pictureFile);
        fos.write(data);
        fos.close();
    } catch (FileNotFoundException e) {
        Log.d(TAG, "File not found: " + e.getMessage());
    } catch (IOException e) {
        Log.d(TAG, "Error accessing file: " + e.getMessage());
    }

    // ----- call_next_activity code here ----- //
    Intent intent = new Intent (getApplicationContext(), next_activity.class);
    intent.putExtra("image_path", pictureFile.getAbsolutePath());
    startActivity(intent);
}

PS:我删除了我的picturePath(string)变量,并通过pictureFile.getAbsolutePath()更改picturePath。

谢谢大家!

2 个答案:

答案 0 :(得分:1)

这是因为camera.takePicture()是异步的。你有:

@Override
public void onClick(View v) {
    camera.takePicture(null, null, mPicture);
    call_next_activity(v); //<----------here picturePath is not yet initialised
}

因此,当您调用上面的takePicture()时,它会立即返回并调用call_next_activity(),但还没有设置picturePath。

将你的call_next_activity()代码移动到你的mPicture()回调中,在设置了picturePath之后。

编辑:

声明

private Context context;
在你的A类中

,然后在setContentView()之后将它设置在onCreate()上:

context = this;

最后,用它来设定你的意图:

public void call_next_activity(v) {
    Intent intent = new Intent (context, next_activity.class);
    intent.putExtra("image_path", picturePath);
    startActivity(intent);
}

或者,您可以使用:

Intent intent = new Intent(getApplicationContext(), next_activity.class);

Intent intent = new Intent(A.this, next_activity.class);

答案 1 :(得分:0)

根据您的相关代码,我认为您收到java.lang.NullPointerException,因为您的String变量picturePath没有任何价值。请初始化一些值。

希望它能帮到你