CGAL:如何在加载 .off 文件后访问顶点颜色?
CGAL: How can I access vertex colors after loading an .off file?
加载 .off 文件很容易:
typedef CGAL::Simple_cartesian<double> Kernel;
typedef CGAL::Surface_mesh<Kernel::Point_3> SurfaceMesh;
typedef CGAL::Polyhedron_3<Kernel> Polyhedron;
...
SurfaceMesh surface;
Polyhedron poly;
std::fstream inputOffFile( "myFile.off" );
inputOffFile >> poly;
CGAL::copy_face_graph( poly, surface);
然后,我可以通过以下方式迭代顶点坐标:
std::vector<float> verts;
for( SurfaceMesh::Vertex_index vi : surface.vertices() )
{
Point pt = surface.point( vi );
verts.push_back( pt.x() );
verts.push_back( pt.y() );
verts.push_back( pt.z() );
}
但是我怎样才能访问存储在 .off 文件中的顶点颜色呢?
编辑:可能 CGAL::copy_face_graph 没有复制颜色 属性,所以我想我需要一个不同的方法?
您需要使用 SurfaceMesh 的 属性 贴图。当且仅当 OFF 文件有颜色(意味着第一个指示是 COFF 而不是第一行的 OFF),并且每个顶点都有颜色而不仅仅是每个面,那么你的 SurfaceMesh 将有一个内部 属性 贴图称为 "v:color"。您可以通过调用
访问它
SurfaceMesh::Property_map<SurfaceMesh::Vertex_index, CGAL::Color> vcolors =
surface.property_map<SurfaceMesh::Vertex_index, CGAL::Color >("v:color").first;
for( SurfaceMesh::Vertex_index vi : surface.vertices() )
{
CGAL::Color ci = vcolors[vi];
}
如果每个面都有颜色,您可以类似地访问它,但是通过搜索名为 "f:color" 的 属性 地图。您可以使用 surface.property_map<......>(...).second.
检查地图是否存在
好的,这是完整的解决方案,包括访问面顶点(如果您想通过 OpenGL 渲染网格,则需要)。使用 SurfaceMesh 是关键。
...
std::vector<Point> verts;
std::vector<Color> cols;
SurfaceMesh::Property_map<SurfaceMesh::Vertex_index, CGAL::Color> vcolors =
m_pSurface->property_map<SurfaceMesh::Vertex_index, CGAL::Color >( "v:color" ).first;
bool colorExists = m_pSurface->property_map<SurfaceMesh::Vertex_index, CGAL::Color>( "v:color" ).second;
if( !colorExists )
Error();
for( SurfaceMesh::Vertex_index vi : m_pSurface->vertices() )
{
cols.push_back( vcolors[ vi ] );
verts.push_back( m_pSurface->point( vi ) );
}
for( SurfaceMesh::Face_index face_index : m_pSurface->faces() )
{
CGAL::Vertex_around_face_circulator<SurfaceMesh> vcirc( m_pSurface->halfedge( face_index ), *m_pSurface ), done( vcirc );
signed char count = 0;
do
{
count++;
uint32_t vertexI = *vcirc++;
const Point &pt = verts[ vertexI ];
const Color &col = cols[ vertexI ];
...
} while( vcirc != done );
}
非常感谢有用的评论!
加载 .off 文件很容易:
typedef CGAL::Simple_cartesian<double> Kernel;
typedef CGAL::Surface_mesh<Kernel::Point_3> SurfaceMesh;
typedef CGAL::Polyhedron_3<Kernel> Polyhedron;
...
SurfaceMesh surface;
Polyhedron poly;
std::fstream inputOffFile( "myFile.off" );
inputOffFile >> poly;
CGAL::copy_face_graph( poly, surface);
然后,我可以通过以下方式迭代顶点坐标:
std::vector<float> verts;
for( SurfaceMesh::Vertex_index vi : surface.vertices() )
{
Point pt = surface.point( vi );
verts.push_back( pt.x() );
verts.push_back( pt.y() );
verts.push_back( pt.z() );
}
但是我怎样才能访问存储在 .off 文件中的顶点颜色呢?
编辑:可能 CGAL::copy_face_graph 没有复制颜色 属性,所以我想我需要一个不同的方法?
您需要使用 SurfaceMesh 的 属性 贴图。当且仅当 OFF 文件有颜色(意味着第一个指示是 COFF 而不是第一行的 OFF),并且每个顶点都有颜色而不仅仅是每个面,那么你的 SurfaceMesh 将有一个内部 属性 贴图称为 "v:color"。您可以通过调用
访问它SurfaceMesh::Property_map<SurfaceMesh::Vertex_index, CGAL::Color> vcolors =
surface.property_map<SurfaceMesh::Vertex_index, CGAL::Color >("v:color").first;
for( SurfaceMesh::Vertex_index vi : surface.vertices() )
{
CGAL::Color ci = vcolors[vi];
}
如果每个面都有颜色,您可以类似地访问它,但是通过搜索名为 "f:color" 的 属性 地图。您可以使用 surface.property_map<......>(...).second.
检查地图是否存在好的,这是完整的解决方案,包括访问面顶点(如果您想通过 OpenGL 渲染网格,则需要)。使用 SurfaceMesh 是关键。
...
std::vector<Point> verts;
std::vector<Color> cols;
SurfaceMesh::Property_map<SurfaceMesh::Vertex_index, CGAL::Color> vcolors =
m_pSurface->property_map<SurfaceMesh::Vertex_index, CGAL::Color >( "v:color" ).first;
bool colorExists = m_pSurface->property_map<SurfaceMesh::Vertex_index, CGAL::Color>( "v:color" ).second;
if( !colorExists )
Error();
for( SurfaceMesh::Vertex_index vi : m_pSurface->vertices() )
{
cols.push_back( vcolors[ vi ] );
verts.push_back( m_pSurface->point( vi ) );
}
for( SurfaceMesh::Face_index face_index : m_pSurface->faces() )
{
CGAL::Vertex_around_face_circulator<SurfaceMesh> vcirc( m_pSurface->halfedge( face_index ), *m_pSurface ), done( vcirc );
signed char count = 0;
do
{
count++;
uint32_t vertexI = *vcirc++;
const Point &pt = verts[ vertexI ];
const Color &col = cols[ vertexI ];
...
} while( vcirc != done );
}
非常感谢有用的评论!