Ask Your Question

Revision history [back]

click to hide/show revision 1
initial version

Android: Draw contours arround points detected by MSER

I'm trying to draw countours to indicate the points detected by MSER in a bitmap.

I can detect the points with FeatureDectector.detect() but it returns them as MatOfKeyPoint.

Now I want to dray the contour of these points using Imgproc.drawContours(), but this function receives the points as a List<MatOfPoint>.

I have tried to convert MatOfKeyPoint to List<MatOfPoint>, then use drawContours(). This is what I have tested:

private void processBitmap(Bitmap bmp){
    Mat mat = new Mat(bmp.getWidth(), bmp.getHeight(),
            CvType.CV_16S, new Scalar(4));

    Utils.bitmapToMat(bmp, mat);

    Imgproc.cvtColor(mat, mat, Imgproc.COLOR_RGB2GRAY, 4);

    FeatureDetector fd = FeatureDetector.create(FeatureDetector.MSER);
    MatOfKeyPoint mokp = new MatOfKeyPoint();
    fd.detect(mat, mokp);

    KeyPoint[] kps = mokp.toArray();

    List<MatOfPoint> mops = new ArrayList<MatOfPoint>(kps.length);
    for(int i = 0; i < kps.length; i++)
        mops.set(i, new MatOfPoint(kps[i].pt));

    Scalar s = new Scalar(0);

    Imgproc.drawContours(mat, mops, 1, s);


    Utils.matToBitmap(mat, bmp);
}

In this case, there is no exceptions, but drawContours() does nothing.

I have tested this too:

import org.opencv.core.Point;
[...]

private void processBitmap(Bitmap bmp){
    Mat mat = new Mat(bmp.getWidth(), bmp.getHeight(),
            CvType.CV_16S, new Scalar(4));
    Utils.bitmapToMat(bmp, mat);
    Imgproc.cvtColor(mat, mat, Imgproc.COLOR_RGB2GRAY, 4);

    FeatureDetector fd = FeatureDetector.create(FeatureDetector.MSER);
    MatOfKeyPoint mokp = new MatOfKeyPoint();
    fd.detect(mat, mokp);

    KeyPoint[] kps = mokp.toArray();
    Scalar s = new Scalar(0); //color black

    Point[] points = new Point[kps.length]; //
    for(int i = 0; i < points.length; i++)
        points[i] = kps[i].pt;

    MatOfPoint mop = new MatOfPoint();
    mop.fromArray(points);

    List<MatOfPoint> lmop = new ArrayList<MatOfPoint>();
    lmop.add(mop);

    Imgproc.drawContours(mat, lmop, 5, s);      

    Utils.matToBitmap(mat, bmp);
}

In this case there is an exception:

OpenCV Error: Assertion failed (0 <= contourIdx && contourIdx < (int)last

I have read the documentation of OpenCV for java here:

http://docs.opencv.org/java/

But the example is only with findContours().

I have read that MatOfPoint is only a way used by OpenCV to avoid to copy points between native part and java part,

(See: http://www.answers.opencv.org/question/6206/opencv4android-conversion-from-matofkeypoint-to-matofpoint2f/)

so that, I assume that the List<MatOfPoint> must have only 1 component due to MatOfPoint contains all points I need, is this correct?

How can I convert the MatOfKeyPoint in List<MatOfPoint> properly?