美文网首页OpenGL ES
GLKit案例解析

GLKit案例解析

作者: 爱看书de图图 | 来源:发表于2020-07-28 17:13 被阅读0次

      接下来我们用一个案例,来使用GLKit绘制一个旋转的立方体。效果如下:

    GIF
      下面我会讲述一下案例流程,代码部分我只列出重要部分,完整案例可以查看Demo

    初始化

    初始化上下文EAGLContext,并设置为当前的上下文

    //1.创建context
    EAGLContext *context = [[EAGLContext alloc] initWithAPI:kEAGLRenderingAPIOpenGLES2];
    //设置当前context
    [EAGLContext setCurrentContext:context];
    

    初始化GLKView对象,并设置相关属性。

    self.glkView = [[GLKView alloc] initWithFrame:frame context:context];
    //3.使用深度缓存
    self.glkView.drawableDepthFormat = GLKViewDrawableDepthFormat24;
    

    初始化纹理对象GLKTextureInfo,之前的文章里,我们讲述了各种生成纹理对象的方法,这里我们用CGImage对象来生成。

    GLKTextureInfo *textureInfo = [GLKTextureLoader textureWithCGImage:[image CGImage]
                                                                   options:options
                                                                     error:NULL];
    

    初始化着色器GLKBaseEffect,并将纹理对象的名字赋值给着色器

    self.baseEffect = [[GLKBaseEffect alloc] init];
    self.baseEffect.texture2d0.name = textureInfo.name;
    self.baseEffect.texture2d0.target = textureInfo.target;
    //开启光照效果
    self.baseEffect.light0.enabled = YES;
    //漫反射颜色
    self.baseEffect.light0.diffuseColor = GLKVector4Make(1, 1, 1, 1);
    //光源位置
    self.baseEffect.light0.position = GLKVector4Make(-0.5, -0.5, 5, 1);
    

    设置顶点数组,我们这里使用结构体来存放顶点坐标,纹理坐标,以及光照坐标。只列出一个前面的一个面来说明各个坐标的设置。

    typedef struct {
        GLKVector3 positionCoord;   //顶点坐标
        GLKVector2 textureCoord;    //纹理坐标
        GLKVector3 normal;          //法线
    } CCVertex;
        // 前面
        self.vertices[0] = (CCVertex){{-0.5, 0.5, 0.5}, {0, 1}, {0, 0, 1}};
        self.vertices[1] = (CCVertex){{-0.5, -0.5, 0.5}, {0, 0}, {0, 0, 1}};
        self.vertices[2] = (CCVertex){{0.5, 0.5, 0.5}, {1, 1}, {0, 0, 1}};
        self.vertices[3] = (CCVertex){{-0.5, -0.5, 0.5}, {0, 0}, {0, 0, 1}};
        self.vertices[4] = (CCVertex){{0.5, 0.5, 0.5}, {1, 1}, {0, 0, 1}};
        self.vertices[5] = (CCVertex){{0.5, -0.5, 0.5}, {1, 0}, {0, 0, 1}};
    

    然后开辟顶点缓冲区,绑定顶点数组,之前说到iOS默认关闭attribute通道,所以我们需要手动开启,并且相关的参数意义在我们之前的文章里都有描述,这里不再赘述。

    //开辟顶点缓存区
    glGenBuffers(1, &_vertexBuffer);
    glBindBuffer(GL_ARRAY_BUFFER, _vertexBuffer);
    GLsizeiptr bufferSizeBytes = sizeof(CCVertex) * kCoordCount;
    glBufferData(GL_ARRAY_BUFFER, bufferSizeBytes, self.vertices, GL_STATIC_DRAW);
    //顶点数据
    glEnableVertexAttribArray(GLKVertexAttribPosition);
    glVertexAttribPointer(GLKVertexAttribPosition, 3, GL_FLOAT, GL_FALSE, sizeof(CCVertex), NULL + offsetof(CCVertex, positionCoord));
    //纹理数据
    glEnableVertexAttribArray(GLKVertexAttribTexCoord0);
    glVertexAttribPointer(GLKVertexAttribTexCoord0, 2, GL_FLOAT, GL_FALSE, sizeof(CCVertex), NULL + offsetof(CCVertex, textureCoord));
    //法线数据
    glEnableVertexAttribArray(GLKVertexAttribNormal);
    glVertexAttribPointer(GLKVertexAttribNormal, 3, GL_FLOAT, GL_FALSE, sizeof(CCVertex), NULL + offsetof(CCVertex, normal));
    

    让立方体自动旋转需要设置定时器,这里可以自由发挥,比较简单,需要注意在代理方法里,开启关闭深度测试,准备绘制等。

    //1.开启深度测试
    glEnable(GL_DEPTH_TEST);
    //2.清除颜色缓存区&深度缓存区
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
    //3.准备绘制
    [self.baseEffect prepareToDraw];
    //4.绘图
    glDrawArrays(GL_TRIANGLES, 0, kCoordCount);
    

    相关文章

      网友评论

        本文标题:GLKit案例解析

        本文链接:https://www.haomeiwen.com/subject/xsnfrktx.html