iOS-OpenGL ES 体验(一)

之前一直都听说OpenGL ES是一个很错的框架,但是公司开发的项目中没有用到这个技术,所以就没有太过研究它。这个框架是苹果封装的OpenG,底层用C语言实现,所以玩起来有点复杂!现在有闲暇时间就研究下这个框架,第一次用OpenGL ES渲染一张图片(纹理),以后会持续更新。

1.GLKViewController & GLKView

首先需要导入头文件

#import

让我们的viewConreoller继承于GLKViewController

// 修改继承关系
@interface ViewController : GLKViewController
@interface ViewController ()<GLKViewDelegate>
{
    // 上下文
    EAGLContext *context;
    // 着色器或者光照
    GLKBaseEffect *effect;    
    // 顶点数量
    int vertexCount;
}
@end

2.创建OpenGL ES上下文EAGLContext

- (void)setupConfig
{
    context = [[EAGLContext alloc]initWithAPI:kEAGLRenderingAPIOpenGLES3];
    if (context == nil) {
        NSLog(@"Failed to creat ES context");
        return;
    }
    GLKView *view = (GLKView *)self.view;
    view.context = context;
    view.drawableColorFormat = GLKViewDrawableColorFormatRGBA8888;
    //view.drawableDepthFormat = GLKViewDrawableDepthFormat24;

    // 设置当前content
    [EAGLContext setCurrentContext:context];

    // 开启深度测试,让离得近的物体可以遮挡离得远的物体
   glEnable(GL_DEPTH_TEST);
   glClearColor(0.0f, 0.0f, 0.0f, 1.0f);

}

想了解更多关于EAGLContext。

3.加载顶点数据

- (void)uploadVertexArray
{
    // 顶点数据,前三个是顶点坐标,后面两个是纹理坐标
    // 居中展示
    GLfloat vertexData[] =
    {
       0.5f,-0.5f,0.0f,     1.0f,0.0f, // 右下
       0.5f,0.5f,0.0f,      1.0f,1.0f, // 右上
       -0.5f,0.5f,0.0f,     0.0f,1.0f, // 左上

       0.5f,-0.5f,0.0f,     1.0f,0.0f, // 右下
       -0.5f,0.5f,0.0f,     0.0f,1.0f, // 左上
       -0.5f,-0.5f,0.0f,    0.0f,0.0f, // 左下
    };
    // 顶点数
    vertexCount = 6;

    // 缓存区
    GLuint buffer;
    // 申请一个缓冲区
    glGenBuffers(1, &buffer);

    glBindBuffer(GL_ARRAY_BUFFER, buffer);

    // 把顶点数据从CPU传到GPU
    glBufferData(GL_ARRAY_BUFFER, sizeof(vertexData), vertexData, GL_STATIC_DRAW);

    // 交给顶点
    glEnableVertexAttribArray(GLKVertexAttribPosition);

    // 读取顶点数据交给GLKVertexAttribPosition
    glVertexAttribPointer(GLKVertexAttribPosition,
                          3,// 3个顶点数据
                          GL_FLOAT,
                          GL_FALSE,
                          sizeof(GLfloat) * 5,// 偏移量5
                          (GLfloat *)NULL);

    // 纹理
    glEnableVertexAttribArray(GLKVertexAttribTexCoord0);

    // 读取纹理数据,交给GLKVertexAttribTexCoord0
    glVertexAttribPointer(GLKVertexAttribTexCoord0,
                          2,// 2个纹理
                          GL_FLOAT,
                          GL_FALSE,
                          sizeof(GLfloat) * 5,// 偏移量5
                          (GLfloat *)NULL + 3);


}

注意:

  1. 顶点坐标,OpenGL ES的坐标系是[-1, 1],屏幕中心点坐标(0, 0)。
  2. 纹理坐标系的取值范围是[0, 1],原点(0, 0)在左下角,点(1, 1)在右上角。你想修改渲染纹理的效果,只需要修改相对应的纹理坐标即可,我在Demo里面都有写到。

3.加载纹理,创建着色器

- (void)uploadTexture
{
    // Texture:纹理
    // 获取纹理(图片)保存路径
    NSString *filePath = [[NSBundle mainBundle] pathForResource:@"111" ofType:@"jpg"];

    // 读取纹理,纹理是倒的,要从左下角开始
    NSDictionary *options = [NSDictionary dictionaryWithObjectsAndKeys:@(1),GLKTextureLoaderOriginBottomLeft, nil];
    GLKTextureInfo *textureInfo = [GLKTextureLoader textureWithContentsOfFile:filePath options:options error:nil];

    // 创建着色器
    effect = [[GLKBaseEffect alloc] init];
    effect.texture2d0.enabled = GL_TRUE;
    effect.texture2d0.name = textureInfo.name;

}

注意:纹理是倒的,再读取的时候要从左下方开始(GLKTextureLoaderOriginBottomLeft)。

4.GLKViewDelegate代理方法回调

// 场景数据变化
- (void)update {
    //NSLog(@"upload");
}

// 渲染场景代码
- (void)glkView:(GLKView *)view drawInRect:(CGRect)rect
 { 
    glClearColor(1.0f, 1.0f, 1.0f, 1.0f);
    glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

    //启动着色器
    [effect prepareToDraw];

    // triangle 三角形
    glDrawArrays(GL_TRIANGLES, 0, vertexCount);
    //glDrawElements(GL_TRIANGLES, vertexCount, GL_UNSIGNED_INT, 0);
}

这有几篇相关博客可以参考:详解第一个OpenGL程序,西蒙iPhone-OpenGL ES 中文教程专题。

本文只是初步简单的使用OpenGL ES ,渲染一张图片,里面有许多的参数、方法等我们看上去很奇怪,这是因为我们玩的少。如果深研究的话,其实要先去研究OpenGL,然后再来学OpenGL ES就简单多了。上面是我自己参考别的技术博客写的代码,可能有些问题,希望大家能多提建议,共同进步!关于OpenGL ES我会持续更新博客。

Demo下载地址

你可能感兴趣的:(技术类博客)