| 273 | |
| 274 | |
| 275 | CV_IMPL int |
| 276 | cvMinEnclosingCircle( const void* array, CvPoint2D32f * _center, float *_radius ) |
| 277 | { |
| 278 | const int max_iters = 100; |
| 279 | const float eps = FLT_EPSILON*2; |
| 280 | CvPoint2D32f center = { 0, 0 }; |
| 281 | float radius = 0; |
| 282 | int result = 0; |
| 283 | |
| 284 | if( _center ) |
| 285 | _center->x = _center->y = 0.f; |
| 286 | if( _radius ) |
| 287 | *_radius = 0; |
| 288 | |
| 289 | CvSeqReader reader; |
| 290 | int k, count; |
| 291 | CvPoint2D32f pts[8]; |
| 292 | CvContour contour_header; |
| 293 | CvSeqBlock block; |
| 294 | CvSeq* sequence = 0; |
| 295 | int is_float; |
| 296 | |
| 297 | if( !_center || !_radius ) |
| 298 | CV_Error( CV_StsNullPtr, "Null center or radius pointers" ); |
| 299 | |
| 300 | if( CV_IS_SEQ(array) ) |
| 301 | { |
| 302 | sequence = (CvSeq*)array; |
| 303 | if( !CV_IS_SEQ_POINT_SET( sequence )) |
| 304 | CV_Error( CV_StsBadArg, "The passed sequence is not a valid contour" ); |
| 305 | } |
| 306 | else |
| 307 | { |
| 308 | sequence = cvPointSeqFromMat( |
| 309 | CV_SEQ_KIND_GENERIC, array, &contour_header, &block ); |
| 310 | } |
| 311 | |
| 312 | if( sequence->total <= 0 ) |
| 313 | CV_Error( CV_StsBadSize, "" ); |
| 314 | |
| 315 | cvStartReadSeq( sequence, &reader, 0 ); |
| 316 | |
| 317 | count = sequence->total; |
| 318 | is_float = CV_SEQ_ELTYPE(sequence) == CV_32FC2; |
| 319 | |
| 320 | if( !is_float ) |
| 321 | { |
| 322 | CvPoint *pt_left, *pt_right, *pt_top, *pt_bottom; |
| 323 | CvPoint pt; |
| 324 | pt_left = pt_right = pt_top = pt_bottom = (CvPoint *)(reader.ptr); |
| 325 | CV_READ_SEQ_ELEM( pt, reader ); |
| 326 | |
| 327 | for(int i = 1; i < count; i++ ) |
| 328 | { |
| 329 | CvPoint* pt_ptr = (CvPoint*)reader.ptr; |
| 330 | CV_READ_SEQ_ELEM( pt, reader ); |
| 331 | |
| 332 | if( pt.x < pt_left->x ) |
no test coverage detected