176 lines
5.2 KiB
C
176 lines
5.2 KiB
C
#ifndef GEOMETRIC_FITTING_H
|
|
#define GEOMETRIC_FITTING_H
|
|
|
|
#include "HoleDetectionParams.h"
|
|
#include "ErrorCodes.h"
|
|
#include "../include/VZNL_Types.h"
|
|
|
|
/**
|
|
* @brief Fit ellipse to 2D boundary points
|
|
*
|
|
* @param [in] points 3D boundary points (will be projected to 2D)
|
|
* @param [in] pointCount Number of points
|
|
* @param [out] outCenter Ellipse center (x, y, z)
|
|
* @param [out] outRadius Ellipse radius (average of semi-major and semi-minor axes)
|
|
* @param [out] outEccentricity Eccentricity (0 = circle)
|
|
* @param [out] errCode Error code output
|
|
* @return 0 on success, non-zero on error
|
|
*
|
|
* @pre points != nullptr
|
|
* @pre pointCount >= 5
|
|
* @pre outCenter != nullptr
|
|
* @pre outRadius != nullptr
|
|
* @pre outEccentricity != nullptr
|
|
* @pre errCode != nullptr
|
|
*/
|
|
int FitEllipse(
|
|
const SVzNLPointXYZ* points,
|
|
int pointCount,
|
|
SVzNL3DPointF* outCenter,
|
|
float* outRadius,
|
|
float* outEccentricity,
|
|
int* errCode
|
|
);
|
|
|
|
/**
|
|
* @brief Fit plane to 3D points
|
|
*
|
|
* @param [in] points 3D points
|
|
* @param [in] pointCount Number of points
|
|
* @param [out] outNormal Plane normal vector (unit length)
|
|
* @param [out] outD Plane equation constant (ax+by+cz+d=0)
|
|
* @param [out] errCode Error code output
|
|
* @return 0 on success, non-zero on error
|
|
*
|
|
* @pre points != nullptr
|
|
* @pre pointCount >= 3
|
|
* @pre outNormal != nullptr
|
|
* @pre outD != nullptr
|
|
* @pre errCode != nullptr
|
|
*
|
|
* @post ||outNormal|| = 1.0 ± 1e-6
|
|
*/
|
|
int FitPlane(
|
|
const SVzNLPointXYZ* points,
|
|
int pointCount,
|
|
SVzNL3DPointF* outNormal,
|
|
float* outD,
|
|
int* errCode
|
|
);
|
|
|
|
/**
|
|
* @brief Compute quality score for hole
|
|
*
|
|
* @param [in] eccentricity Eccentricity (0 = perfect circle)
|
|
* @param [in] radiusVariance Radius variance (mm)
|
|
* @param [in] angularSpan Angular coverage (degrees)
|
|
* @param [in] boundaryPointCount Number of boundary points
|
|
* @return Quality score (0-1, higher = better)
|
|
*/
|
|
float ComputeQualityScore(
|
|
float eccentricity,
|
|
float radiusVariance,
|
|
float angularSpan,
|
|
int boundaryPointCount
|
|
);
|
|
|
|
/**
|
|
* @brief Compute rectangularity score using PCA + corner detection
|
|
*
|
|
* Uses PCA to align points, then counts points in "corner regions"
|
|
* (where u² + v² > 1.1 in normalized coordinates).
|
|
* Ellipse points stay within u² + v² ≤ 1.0, rectangle corners exceed this.
|
|
*
|
|
* @param [in] points 3D boundary points (X-Y used for analysis)
|
|
* @param [in] pointCount Number of points
|
|
* @return Corner ratio (0-1). Higher = more rectangular.
|
|
* Returns 0 if pointCount < 4.
|
|
*/
|
|
float ComputeRectangularityScore(
|
|
const SVzNLPointXYZ* points,
|
|
int pointCount
|
|
);
|
|
|
|
/**
|
|
* @brief Compute angular coverage of points around centroid
|
|
*
|
|
* Calculates what percentage of 360° is covered by the point distribution.
|
|
* Used to detect incomplete/non-closed boundaries.
|
|
*
|
|
* @param [in] points 3D boundary points (X-Y used for analysis)
|
|
* @param [in] pointCount Number of points
|
|
* @param [in] numBins Number of angular bins (default: 36 = 10° each)
|
|
* @return Angular coverage in degrees (0-360).
|
|
* Returns 0 if pointCount < 3.
|
|
*/
|
|
float ComputeAngularCoverage(
|
|
const SVzNLPointXYZ* points,
|
|
int pointCount,
|
|
int numBins = 36
|
|
);
|
|
|
|
/**
|
|
* @brief Compute angular coverage of points around a specified center
|
|
*
|
|
* Same as above, but uses the given center instead of computing centroid.
|
|
* Use this when a fitted center (e.g. from ellipse fitting) is available.
|
|
*
|
|
* @param [in] points 3D boundary points (X-Y used for analysis)
|
|
* @param [in] pointCount Number of points
|
|
* @param [in] centerX X coordinate of the reference center
|
|
* @param [in] centerY Y coordinate of the reference center
|
|
* @param [in] numBins Number of angular bins (default: 36 = 10° each)
|
|
* @return Angular coverage in degrees (0-360).
|
|
* Returns 0 if pointCount < 3.
|
|
*/
|
|
float ComputeAngularCoverage(
|
|
const SVzNLPointXYZ* points,
|
|
int pointCount,
|
|
float centerX,
|
|
float centerY,
|
|
int numBins = 36
|
|
);
|
|
|
|
/**
|
|
* @brief Check circularity of points in X-Y plane
|
|
*
|
|
* Computes the coefficient of variation (CV) of distances from each point
|
|
* to the centroid. Low CV indicates circular/elliptical distribution.
|
|
*
|
|
* @param [in] points 3D boundary points (X-Y used for analysis)
|
|
* @param [in] pointCount Number of points
|
|
* @param [in] maxCV Maximum allowed CV (default: 0.4)
|
|
* @return true if CV <= maxCV (circular enough), false otherwise.
|
|
* Returns false if pointCount < 3.
|
|
*/
|
|
bool CheckCircularity(
|
|
const SVzNLPointXYZ* points,
|
|
int pointCount,
|
|
float maxCV = 0.4f
|
|
);
|
|
|
|
/**
|
|
* @brief Compute inlier ratio for ellipse fit
|
|
*
|
|
* Calculates the fraction of points whose distance to the fitted ellipse
|
|
* center is within tolerance of the fitted radius.
|
|
*
|
|
* @param [in] points 2D projected points (X-Y used)
|
|
* @param [in] pointCount Number of points
|
|
* @param [in] centerX Fitted ellipse center X
|
|
* @param [in] centerY Fitted ellipse center Y
|
|
* @param [in] radius Fitted average radius
|
|
* @param [in] tolerance Distance tolerance as fraction of radius (default: 0.3)
|
|
* @return Inlier ratio (0-1). Higher = better fit.
|
|
*/
|
|
float ComputeEllipseInlierRatio(
|
|
const SVzNLPointXYZ* points,
|
|
int pointCount,
|
|
float centerX,
|
|
float centerY,
|
|
float radius,
|
|
float tolerance = 0.3f
|
|
);
|
|
|
|
#endif // GEOMETRIC_FITTING_H
|