1

Let me begin with the coding first. My xml file (relevant part of it) contains this:

<FrameLayout
        xmlns:android="http://schemas.android.com/apk/res/android"
        android:orientation="vertical"
        android:layout_width="fill_parent"
        android:layout_height="fill_parent"
        android:layout_weight="1"
        android:background="#ffffff">


        <SurfaceView
            android:id="@+id/cameraView"
            android:layout_width="fill_parent"
            android:layout_height="fill_parent"
            android:visibility="gone" />

        <LinearLayout
            android:id="@+id/layStatus"
            android:orientation="horizontal"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:visibility="gone">

            <TextView
                android:id="@+id/txtStatus"
                android:layout_width="fill_parent"
                android:layout_height="fill_parent"
                android:background="#90000000"
                android:paddingBottom="5dip"
                android:paddingTop="5dip"
                android:gravity="center_vertical|center_horizontal"
                android:textSize="20dip" />
        </LinearLayout>
</FrameLayout>

As you can see I've got a basic set up, a frame layout which contains a surfaceview (which has visibility set to gone) and another layout with a simple TextView. Here is what I have in my activity:

@Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.mylayout);

        cameraView = (SurfaceView)findViewById(R.id.cameraView);

        surfaceHolder = cameraView.getHolder();
        surfaceHolder.addCallback(CompassActivity.this);
        surfaceHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);
}

public void btnCameraOnClick(View target) {

    cameraView.setVisibility(View.VISIBLE);

    }

Starting the camera preview is done in Surface changed, which fires when visibility of the surface changes.

@Override
    public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
            txtStatus.setVisibility(View.Visible);
            txtStatus.setText("Starting camera");
camera = Camera.open();
if (camera != null){
                try {

                    camera.setDisplayOrientation(90);
                    Camera.Parameters parameters = camera.getParameters();

                    List<Size> sizes = parameters.getSupportedPreviewSizes();
                    Size size = sizes.get(0);
                    parameters.setPreviewSize(size.width, size.height);

                    camera.setParameters(parameters);

                    camera.setPreviewDisplay(holder);
                    camera.startPreview();

                     txtStatis.setVisibility(View.GONE);
                } catch (IOException e) {
                }
            }
}

So what's the problem ? I want to simply display a text while the camera preview starts. To do this, I make the txtStatus visible and set a text to it. When the preview is started, I simply hide it. Well, it doesn't work like this, When I press a button to start camera preview, the UI thread freezes waiting for the preview and my status message is not displayed. How can I fix it ? There is a solution at HERE but I was thinking that maybe there is a simpler one.

Thank you for your time.

Community
  • 1
  • 1
Alin
  • 14,809
  • 40
  • 129
  • 218

1 Answers1

2

Camera start up takes some time - external process shall be started and everything set up. I would speculate, that surface changed callback is executed directly from setVisibility() and blocks UI thread. Solution is pretty simple - just spawn new thread and do camera init there.

In my OCR applicatios I start camera in onResume() - since I always need working preview

You may find my OCR android demos helpful:

http://sourceforge.net/projects/javaocr/

( camera preview, with overlays )

Konstantin Pribluda
  • 12,329
  • 1
  • 30
  • 35