#ifndef HOLE_DETECTION_VISUALIZER_H #define HOLE_DETECTION_VISUALIZER_H #include "HoleDetection.h" #include "../include/VZNL_Types.h" #include #include /** * @brief Visualizer for hole detection algorithm using VTK * * This class provides visualization capabilities for each step of the * hole detection pipeline: * 1. Original point cloud * 2. Detected boundary points * 3. Clustered boundary points * 4. Fitted ellipses and planes * 5. Final detected holes */ class HoleDetectionVisualizer { public: HoleDetectionVisualizer(); ~HoleDetectionVisualizer(); /** * @brief Visualize original point cloud * * @param points Input point cloud * @param rows Number of rows * @param cols Number of columns * @param title Window title */ void VisualizePointCloud( const SVzNLPointXYZ* points, int rows, int cols, const std::string& title = "Original Point Cloud" ); /** * @brief Visualize boundary points on top of original cloud * * @param points Original point cloud * @param rows Number of rows * @param cols Number of columns * @param boundaryPoints Detected boundary points * @param title Window title */ void VisualizeBoundaryPoints( const SVzNLPointXYZ* points, int rows, int cols, const std::vector& boundaryPoints, const std::string& title = "Detected Boundary Points" ); /** * @brief Visualize segment endpoint pairs with different colors * * @param points Original point cloud * @param rows Number of rows * @param cols Number of columns * @param segmentPairs Detected segment pairs * @param title Window title */ void VisualizeSegmentPairs( const SVzNLPointXYZ* points, int rows, int cols, const std::vector& segmentPairs, const std::string& title = "Detected Segment Pairs" ); /** * @brief Visualize clustered boundary points with different colors * * @param points Original point cloud * @param rows Number of rows * @param cols Number of columns * @param boundaryPoints All boundary points * @param clusters Cluster indices * @param title Window title */ void VisualizeClusters( const SVzNLPointXYZ* points, int rows, int cols, const std::vector& boundaryPoints, const std::vector>& clusters, const std::string& title = "Clustered Boundary Points" ); /** * @brief Visualize extreme points extracted from clusters * * @param points Original point cloud * @param rows Number of rows * @param cols Number of columns * @param boundaryPoints All boundary points * @param allExtremePoints Extreme points for each cluster * @param title Window title */ void VisualizeExtremePoints( const SVzNLPointXYZ* points, int rows, int cols, std::vector& extremePoints, const std::string& title = "Extreme Points from Clusters" ); /** * @brief Visualize expanded region points used for plane fitting * * @param points Original point cloud * @param rows Number of rows * @param cols Number of columns * @param clusterPoints Cluster boundary points (shown in red) * @param expandedRegionPoints Expanded region points for plane fitting (shown in green) * @param title Window title */ void VisualizeExpandedRegion( const SVzNLPointXYZ* points, int rows, int cols, const std::vector& clusterPoints, const std::vector& expandedRegionPoints, const std::string& title = "Expanded Region for Plane Fitting" ); /** * @brief Visualize a single line evaluation result * * @param points Original point cloud * @param rows Number of rows * @param cols Number of columns * @param startIdx Starting index of the line * @param step Step size (1 for row, cols for column) * @param count Number of points in the line * @param newBoundaryPoints Boundary points detected in this line * @param lineType "Row" or "Column" * @param lineIndex Row or column index */ void VisualizeLineEvaluation( const SVzNLPointXYZ* points, int rows, int cols, int startIdx, int step, int count, const std::vector& newBoundaryPoints, const std::string& lineType, int lineIndex ); /** * @brief Visualize final detected holes with ellipses and planes * * @param points Original point cloud * @param rows Number of rows * @param cols Number of columns * @param result Detection result * @param title Window title */ void VisualizeDetectedHoles( const SVzNLPointXYZ* points, int rows, int cols, const SMultiHoleResult& result, const std::string& title = "Detected Holes" ); /** * @brief Visualize candidate holes from ellipse fitting (before filtering) * * @param points Original point cloud * @param rows Number of rows * @param cols Number of columns * @param candidateHoles All candidate holes from ellipse fitting * @param title Window title */ void VisualizeCandidateHoles( const SVzNLPointXYZ* points, int rows, int cols, const std::vector& candidateHoles, const std::string& title = "Candidate Holes (Before Filtering)" ); /** * @brief Visualize filter comparison showing which holes were filtered * * @param points Original point cloud * @param rows Number of rows * @param cols Number of columns * @param candidateHoles All candidate holes * @param filteredHoles Holes that passed filtering * @param title Window title */ void VisualizeFilterComparison( const SVzNLPointXYZ* points, int rows, int cols, const std::vector& candidateHoles, const std::vector& filteredHoles, const std::string& title = "Filter Comparison" ); /** * @brief Visualize sorted holes with rank indicators * * @param points Original point cloud * @param rows Number of rows * @param cols Number of columns * @param sortedHoles Sorted holes * @param sortMode Sort mode used * @param title Window title */ void VisualizeSortedHoles( const SVzNLPointXYZ* points, int rows, int cols, const std::vector& sortedHoles, ESortMode sortMode, const std::string& title = "Sorted Holes" ); /** * @brief Set whether to show interactive window (default: true) * If false, saves screenshots instead */ void SetInteractive(bool interactive); /** * @brief Set output directory for screenshots */ void SetOutputDirectory(const std::string& dir); private: bool m_interactive; std::string m_outputDir; // Helper methods void SaveScreenshot(void* renderer, const std::string& filename); void* CreatePointCloudActor(const SVzNLPointXYZ* points, int count, double r, double g, double b, double pointSize); void* CreateEllipseActor(const SHoleResult& hole, double r, double g, double b); void* CreatePlaneActor(const SHoleResult& hole, double size, double r, double g, double b); }; /** * @brief Load extreme points from CSV and verify via FitHoleFromExtremePoints * * @param [in] csvPath Path to CSV file saved by VisualizeDetectionPipeline * @param [in] points Original point cloud (grid format, needed for plane fitting) * @param [in] rows Number of rows * @param [in] cols Number of columns * @param [in] detectionParams Detection parameters * @param [in] filterParams Filter parameters * @param [out] outHole Fitted hole result if successful * @return true on success, false on failure */ bool VerifyExtremePointsFromFile( const std::string& csvPath, const SVzNLPointXYZ* points, int rows, int cols, const SHoleDetectionParams& detectionParams, const SHoleFilterParams& filterParams, SHoleResult& outHole ); #endif // HOLE_DETECTION_VISUALIZER_H