/**
 * @class    operation_mesh
 *
 * @author   Astrid BEYER
 * @date     2023
 * @version  1.2
 *
 */

#ifndef OPERATION_MESH_H
#define OPERATION_MESH_H

#include <vtkTriangleFilter.h>

namespace operation
{
    /**
     * @brief   buildValidTriangulation : transforms, if necessary, input's polyData so it ensure it's triangulated
     * @param   polyData
     * @returns vtkSmartPointer<vtkPolyData>
     */
    vtkSmartPointer<vtkPolyData> buildValidTriangulation(vtkSmartPointer<vtkPolyData> polyData);
    /**
     * @brief   closeMesh : close the surface of the mesh, if necessary
     * @param   polyData
     * @returns vtkSmartPointer<vtkPolyData>
     */
    vtkSmartPointer<vtkPolyData> closeMesh(vtkSmartPointer<vtkPolyData> polyData);

    /**
     * @brief   getDegree : returns number of neighbors a vertex belongs to
     * @param   source, point
     * @returns int
     */
    int getDegree(vtkSmartPointer<vtkPolyData> source, vtkIdType point);

    /**
     * @brief   getPointCells : get the identifiers of the vertices of a given cell
     * @param   polyData, pointId, cellIds
     * @returns void
     */
    void getPointCells(vtkPolyData *polyData, vtkIdType pointId, vtkIdList *cellIds);

    /**
     * @brief   computeTriangleArea : using formula for the half-sum of side lengths to calculate the area of a triangle
     * @param   p0, p1, p2
     * @returns double
     */
    double computeTriangleArea(const std::array<double, 3> &p0, const std::array<double, 3> &p1, const std::array<double, 3> &p2);

    vtkIdType getNeighborId(vtkSmartPointer<vtkPolyData> source, vtkIdType pointId);
    std::array<double, 3> computeCentroid(vtkSmartPointer<vtkPolyData> source, vtkIdType pointId1, vtkIdType pointId2);
}

#endif