Ask Your Question

Revision history [back]

click to hide/show revision 1
initial version

I was looking for the same thing and @StevenPuttemans directed me here. This is another solution, based on the format of the example apps in 2.4.4:

In your layout, use two views, initially both invisible, at the same location on the screen. One uses the default camera, one the second. This code assumes you have two cameras and that neither are locked or otherwise unavailable. You'll need to add your own code to check to see if a second camera is available and if not, don't allow this code to run:

<LinearLayout
  xmlns:android="http://schemas.android.com/apk/res/android"
  xmlns:tools="http://schemas.android.com/tools"
  xmlns:opencv="http://schemas.android.com/apk/res-auto"
  android:layout_width="match_parent"
  android:layout_height="match_parent" 
  android:screenOrientation="landscape"
  >

  <barry.opencvd2.OpenCVDemo2View
    android:layout_width="0dp"
    android:layout_height="0dp"
    android:visibility="gone"
    android:adjustViewBounds="true"
    android:gravity="center_vertical"
    android:id="@+id/java_surface_view0" />

  <barry.opencvd2.OpenCVDemo2View
    android:layout_width="0dp"
    android:layout_height="0dp"
    android:visibility="gone"
    opencv:camera_id="1" 
    android:adjustViewBounds="true"
    android:gravity="center_vertical"
    android:id="@+id/java_surface_view1" />

</LinearLayout>

In your onCreate, get a handle to the two views and set up listeners for both cameras:

@Override
public void onCreate(Bundle savedInstanceState) {
  //Log.d(TAG, "called onCreate");
  super.onCreate(savedInstanceState);
  getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);

  setContentView(R.layout.tutorial2_surface_view);

  mOpenCvCameraView0 = (OpenCVDemo2View) findViewById(R.id.java_surface_view0);
  mOpenCvCameraView1 = (OpenCVDemo2View) findViewById(R.id.java_surface_view1);

  mOpenCvCameraView0.setVisibility(SurfaceView.VISIBLE);
  mOpenCvCameraView0.setCvCameraViewListener(this);
  mOpenCvCameraView0.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT));

  mOpenCvCameraView1.setVisibility(SurfaceView.GONE);
  mOpenCvCameraView1.setCvCameraViewListener(this);
  mOpenCvCameraView1.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT));

  OpenCVLoader.initAsync(OpenCVLoader.OPENCV_VERSION_2_4_4, this, mLoaderCallback);
  }

Also make sure the views are disabled in onPause and onDestroy:

@Override
public void onPause() {
  super.onPause();
  if (mOpenCvCameraView0 != null) 
      mOpenCvCameraView0.disableView();
  if (mOpenCvCameraView1 != null) 
      mOpenCvCameraView1.disableView();
  }

public void onDestroy() {
  super.onDestroy();
  if (mOpenCvCameraView0 != null) 
      mOpenCvCameraView0.disableView();
  if (mOpenCvCameraView1 != null) 
      mOpenCvCameraView1.disableView();
  }

In my menu I have an option for swapping cameras, here's what it does:

if (item.getItemId() == R.id.swapcameras) {
  if (iCamera == 0) {
    mOpenCvCameraView0.setVisibility(SurfaceView.GONE);
    mOpenCvCameraView0.disableView();
    mOpenCvCameraView1 = (OpenCVDemo2View) findViewById(R.id.java_surface_view1);
    mOpenCvCameraView1.setCvCameraViewListener(this);
    mOpenCvCameraView1.setVisibility(SurfaceView.VISIBLE);

iCamera = 1;
}
  else {
    mOpenCvCameraView1.setVisibility(SurfaceView.GONE);
    mOpenCvCameraView1.disableView();
    mOpenCvCameraView0 = (OpenCVDemo2View) findViewById (R.id.java_surface_view0);
    mOpenCvCameraView0.setCvCameraViewListener(this);
    mOpenCvCameraView0.setVisibility(SurfaceView.VISIBLE);

    iCamera = 0;
    }

  OpenCVLoader.initAsync(OpenCVLoader.OPENCV_VERSION_2_4_4, this, mLoaderCallback);
  }

