geolaw
geolaw

Reputation: 452

C# Android MediaStore.ACTION_IMAGE_CAPTURE

Trying to access the Android native camera component in Unity C# but having trouble porting over the java code properly. I have another intent call working for sharing but I can't seem to get this to work.

Here is my code:

static int REQUEST_IMAGE_CAPTURE = 1;

public void TakePhotoWithCamera()
{
    AndroidJavaClass intentClass = new AndroidJavaClass("android.provider.MediaStore");
    AndroidJavaObject intentObject = new AndroidJavaObject("android.provider.MediaStore");

    intentObject.GetStatic<string>("ACTION_IMAGE_CAPTURE");

    AndroidJavaClass unity = new AndroidJavaClass("com.unity3d.player.UnityPlayer");
    AndroidJavaObject currentActivity = unity.GetStatic<AndroidJavaObject>("currentActivity");
    currentActivity.Call("startActivity", intentObject, REQUEST_IMAGE_CAPTURE);
}

Upvotes: 2

Views: 845

Answers (2)

Chris
Chris

Reputation: 508

While the code is good if you want to work with the camera outside of unity - it which doesn't allow you to manipulate the camera preview inside unity, for instance adding shaders or UI elements on-top.

If you want to do more advanced stuff you can use the following code to get an instance to the running device in a WebCamTexture and modify the properties and behaviour of the camera.

Here is an example of some code that comes from the asset CameraCaptureKit (https://www.assetstore.unity3d.com/en/#!/content/56673) which is the component we used to take photos and share them in a social app.

Class clsPlayer = Class.forName("com.unity3d.player.UnityPlayer"); // com.unity3d.player.UnityPlayerNativeActivity
        Field fCurrentActivity = clsPlayer.getDeclaredField("currentActivity");
        fCurrentActivity.setAccessible(true);
        android.app.Activity currentActivity = (android.app.Activity)fCurrentActivity.get(null);
        ret.playerActivity = currentActivity;

        Field fPlayer = currentActivity.getClass().getDeclaredField("mUnityPlayer");
        fPlayer.setAccessible(true);
        com.unity3d.player.UnityPlayer player = (com.unity3d.player.UnityPlayer)fPlayer.get(currentActivity);
        ret.player = player;

        Field f = player.getClass().getDeclaredField("y");
        f.setAccessible(true);


        //Field fGetNumCameras = player.getClass().getDeclaredField("getNumCameras");


        java.util.ArrayList cameraArrays = (java.util.ArrayList)f.get( player );
        int sz = cameraArrays.size();

        if( sz == 0 ) {
            Log.d("Unity","CameraCaptureKit: Error cannot resolve Unity camera! - Maybe Unity has crashed and restarted?");
            ret.ok=false;
        } else {
            //Log.d("Unity","CameraCaptureKit: SIZE CAMERA ARRAY : " + sz);
            Object cameraContainer = (Object)cameraArrays.get(0);



            Field fCameraId = cameraContainer.getClass().getDeclaredField("h"); 
            fCameraId.setAccessible(true);
            ret.cameraId = (int)fCameraId.get( cameraContainer );

            Field fCameraInst = cameraContainer.getClass().getDeclaredField("a"); // there is a member called A which is private and contains a referance to the camera
            if( dbg ) Log.d("Unity", "CameraCaptureKit : a fieldType=" + ((Class) fCameraInst.getClass()).getName() );
            fCameraInst.setAccessible(true);
            Camera adkCamera = (Camera)fCameraInst.get( cameraContainer );

Upvotes: 1

geolaw
geolaw

Reputation: 452

Rather than delete the question because I had a hard time finding anything to help me I will post what I did.

static int REQUEST_IMAGE_CAPTURE = 1;

public void TakePhotoWithCamera()
{
    AndroidJavaClass IntentClass = new AndroidJavaClass("android.content.Intent");
    AndroidJavaObject IntentObject = new AndroidJavaObject("android.content.Intent");

    AndroidJavaObject MSObject = new AndroidJavaObject("android.provider.MediaStore");

    IntentObject.Call<AndroidJavaObject>("setAction", MSObject.GetStatic<string>("ACTION_IMAGE_CAPTURE"));

    AndroidJavaClass unity = new AndroidJavaClass("com.unity3d.player.UnityPlayer");
    AndroidJavaObject currentActivity = unity.GetStatic<AndroidJavaObject>("currentActivity");
    currentActivity.Call("startActivityForResult", IntentObject, REQUEST_IMAGE_CAPTURE);
}

Upvotes: 1

Related Questions