0

我整天都在努力让一个物体正常点亮,但没有结果,所以我要在这里尝试。本质上,我正在尝试使对象看起来像这样:

我在 GLC 播放器中的 3D 模型的一部分(3D 模型查看器)

在我的程序中,它看起来像这样:

我的渲染器绘制的 3D 模型的一部分

这是我的背景:

glClearDepth(1.0);
glShadeModel(GL_SMOOTH);
glEnable(GL_DEPTH_TEST);
glEnable(GL_BLEND);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
glEnable(GL_LIGHTING);
glEnable(GL_LIGHT0);
glLight(GL_LIGHT0, GL_POSITION, {0, 5, 0, 1});
glDisable(GL_TEXTURE_2D);

我的材质/照明设置:

glMaterialf(GL_FRONT, GL_SHININESS, 10);

glLight(GL_LIGHT0, GL_AMBIENT, {0.1, 0.1, 0.1, 1.0});
glLight(GL_LIGHT0, GL_DIFFUSE, {0.2, 0.2, 0.2, 1.0});
glLight(GL_LIGHT0, GL_SPECULAR, {0.6, 0.6, 0.6, 1.0});

glMaterial(GL_FRONT, GL_AMBIENT, {1, 0.8078, 0});
glMaterial(GL_FRONT, GL_DIFFUSE, {1, 0.8078, 0});
glMaterial(GL_FRONT, GL_SPECULAR, {0.5, 0.5, 0.5});
glMaterial(GL_FRONT, GL_EMISSION, {0, 0, 0});

[为简单起见,我使用 {r, g, b, a} 来表示数组。我查找了用于绘制模型的实际值并将它们写入数组]

主要问题是,每当我的物体完全亮起时,所有东西都会“杂乱”在一起,形成环境色。不再有取决于碎片方向的更亮和更暗的部分,只有一大块纯色。

我已经在整个项目中搜索了我可能错过的 openGL 设置,但我发现的唯一内容就是您在上面看到的内容(省略了一些重置投影和模型视图矩阵的调用、清除屏幕和平移/旋转)。

我还尝试改变灯光和材料的值,但没有取得多大成功。改变环境颜色只会使整个模型变得更亮。我也试过移动灯。

编辑:根据要求,这是我存储和绘制模型的方式:

我从 OBJ 文件加载模型。我查看了文件本身,其中列出了法线。装载机也认识到这一点。

下面是它如何绘制 VBO:

glEnableClientState(GL_VERTEX_ARRAY);
glEnableClientState(GL_NORMAL_ARRAY);
glEnableClientState(GL_TEXTURE_COORD_ARRAY);
glBindBufferARB(GL_ARRAY_BUFFER_ARB, vertexBufferID);
glVertexPointer(3, GL_FLOAT, stride, 0 * 4);
glNormalPointer(GL_FLOAT, stride, 3 * 4);
glBindBufferARB(GL_ELEMENT_ARRAY_BUFFER_ARB, indexBufferID);
glDrawElements(GL_TRIANGLES, this.numberOfVertices, GL_UNSIGNED_INT, 0);

VBO 是交错的,格式类似于 [vertex, normal, vertex, normal, ..]。我在绘图代码中删除了一些打印调用,它设置了顶点和法线指针。因此,我很确定 VBO 本身已正确加载和绘制。

4

2 回答 2

2

它崩溃了,因为您启用了 texture_coord_array 客户端状态,因此它尝试访问 texcoord 指针处的任何内容,该指针为空。

于 2012-08-24T20:01:47.100 回答
1

所以有很多问题,答案往往出乎意料。第一部分是我用来确定如何设置 VBO 的数据指针的 switch 语句:

private void setDataPointers() {
    int stride = this.dataFormat.elementsPerVertex * 4;
    glVertexPointer(3, GL_FLOAT, stride, 0 * 4);
    switch(this.dataFormat)
    {
        case VERTICES_AND_TEXTURES:
            glTexCoordPointer(2, GL_FLOAT, stride, (3)*4);
        case VERTICES_AND_NORMALS:
            glNormalPointer(GL_FLOAT, stride, 3 * 4);
        case VERTICES_TEXTURES_NORMALS:
            glTexCoordPointer(2, GL_FLOAT, stride, 3 * 4);
            glNormalPointer(GL_FLOAT, stride, (3 + 3) * 4); 
    }
}

如您所见,休息时间;语句丢失。因此将设置顶点、法线和纹理指针。

其次,在绘制 VBO 时,启用了所有三种客户端模式:

glEnableClientState(GL_VERTEX_ARRAY);
glEnableClientState(GL_NORMAL_ARRAY);
glEnableClientState(GL_TEXTURE_COORD_ARRAY);

所以渲染器正在寻找不存在的纹理坐标,并以某种方式吐出奇怪的无光照几何体。

于 2012-08-24T20:10:42.380 回答