GLKit实战 第02话 三角形

整体步骤

绘制出一个图形,大体需要以下步骤:

  1. 创建上下文,并将其指定为当前的上下文
  2. 创建GLKBaseEffect对象,并对其进行相应的配置
  3. 创建并绑定VAO(vertex array object,顶点数组对象)
  4. 创建并绑定VBO(vertex buffer object,顶点缓冲区对象)
  5. 设置顶点数据
  6. 启用顶点属性,并告知其如何使用顶点数据
  7. 在进行每一帧的绘制时,先同步状态,也即调用GLKBaseEffectprepareToDraw方法
  8. 调用glDraw***函数进行绘制

其中,第3步,是被强烈建议使用的,这样可以提高性能,当然,也可以将其忽略。第4、5、6步,可以看作是一大步骤,它们必须都存在。

绘制三角形

先期准备

首先,会继承GLKViewController,并实现- (void)glkView:(GLKView *)view drawInRect:(CGRect)rect方法。

根据上面的步骤,必须有顶点数据才行,因此,先定义一个结构体,用来描述顶点,其中的position,代表了顶点的位置,它属于顶点的一个属性:

1
2
3
typedef struct Vertex {
GLKVector3 position;
} Vertex;

因为是绘制三角形,至少需要3个顶点,声明一个成员,用来存放顶点数据:

1
Vertex _vertices[3];

上下文

在视图加载完成后,创建出上下文对象,并将其指定为当前的上下文:

1
2
EAGLContext *glCtx = [[EAGLContext alloc] initWithAPI:kEAGLRenderingAPIOpenGLES2];
[EAGLContext setCurrentContext:glCtx];

切记!!!也必须将其赋给GLKViewcontext属性:

1
glView.context = glCtx;

GLKBaseEffect

考虑到目前的顶点只有位置数据,因此绘制出来的三角形将会是单色的。

useConstantColor被设置为GL_TRUE时,constantColor将会被用作每个顶点的颜色。当useConstantColor被设置为GL_FALSE时,则表明需要启用顶点颜色属性,并为每个顶点提供颜色数据。

GLKBaseEffect.h.jpg

默认情况下,useConstantColorGL_TRUEconstantColor为白色。为了明确,显式地为它们进行赋值。

1
2
3
self.effect = [[GLKBaseEffect alloc] init];
self.effect.useConstantColor = GL_TRUE;
self.effect.constantColor = GLKVector4Make(1.0f, 1.0f, 1.0f, 1.0f);

创建VBO,设置顶点数据

这一部分,将第4、5、6步放在一起。

创建VBO:

1
glGenBuffers(1, &_vbo);

绑定VBO:

1
glBindBuffer(GL_ARRAY_BUFFER, _vbo);

设置顶点数据:

1
2
3
4
_vertices[0].position = GLKVector3Make( 0.5f,  0.5f, 0.0f);
_vertices[1].position = GLKVector3Make(-0.5f, 0.5f, 0.0f);
_vertices[2].position = GLKVector3Make(-0.5f, -0.5f, 0.0f);
glBufferData(GL_ARRAY_BUFFER, sizeof(_vertices), _vertices, GL_STATIC_DRAW);

启用顶点的位置属性:

1
glEnableVertexAttribArray(GLKVertexAttribPosition);

告知顶点的位置属性,应该如何使用顶点数据:

1
glVertexAttribPointer(GLKVertexAttribPosition, 3, GL_FLOAT, GL_FALSE, sizeof(Vertex), NULL + offsetof(Vertex, position));

绘制

在绘制之前,可以设置一下清除色,也即背景颜色,默认情况下,为黑色。虽然绘制的三角形使用的是白色,背景色和三角形的颜色对比明显,可以忽略其设置,但,为了更明确,还是设置一下比较好。

1
glClearColor(0.0f, 0.0f, 0.0f, 1.0f);

- (void)glkView:(GLKView *)view drawInRect:(CGRect)rect方法中,先应用背景色,也即清除颜色缓冲区:

1
glClear(GL_COLOR_BUFFER_BIT);

然后,同步状态,并绘制三角形:

1
2
[self.effect prepareToDraw];
glDrawArrays(GL_TRIANGLES, 0, 3);

这样,一个单色的三角形就出来了。

Pure Triangle.png

彩色三角形

根据上文内容,可以知道,为了让三角形是彩色的,就需要启用顶点颜色属性,并为顶点提供不同的颜色数据。

修改GLKBaseEffect的配置:

1
self.effect.useConstantColor = GL_FALSE;

删除self.effect.constantColor = GLKVector4Make(1.0f, 1.0f, 1.0f, 1.0f);

其实,完全不用修改配置信息,因为,当启用顶点颜色属性,并提供颜色数据后,GLKBaseEffect中颜色相关的配置将会被忽略,也就是会失效。

修改Vertex结构体:

1
2
3
4
typedef struct Vertex {
GLKVector3 position;
GLKVector4 color;
} Vertex;

加入了color字段,用于表示顶点颜色。

配置顶点颜色数据:

在调用glBufferData之前,加入:

1
2
3
_vertices[0].color = GLKVector4Make(1.0f, 0.0f, 0.0f, 1.0f);
_vertices[1].color = GLKVector4Make(0.0f, 1.0f, 0.0f, 1.0f);
_vertices[2].color = GLKVector4Make(0.0f, 0.0f, 1.0f, 1.0f);

启用顶点颜色属性:

1
glEnableVertexAttribArray(GLKVertexAttribColor);

告知顶点的颜色属性,应该如何使用顶点数据:

1
glVertexAttribPointer(GLKVertexAttribColor, 3, GL_FLOAT, GL_FALSE, sizeof(Vertex), NULL + offsetof(Vertex, color));

这样,一个彩色的三角形就完成了:

Colorful Triangle.png


GLKit实战 第02话 三角形
https://daniate.github.io/2020/01/29/GLKit实战 第02话 三角形/
作者
Daniate
发布于
2020年1月29日
许可协议