If anyone wants the entire source code, just let me know.

I was looking for the same thing and @StevenPuttemans directed me here. This is another solution, based on the format of the example apps in 2.4.4:

In your layout, use two views, initially both invisible, at the same location on the screen. One uses the default camera, one the second. This code assumes you have two cameras and that neither are locked or otherwise unavailable. You'll need to add your own code to check to see if a second camera is available and if not, don't allow this code to run:

<LinearLayout
  xmlns:android="http://schemas.android.com/apk/res/android"
  xmlns:tools="http://schemas.android.com/tools"
  xmlns:opencv="http://schemas.android.com/apk/res-auto"
  android:layout_width="match_parent"
  android:layout_height="match_parent" 
  android:screenOrientation="landscape"
  >

  <barry.opencvd2.OpenCVDemo2View
    android:layout_width="0dp"
    android:layout_height="0dp"
    android:visibility="gone"
    android:adjustViewBounds="true"
    android:gravity="center_vertical"
    android:id="@+id/java_surface_view0" />

  <barry.opencvd2.OpenCVDemo2View
    android:layout_width="0dp"
    android:layout_height="0dp"
    android:visibility="gone"
    opencv:camera_id="1" 
    android:adjustViewBounds="true"
    android:gravity="center_vertical"
    android:id="@+id/java_surface_view1" />

</LinearLayout>

In your onCreate, get a handle to the two views and set up listeners for both cameras:

@Override
public void onCreate(Bundle savedInstanceState) {
  //Log.d(TAG, "called onCreate");
  super.onCreate(savedInstanceState);
  getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);

  setContentView(R.layout.tutorial2_surface_view);

  mOpenCvCameraView0 = (OpenCVDemo2View) findViewById(R.id.java_surface_view0);
  mOpenCvCameraView1 = (OpenCVDemo2View) findViewById(R.id.java_surface_view1);

  mOpenCvCameraView0.setVisibility(SurfaceView.VISIBLE);
  mOpenCvCameraView0.setCvCameraViewListener(this);
  mOpenCvCameraView0.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT));

  mOpenCvCameraView1.setVisibility(SurfaceView.GONE);
  mOpenCvCameraView1.setCvCameraViewListener(this);
  mOpenCvCameraView1.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT));

  OpenCVLoader.initAsync(OpenCVLoader.OPENCV_VERSION_2_4_4, this, mLoaderCallback);
  }

Also make sure the views are disabled in onPause and onDestroy:

@Override
public void onPause() {
  super.onPause();
  if (mOpenCvCameraView0 != null) 
      mOpenCvCameraView0.disableView();
  if (mOpenCvCameraView1 != null) 
      mOpenCvCameraView1.disableView();
  }

public void onDestroy() {
  super.onDestroy();
  if (mOpenCvCameraView0 != null) 
      mOpenCvCameraView0.disableView();
  if (mOpenCvCameraView1 != null) 
      mOpenCvCameraView1.disableView();
  }

In my menu I have an option for swapping cameras, here's what it does:

if (item.getItemId() == R.id.swapcameras) {
  if (iCamera == 0) {
    mOpenCvCameraView0.setVisibility(SurfaceView.GONE);
    mOpenCvCameraView0.disableView();
    mOpenCvCameraView1 = (OpenCVDemo2View) findViewById(R.id.java_surface_view1);
    mOpenCvCameraView1.setCvCameraViewListener(this);
    mOpenCvCameraView1.setVisibility(SurfaceView.VISIBLE);

 iCamera = 1;
 }
  else {
    mOpenCvCameraView1.setVisibility(SurfaceView.GONE);
    mOpenCvCameraView1.disableView();
    mOpenCvCameraView0 = (OpenCVDemo2View) findViewById (R.id.java_surface_view0);
    mOpenCvCameraView0.setCvCameraViewListener(this);
    mOpenCvCameraView0.setVisibility(SurfaceView.VISIBLE);

    iCamera = 0;
    }

  OpenCVLoader.initAsync(OpenCVLoader.OPENCV_VERSION_2_4_4, this, mLoaderCallback);
  }

If anyone wants the entire source code, just let me know.