如何在 CGAL 中更新已修改人脸的人脸信息

问题描述 投票:0回答:0

让我们考虑使用 CGAL 的二维约束 Delaunay 三角剖分。

在这个小例子中,我考虑了一组由 5 个 5 个点组成的正方形。点的“内部正方形”将在三角剖分中受到约束。

我需要在 CGAL 的脸上存储一些数据。我用这个

Triangulation_face_base_with_info_2
。在下面的代码片段中,数据只是一个
double
,如果我们在“内部正方形”内则为 1,否则为 0,在我的实际项目中,这是一个计算成本更高的数据。

在代码片段的第一步中,三角测量和数据被初始化,我们得到以下内容(红色 -> 1,紫色 -> 0):

现在让我们在“内部正方形”内添加一个点,看看存储的数据发生了什么:

编辑:现在让我们删除中心的点:

现在问题来了:有没有一种方法,当adding or removing a point from the triangulation, to obtain modified faces list to update their data (stored in a face's info) and keep the old data in未修改的面孔,而不是再次遍历整个面孔列表(这会很昂贵)?

#include <iostream>
#include <CGAL/Exact_predicates_inexact_constructions_kernel.h>
#include <CGAL/Triangulation_face_base_with_info_2.h>
#include <CGAL/Triangulation_vertex_base_with_info_2.h>
#include <CGAL/Delaunay_mesh_face_base_2.h>
#include <CGAL/Constrained_Delaunay_triangulation_2.h>

struct FaceInfo
{
    double superComplexData = 0.0;
};

typedef CGAL::Exact_predicates_inexact_constructions_kernel            K;
typedef K::FT                                                          FT;
typedef CGAL::Triangulation_face_base_with_info_2<FaceInfo, K>         Fb2;
typedef CGAL::Triangulation_vertex_base_with_info_2<std::size_t, K>    Vb2;
typedef CGAL::Constrained_triangulation_face_base_2<K, Fb2>            CFb2;
typedef CGAL::Triangulation_data_structure_2<Vb2,CFb2>                 Tds2;
typedef CGAL::Constrained_Delaunay_triangulation_2<K,Tds2>             Triangulation_2;
typedef K::Point_2                                                     Point_2;

int main()
{
    // Part 0: initialize the triangulation 
    std::vector<std::pair<Point_2, std::size_t>> pointsList {
        //Outer points
        {Point_2(0.0, 0.0), 0},
        {Point_2(1.0, 0.0), 1},
        {Point_2(2.0, 0.0), 2},
        {Point_2(3.0, 0.0), 3},
        {Point_2(4.0, 0.0), 4},
        {Point_2(0.0, 1.0), 5},
        {Point_2(0.0, 2.0), 6},
        {Point_2(0.0, 3.0), 7},
        {Point_2(0.0, 4.0), 8},
        {Point_2(1.0, 4.0), 9},
        {Point_2(2.0, 4.0), 10},
        {Point_2(3.0, 4.0), 11},
        {Point_2(4.0, 4.0), 12},
        {Point_2(4.0, 3.0), 13},
        {Point_2(4.0, 2.0), 14},
        {Point_2(4.0, 1.0), 15},
        //Inner points (constraint)
        {Point_2(1.0, 1.0), 16},
        {Point_2(2.0, 1.0), 17},
        {Point_2(3.0, 1.0), 18},
        {Point_2(1.0, 2.0), 19},
        {Point_2(1.0, 3.0), 20},
        {Point_2(2.0, 3.0), 21},
        {Point_2(3.0, 3.0), 22},
        {Point_2(3.0, 2.0), 23},
        {Point_2(3.0, 1.0), 24},
        //Center point
        {Point_2(2.0, 2.0), 25}
    };

    std::vector<std::pair<Point_2, Point_2>> constraintsList {
        {Point_2(1.0, 1.0), Point_2(2.0, 1.0)},
        {Point_2(2.0, 1.0), Point_2(3.0, 1.0)},
        {Point_2(3.0, 1.0), Point_2(3.0, 2.0)},
        {Point_2(3.0, 2.0), Point_2(3.0, 3.0)},
        {Point_2(3.0, 3.0), Point_2(2.0, 3.0)},
        {Point_2(2.0, 3.0), Point_2(1.0, 3.0)},
        {Point_2(1.0, 3.0), Point_2(1.0, 2.0)},
        {Point_2(1.0, 2.0), Point_2(1.0, 1.0)},
    };

    Triangulation_2 cdt;
    cdt.insert_constraints(constraintsList.begin(), constraintsList.end());
    cdt.insert(pointsList.begin(), pointsList.end());

    // Part 1: face data is 1 inside the "inner square" 
    for(auto fit = cdt.finite_faces_begin(); fit < cdt.finite_faces_end() ; ++fit)
    {
        Triangulation_2::Face_handle face {fit};
        Point_2 centroid = CGAL::centroid(face->vertex(0)->point(), face->vertex(1)->point(), face->vertex(2)->point());
        if(centroid.x() > 1.0 && centroid.x() < 3.0 && centroid.y() > 1.0 && centroid.y() < 3.0)
            face->info().superComplexData = 1.0; //Normally super complex function
    }

    std::size_t counter = 0;
    for(auto fit = cdt.finite_faces_begin(); fit < cdt.finite_faces_end() ; ++fit)
    {
        Triangulation_2::Face_handle face {fit};
        std::cout << counter<< ": " << face->info().superComplexData << ": "
                  << face->vertex(0)->point() << ", " << face->vertex(1)->point() << ", " << face->vertex(2)->point() << ", " << std::endl;
        counter++;
    }

    // Part 2: add point and check face data
    Point_2 pointToAdd = Point_2(1.5, 1.5);
    Triangulation_2::Vertex_handle vh = cdt.insert(pointToAdd);
    vh->info() = pointsList.size();
    pointsList.push_back({pointToAdd, vh->info()});

    // EDIT: Part 3: remove point at he center
    for(auto vit = cdt.finite_vertices_begin() ; vit < cdt.finite_vertices_end() ; ++vit)
    {
        if(vit->point().x() > 1.9 && vit->point().x() < 2.1 && vit->point().y() > 1.9 && vit->point().y() < 2.1)
            cdt.remove(vit);
    }

    counter = 0;
    for(auto fit = cdt.finite_faces_begin(); fit < cdt.finite_faces_end() ; ++fit)
    {
        Triangulation_2::Face_handle face {fit};
        std::cout << counter<< ": " << face->info().superComplexData << ": "
                  << face->vertex(0)->point() << ", " << face->vertex(1)->point() << ", " << face->vertex(2)->point() << ", " << std::endl;
        counter++;
    }

    return 0;
}
c++ cgal
© www.soinside.com 2019 - 2024. All rights reserved.