项目需要对blender轮廓提取功能进行分析和提取:
从blender的基本操作入手学习如何建模和修改,发现在模型(object)状态下选中一个三维模型系统会自动产生该三维模型的投影轮廓,并且移动旋转视图等操作,轮廓图像都会实时修改,于是选择最有可能发现轮廓提取算法所在的选择视图操作相关代码进行跟踪学习。
发现:
绘制轮廓的入口点在:
BL_src : drawobject.c
static void draw_mesh_object_outline(Object *ob, DerivedMesh *dm)
调用的实际绘制函数为:
blenkenerl中cdderivedmesh.c
static void cdDM_drawEdges(DerivedMesh *dm, int drawLooseEdges)
{
CDDerivedMesh *cddm = (CDDerivedMesh*) dm;//利用了数据结构本身,使用了技巧进行类型转换,实现了多态性。
MVert *mvert = cddm->mvert;
MEdge *medge = cddm->medge;
int i;
glBegin(GL_LINES);
for(i = 0; i < dm->numEdgeData; i++, medge++) {
if((medge->flag&ME_EDGEDRAW)
&& (drawLooseEdges || !(medge->flag&ME_LOOSEEDGE))) {
glVertex3fv(mvert[medge->v1].co);
glVertex3fv(mvert[medge->v2].co);
}
}
glEnd();
}
调用这一段代码就实现了轮廓的绘制。但具体的medge->flag, dm , MVert, MEdge, mvert[medge->v1].co具体什么以及怎样计算得出的还不知道。
blenkenerl中
cdderivedmesh.h对CCDerivedMesh进行了详细的定义,以及接口函数的定义及实现
typedef struct {
DerivedMesh dm;
/* these point to data in the DerivedMesh custom data layers,
they are only here for efficiency and convenience **/
MVert *mvert;
MEdge *medge;
MFace *mface;
} CDDerivedMesh;
对于指定的网格
DerivedMesh *dm= mesh_get_derived_final(ob, get_viewedit_datamask());生成网格
实验测定程序的关键点在于
glVertex3fv(mvert[medge->v1].co);
glVertex3fv(mvert[medge->v2].co);
尤其是mvert[medge->v1].co是如何计算的,进一步说就是
CDDerivedMesh *cddm = (CDDerivedMesh*) dm中到底执行了什么操作,怎么进行的赋值。
因此对dm进行专项分析:
typedef struct MVert {
float co[3];
short no[3];
char flag, mat_nr;
} MVert;
typedef struct MEdge {
unsigned int v1, v2;
char crease, pad;
short flag;
} MEdge;
程序中dm 的来源:
drawview.c中drawview3dspace:
Base* base;
drawobject.c中draw_object:
Object* ob = base->object;
mymultmatrix(ob->obmat);
{
在这里对ob->obmat与当前视角矩阵进行相乘处理;
顺序是:
Mywindow.c中