首页 文章

如何从Android相机中找到框架的轮廓并将其转换为box2d实体?

提问于
浏览
7

使用OpenFrameworks,OpenCV和Box2D,我能够以良好的帧速率实现它 . 使用Android似乎是一项更复杂的任务(部分原因是因为我是JAVA新手) .

这就是我的开始:

  • 使用“OpenCV样本 - 图像处理”并删除除“canny”效果之外的所有内容,这样可以生成漂亮的黑白图像,非常适合查找轮廓 .
public Mat onCameraFrame(CvCameraViewFrame inputFrame)
{
    mRgba = inputFrame.rgba();
    Imgproc.Canny(mRgbaInnerWindow, mIntermediateMat, 50, 100);
    Imgproc.cvtColor(mIntermediateMat, mRgbaInnerWindow, Imgproc.COLOR_GRAY2BGRA, 4);

    return mRgba;
}
  • 从“OpenCV Sample - color-blob-detection”中我 grab 了在Mat中找到轮廓的逻辑:
// These two lines are actually in the function onCameraViewStarted
mHierarchy = new Mat();
CONTOUR_COLOR = new Scalar(255,0,0,255);

// These lines are in function onCameraFrame
List<MatOfPoint> contours = new ArrayList<MatOfPoint>();        
Imgproc.findContours(mRgbaInnerWindow, contours, mHierarchy, Imgproc.RETR_EXTERNAL,     
Imgproc.CHAIN_APPROX_SIMPLE);
Imgproc.drawContours(mIntermediateMat, contours, -1, CONTOUR_COLOR);

所以,我当前的函数看起来像这样,它不起作用:

public Mat onCameraFrame(CvCameraViewFrame inputFrame)
{
    mRgba = inputFrame.rgba();

    if ((mRgbaInnerWindow == null) || (mGrayInnerWindow == null) || (mRgba.cols() != mSizeRgba.width) || (mRgba.height() != mSizeRgba.height))
        CreateAuxiliaryMats();

    Imgproc.Canny(mRgbaInnerWindow, mIntermediateMat, 50, 100);
    //Imgproc.cvtColor(mIntermediateMat, mRgbaInnerWindow, Imgproc.COLOR_GRAY2BGRA, 4);

    List<MatOfPoint> contours = new ArrayList<MatOfPoint>();

    Imgproc.findContours(mRgbaInnerWindow, contours, mHierarchy, Imgproc.RETR_EXTERNAL, Imgproc.CHAIN_APPROX_SIMPLE);
    //Imgproc.drawContours(mIntermediateMat, contours, -1, CONTOUR_COLOR);

    return mRgba;
}

2 回答

  • 0

    嗨,我也是openCV的新手,但是这段代码可能有帮助,

    import android.app.Activity;
    import android.os.Bundle;
    import android.util.Log;
    import android.view.SurfaceView;
    import org.opencv.android.*;
    import org.opencv.core.*;
    import org.opencv.imgproc.Imgproc;
    
    
    import java.util.ArrayList;
    import java.util.List;
    
    public class MainActivity extends Activity implements CvCameraViewListener2{
    
    private static final String TAG = MainActivity.class.getCanonicalName();
    
    private CameraBridgeViewBase mOpenCvCameraView;
    
    private Mat                    mRgba;
    private Mat                    mIntermediateMat;
    private Mat                    mGray;
    Mat hierarchy;
    
    
    List<MatOfPoint> contours;
    
    private BaseLoaderCallback mLoaderCallback = new BaseLoaderCallback(this) {
        @Override
        public void onManagerConnected(int status) {
            switch (status) {
                case LoaderCallbackInterface.SUCCESS:
                {
                    Log.i(TAG, "OpenCV loaded successfully");
                    mOpenCvCameraView.enableView();
                } break;
                default:
                {
                    super.onManagerConnected(status);
                } break;
            }
        }
    };
    
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
    
        mOpenCvCameraView = (CameraBridgeViewBase) findViewById(R.id.java_surface_view);
        mOpenCvCameraView.setVisibility(SurfaceView.VISIBLE);
    
        mOpenCvCameraView.setCvCameraViewListener(this);
    
    }
    
    @Override
    public void onResume() {
        super.onResume();
        OpenCVLoader.initAsync(OpenCVLoader.OPENCV_VERSION_2_4_3, this,
                mLoaderCallback);
    }
    
    @Override
    public void onPause() {
        super.onPause();
        if (mOpenCvCameraView != null)
            mOpenCvCameraView.disableView();
    }
    
    
    
    @Override
    public void onCameraViewStarted(int width, int height) {
        mRgba = new Mat(height, width, CvType.CV_8UC4);
        mIntermediateMat = new Mat(height, width, CvType.CV_8UC4);
        mGray = new Mat(height, width, CvType.CV_8UC1);
        hierarchy = new Mat();
    }
    
    @Override
    public void onCameraViewStopped() {
        mRgba.release();
        mGray.release();
        mIntermediateMat.release();
        hierarchy.release();
    }
    
    @Override
    public Mat onCameraFrame(CvCameraViewFrame inputFrame) {
         mRgba = inputFrame.gray();
            contours = new ArrayList<MatOfPoint>();
            hierarchy = new Mat();
    
         Imgproc.Canny(mRgba, mIntermediateMat, 80, 100);
         Imgproc.findContours(mIntermediateMat, contours, hierarchy, Imgproc.RETR_TREE, Imgproc.CHAIN_APPROX_SIMPLE, new Point(0, 0));
        /* Mat drawing = Mat.zeros( mIntermediateMat.size(), CvType.CV_8UC3 );
         for( int i = 0; i< contours.size(); i++ )
         {
        Scalar color =new Scalar(Math.random()*255, Math.random()*255, Math.random()*255);
         Imgproc.drawContours( drawing, contours, i, color, 2, 8, hierarchy, 0, new Point() );
         }*/
         hierarchy.release();
         Imgproc.drawContours(mRgba, contours, -1, new Scalar(Math.random()*255, Math.random()*255, Math.random()*255));//, 2, 8, hierarchy, 0, new Point());
        // Imgproc.cvtColor(mIntermediateMat, mRgba, Imgproc.COLOR_GRAY2RGBA, 4);
        return mRgba;
    }
    
    }
    

    我知道这可能不是实现这一目标的最佳方式,但我们都在这里学习新方法:)

  • 12

    简答:您必须使用 Canny 的结果作为 findContours 的输入(第一个参数),即

    Imgproc.findContours(mIntermediateMat, ...);
    

相关问题