Update to 2.0.0 tree from current Fremantle build
[opencv] / samples / c / fitellipse.cpp
1 /********************************************************************************
2 *
3 *
4 *  This program is demonstration for ellipse fitting. Program finds
5 *  contours and approximate it by ellipses.
6 *
7 *  Trackbar specify threshold parametr.
8 *
9 *  White lines is contours. Red lines is fitting ellipses.
10 *
11 *
12 *  Autor:  Denis Burenkov.
13 *
14 *
15 *
16 ********************************************************************************/
17 #ifdef _CH_
18 #pragma package <opencv>
19 #endif
20
21 #define CV_NO_BACKWARD_COMPATIBILITY
22
23 #ifndef _EiC
24 #include "cv.h"
25 #include "highgui.h"
26 #endif
27
28 int slider_pos = 70;
29
30 // Load the source image. HighGUI use.
31 IplImage *image02 = 0, *image03 = 0, *image04 = 0;
32
33 void process_image(int h);
34
35 int main( int argc, char** argv )
36 {
37     const char* filename = argc == 2 ? argv[1] : (char*)"stuff.jpg";
38
39     // load image and force it to be grayscale
40     if( (image03 = cvLoadImage(filename, 0)) == 0 )
41         return -1;
42
43     // Create the destination images
44     image02 = cvCloneImage( image03 );
45     image04 = cvCloneImage( image03 );
46
47     // Create windows.
48     cvNamedWindow("Source", 1);
49     cvNamedWindow("Result", 1);
50
51     // Show the image.
52     cvShowImage("Source", image03);
53
54     // Create toolbars. HighGUI use.
55     cvCreateTrackbar( "Threshold", "Result", &slider_pos, 255, process_image );
56
57     process_image(0);
58
59     // Wait for a key stroke; the same function arranges events processing
60     cvWaitKey(0);
61     cvReleaseImage(&image02);
62     cvReleaseImage(&image03);
63
64     cvDestroyWindow("Source");
65     cvDestroyWindow("Result");
66
67     return 0;
68 }
69
70 // Define trackbar callback functon. This function find contours,
71 // draw it and approximate it by ellipses.
72 void process_image(int h)
73 {
74     CvMemStorage* storage;
75     CvSeq* contour;
76
77     // Create dynamic structure and sequence.
78     storage = cvCreateMemStorage(0);
79     contour = cvCreateSeq(CV_SEQ_ELTYPE_POINT, sizeof(CvSeq), sizeof(CvPoint) , storage);
80
81     // Threshold the source image. This needful for cvFindContours().
82     cvThreshold( image03, image02, slider_pos, 255, CV_THRESH_BINARY );
83
84     // Find all contours.
85     cvFindContours( image02, storage, &contour, sizeof(CvContour),
86                     CV_RETR_LIST, CV_CHAIN_APPROX_NONE, cvPoint(0,0));
87
88     // Clear images. IPL use.
89     cvZero(image02);
90     cvZero(image04);
91
92     // This cycle draw all contours and approximate it by ellipses.
93     for(;contour;contour = contour->h_next)
94     {
95         int count = contour->total; // This is number point in contour
96         CvPoint center;
97         CvSize size;
98         CvBox2D box;
99
100         // Number point must be more than or equal to 6 (for cvFitEllipse_32f).
101         if( count < 6 )
102             continue;
103
104         CvMat* points_f = cvCreateMat( 1, count, CV_32FC2 );
105         CvMat points_i = cvMat( 1, count, CV_32SC2, points_f->data.ptr );
106         cvCvtSeqToArray( contour, points_f->data.ptr, CV_WHOLE_SEQ );
107         cvConvert( &points_i, points_f );
108
109         // Fits ellipse to current contour.
110         box = cvFitEllipse2( points_f );
111
112         // Draw current contour.
113         cvDrawContours(image04,contour,CV_RGB(255,255,255),CV_RGB(255,255,255),0,1,8,cvPoint(0,0));
114
115         // Convert ellipse data from float to integer representation.
116         center = cvPointFrom32f(box.center);
117         size.width = cvRound(box.size.width*0.5);
118         size.height = cvRound(box.size.height*0.5);
119
120         // Draw ellipse.
121         cvEllipse(image04, center, size,
122                   -box.angle, 0, 360,
123                   CV_RGB(0,0,255), 1, CV_AA, 0);
124
125         cvReleaseMat(&points_f);
126     }
127
128     // Show image. HighGUI use.
129     cvShowImage( "Result", image04 );
130 }
131
132 #ifdef _EiC
133 main(1,"fitellipse.c");
134 #endif