首先网格化的步骤为(代码示意)
GLUtesselator *pTessLator;
pTessLator=gluNewTess(); //创建网格化对象
gluTessCallback(pTessLator,GLU_TESS_BEGIN,(void (__stdcall *)())glBegin);//设置回调函数
gluTessCallback(pTessLator,GLU_TESS_END,(void (__stdcall *)())glEnd);
gluTessCallback(pTessLator,GLU_VERTEX,(void (__stdcall *)())glVertex3dv);
gluTessCallback(pTessLator,GLU_TESS_ERROR,(void (__stdcall *)())TessError);
gluTessBeginPolygon(pTessLator,NULL);//开始一条曲线,后面逐一指定顶点,所以第二参数为空
gluTessBeginContour(pTessLator);
group=&(tess.groups[0]);
vector<VertexPoint>::iterator it;
GLdouble vertex[10][3];
int i=0;
for (it=group->vertexsArray.begin();it!=group->vertexsArray.end() ;it++)
{
VertexPoint vp=*it;
vertex[i][0]=vp.xyz[0];
vertex[i][1]=vp.xyz[1];
vertex[i][2]=vp.xyz[2];
gluTessVertex(pTessLator,vertex[i],vertex[i]);
}
gluTessEndContour(pTessLator);
gluTessEndPolygon(pTessLator);
gluDeleteTess(pTessLator);
上面代码正确执行了网格化
但是,上述代码中的红色代码片段。有以下五点:
1. 就是如果只有一个环绕,环绕上各个顶点在三维空间上应尽量处于同一个平面,否则可能看不到网格化结果(这里不解释网格化原理);如果存在多个环绕,相邻环绕可以处在同一平面,也可以不处在同一平面,但是他们之间的深度不能超过他们之间的平面宽度,否则也看不到多环绕的网格化结果。
2. 个就是顶点数组变量vertex,如果vertex的定义放在for循环里面,而且改成一维数组的形式,如下面代码所示
for (it=group->vertexsArray.begin();it!=group->vertexsArray.end() ;it++)
{
VertexPoint vp=*it;
GLdouble vertex[3]={vp.xyz[0],vp.xyz[1],vp.xyz[2]};
gluTessVertex(pTessLator,vertex,vertex);
}
顶点vertex就成了for循环里的局部变量,这时候不能进行网格化,运行看不到结果。原因就是gluTessVertex(pTessLator,vertex,vertex)的第三个参数是void* data类型的,它就是顶点数据来源,必须提供一个跟网格化对象pTessLator同作用域或者更大作用域的数据来源指针,以便回调传给glVertex函数绘制顶点,否则无法找到顶点渲染。
3. 在上面正确运行结果的代码里面,gluTessVertex(pTessLator,vertex[i],vertex[i])的第三个参数vertex[i]指定了顶点的数据来源,不一定要跟第二个参数一致,可以是vertex[(i+a)%N],其中a为任一正整数,N为分隔化曲线的顶点个数。如可以改为
gluTessVertex(pTessLator,vertex[i],vertex[(i+5)%10]);//加入顶点总数为10
程序运行结果正确
4.如果是多个环绕的网格化,相邻环绕各自环绕曲线上的顶点数可以不相等,如下图示,外环绕有是个控制顶点,内部则有五个

5.如果是多环绕,相邻环绕线不能有交叉,否则看不到结果

本文详细解析使用GLUTessellator进行网状化的基本步骤,并指出常见错误及其解决方法,包括如何正确处理顶点数组、多环绕情况下的顶点数不等、环绕线交叉等问题。
931

被折叠的 条评论
为什么被折叠?



