Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Converting NV21 to RGB using OpenCV in Android

I am trying to use OpenCV in Android. So I first tested out OpenCV by having two SurfaceViews placed side-by-side. One SurfaceView is used to preview output (the output format is clearly NV21) from the camera. The other SurfaceView shows the same preview after passing through OpenCV as shown in the code below:

public void onPreviewFrame(byte[] data, Camera camera) {
    // TODO Auto-generated method stub

    if( mYuv != null ) mYuv.release();
    mYuv = new Mat( height + height/2, width, CvType.CV_8UC1 );
    mYuv.put( 0, 0, data);
    Mat mRgba = new Mat();

    Imgproc.cvtColor( mYuv, mRgba, Imgproc.COLOR_YUV2RGB_NV21, 4 );

    Bitmap map = Bitmap.createBitmap( width, height, Bitmap.Config.ARGB_8888 );

    Utils.matToBitmap( mRgba, map );

    preview.setBackgroundDrawable( new BitmapDrawable( map ));
    mRgba.release();

}

But the resulting image after passing through OpenCV is an green, staticy... thing:

green, staticy thing

Any ideas?

Edit:

Modified code a bit as per comment.

public void onPreviewFrame(byte[] data, Camera camera) {
    // TODO Auto-generated method stub

    if( mYuv != null ) mYuv.release();
    mYuv = new Mat( height + height/2, width, CvType.CV_8UC1 );
    mYuv.put( 0, 0, data );
    Mat mRgba = new Mat();

    Imgproc.cvtColor( mYuv, mRgba, Imgproc.COLOR_YUV2RGBA_NV21, 4 );

    Bitmap map = Bitmap.createBitmap( width, height, Bitmap.Config.ARGB_8888 );

    Utils.matToBitmap( mRgba, map );

    preview.setBackgroundDrawable( new BitmapDrawable( where.getResources(), map ));
    mRgba.release();

}

Which results in this: Ugly green thing again.

like image 397
vsector Avatar asked Jul 04 '12 23:07

vsector


1 Answers

Alright, I figured out where I went haywire.

I initially did something like this:

public void surfaceChanged(SurfaceHolder holder, int format, int width,
        int height) {

    this.width = width; this.height = height;
    params.setPreviewSize( width, height );
    camera.setParameters( params );
    camera.startPreview();

}

The problem is, the cameras on android only supports specific preview resolutions. Therefore the specific resolution I was setting did not work. So, I changed it to this:

public void surfaceChanged(SurfaceHolder holder, int format, int width,
        int height) {

    Size size = params.getPreviewSize();
    this.height = size.height;
    this.width = size.width;
    camera.setParameters( params );
    camera.startPreview();

}

And then everything works A-OK! Honestly, this was not where I expected the error to be, so this was not a well formed question.

like image 92
vsector Avatar answered Oct 02 '22 18:10

vsector