Fitting an ellipse with cvFitEllipse2 to a set of points

785 views
Skip to first unread message

N3

unread,
Jun 12, 2013, 5:41:38 PM6/12/13
to jav...@googlegroups.com
Hey,

as per title, I'm trying to fit an ellipse using cvFitEllipse2. However, I keep running into errors that I can't solve. Here are my approaches:

1) Create a CvSeq

CvPoint pts = ... (custom method, collecting points above a given threshold in an image). pts.capacity() yields the correct amount of points.
CvSeq seq = cvCreateSeq(0, Loader.sizeof(CvSeq.class), Loader.sizeof(CvPoint.class), mem);
for (int i=0; i<pts.capacity(); i++) {
   cvSeqPush(seq, pts.position(i));
}
CvBox2D elli = cvFitEllipse2(seq);

Error: OpenCV Error: Bad argument (Unsupported sequence type) in unknown function, file ..\..\..\src\opencv\modules\imgproc\src\shapedescr.cpp, line 790
Exception in thread "main" java.lang.RuntimeException: ..\..\..\src\opencv\modules\imgproc\src\shapedescr.cpp:790: error: (-5) Unsupported sequence type


2) Create a CvMat
CvMat mat = cvCreateMat(pts.capacity(), 2, CV_32S);
mat.getIntBuffer().put(pts.asByteBuffer().asIntBuffer());
CvBox2D elli = cvFitEllipse2(mat);

Error: OpenCV Error: Unsupported format or combination of formats (The matrix can not be converted to point sequence because of inappropriate element type) in unknown function, file ..\..\..\src\opencv\modules\imgproc\src\utils.cpp, line 59
Exception in thread "main" java.lang.RuntimeException: ..\..\..\src\opencv\modules\imgproc\src\utils.cpp:59: error: (-210) The matrix can not be converted to point sequence because of inappropriate element type

I also tried doing CvMat mat = cvCreateMat(1, pts.capacity()*2, CV_32S); with the same result. Unsurprisingly, it seems the CV_32S is wrong? I'm not sure.


Thanks in advance.
Message has been deleted

N3

unread,
Jun 13, 2013, 6:24:30 AM6/13/13
to jav...@googlegroups.com
As for #1 I have tried the following today:

CvMemStorage mem = cvCreateMemStorage(0);
CvSeq seq = cvCreateSeq(0, Loader.sizeof(CvSeq.class), Loader.sizeof(CvPoint.class), mem);
CvPoint pts = new CvPoint(6);
pts.position(0).put(cvPoint(3, 0));
pts.position(1).put(cvPoint(1, 5));
pts.position(2).put(cvPoint(2, 9));
pts.position(3).put(cvPoint(1, 15));
pts.position(4).put(cvPoint(0, 9));
pts.position(5).put(cvPoint(1, 5));
for(int i=0; i<6; i++){
   System.out.println(pts.position(i).x()+", "+pts.position(i).y());
   vSeqPush(seq, pts.position(i));
}
for(int i=0; i<6; i++){
   System.out.println(cvGetSeqElem(seq, i));
   CvPoint v = new CvPoint(cvGetSeqElem(seq, i));
   System.out.println("Seq: "+v.x()+", "+v.y());
}

And its output is:
3, 0
1, 5
2, 9
1, 15
0, 9
1, 5
com.googlecode.javacpp.Pointer[address=0x7f84300f3e40,position=0,limit=0,capacity=0,deallocator=null]
Seq: 3, 0
com.googlecode.javacpp.Pointer[address=0x7f84300f3e48,position=0,limit=0,capacity=0,deallocator=null]
Seq: 3, 0
com.googlecode.javacpp.Pointer[address=0x7f84300f3e50,position=0,limit=0,capacity=0,deallocator=null]
Seq: 3, 0
com.googlecode.javacpp.Pointer[address=0x7f84300f3e58,position=0,limit=0,capacity=0,deallocator=null]
Seq: 3, 0
com.googlecode.javacpp.Pointer[address=0x7f84300f3e60,position=0,limit=0,capacity=0,deallocator=null]
Seq: 3, 0
com.googlecode.javacpp.Pointer[address=0x7f84300f3e68,position=0,limit=0,capacity=0,deallocator=null]
Seq: 3, 0

I can't figure out why the points in my CvSeq behave this way. It seems just Point1 is being pushed to the sequence.

N3

unread,
Jun 13, 2013, 7:11:46 AM6/13/13
to jav...@googlegroups.com
if I do CvPoint v = new CvPoint(pts.position(i).x(), pts.position(i).y()); and push v to the sequence, it works out.

However, sending this sequence into  cvFitEllipse2 fails:
OpenCV Error: Bad argument (Unsupported sequence type) in cvFitEllipse2, file /tmp/opencv-2.4.3+dfsg/modules/imgproc/src/shapedescr.cpp, line 790
Exception in thread "main" java.lang.RuntimeException: /tmp/opencv-2.4.3+dfsg/modules/imgproc/src/shapedescr.cpp:790: error: (-5) Unsupported sequence type in function cvFitEllipse2

What kind of sequence does cvFitEllipse2 expect?

Samuel Audet

unread,
Jun 15, 2013, 9:19:34 PM6/15/13
to jav...@googlegroups.com
On 06/13/2013 06:41 AM, N3 wrote:
> I also tried doing CvMat mat = cvCreateMat(1, pts.capacity()*2, CV_32S);
> with the same result. Unsurprisingly, it seems the CV_32S is wrong? I'm
> not sure.

According to this sample:
https://code.ros.org/trac/opencv/browser/trunk/opencv/samples/c/fitellipse.cpp?rev=4065#L96
It looks like it wants CV_32FC2..

Samuel

N3

unread,
Jun 16, 2013, 9:18:32 AM6/16/13
to jav...@googlegroups.com
Samuel, thanks for your help.

I've been running into the same problems though. Here's the code I used, do you find anything wrong with it?

CvPoint2D32f pts = new CvPoint2D32f(6);
pts.position(0).put(1,1);
pts.position(1).put(1,3);
pts.position(2).put(3,7);
pts.position(3).put(7,3);
pts.position(4).put(3,0);
pts.position(5).put(2,1);
pts.position(6).put(1,0);
CvMat mat = CvMat.create(1, pts.capacity(), CV_32FC2);
mat.getFloatBuffer().put(pts.asByteBuffer().asFloatBuffer());
cvFitEllipse2(mat);

N3

unread,
Jun 17, 2013, 7:22:27 AM6/17/13
to jav...@googlegroups.com
I have found a solution to my problem using a simple float array instead. Here's my solution:

//6  2D-points stored in a 1-dimensional float array
float points[] = { 1.0f, 1.1f, 1.0f, 3.0f, 3.0f, 7.0f, 7.0f, 3.0f, 3.0f, 0.0f, 2.0f, 1.0f,1.0f, 0.0f};
//1 row matrix with 6 2-D points of type CV_32FC2 and a FloatPointer to the points array.
CvMat mat = cvMat(1, 6, CV_32FC2, new FloatPointer(points));
CvBox2D result = cvFitEllipse2(mat);
System.out.println(result);

output> ((4.42315, 4.259364), (5.7341976, 9.166761), 146.46394)

Samuel Audet

unread,
Jun 19, 2013, 8:22:19 AM6/19/13
to jav...@googlegroups.com
Glad to hear that it works!
Reply all
Reply to author
Forward
0 new messages