GECKO 1.0
Human-computer interface based on hand gesture recognition
|
Finds the maximum inscribed circle of the hand contour, which describes the hand palm. { //-- Parameters describing this hand palm procedure: const int x_ratio = 3; //-- Section of the bounding box used for finding center (along X) const int y_ratio = 3; //-- Section of the bounding box used for finding center (along Y) const int step_contour = 1; //-- Test each 'step' points of the contour for easier calculations const int step_points_inside = 1;//-- Test each 'step' points inside the contour //-- Extract points to use std::vector< cv::Point > points_to_use; if ( step_contour == 1) { points_to_use = _hand_contour[0]; } else { for (int i = 0; i < (int) ( _hand_contour[0].size() / (float) step_contour); i++) points_to_use.push_back( _hand_contour[0][i]); } //-- Find initial and ending points of the area to look for std::pair<int,int> x_limits, y_limits; x_limits.first = _hand_bounding_box.x + _hand_bounding_box.width / x_ratio; x_limits.second = _hand_bounding_box.x + (int) ( _hand_bounding_box.width * (1 - 1 /(float) x_ratio)); y_limits.first = _hand_bounding_box.y + _hand_bounding_box.height / y_ratio; y_limits.second = _hand_bounding_box.y + (int) ( _hand_bounding_box.height * (1 - 1 /(float) y_ratio)); //-- Look for center and radius std::pair<int, int> best_center = std::pair<int, int>( x_limits.first, y_limits.first); double best_distance = -1; /* std::cout << "(" << x_limits.first << ", " << x_limits.second << ")" << std::endl; std::cout << "(" << y_limits.first << ", " << y_limits.second << ")" << std::endl; */ for (int j = y_limits.first; j < y_limits.second; j += step_points_inside ) for (int i = x_limits.first; i < x_limits.second; i += step_points_inside ) { double current_distance = cv::pointPolygonTest( points_to_use, cv::Point(i, j), true ); if (current_distance > 0 && current_distance > best_distance) { best_distance = current_distance; best_center.first = i; best_center.second = j; } } //-- Once best distance is found, we get the center and calculate the actual radius (only if something is found) if ( best_distance > -1 ) { _max_circle_incribed_center = cv::Point( best_center.first, best_center.second ); _max_circle_inscribed_radius = best_distance; // std::cout << "[Debug] Inscribed circle: " << _max_circle_incribed_center << " -> r =" << _max_circle_inscribed_radius << std::endl; } else { std::cerr << "[Error]: Inscribed circle could not be found!" << std::endl; } } |