美文网首页
OpenGLES(三)- GLKit: 多边形纹理、旋转

OpenGLES(三)- GLKit: 多边形纹理、旋转

作者: Henry________ | 来源:发表于2020-08-04 11:18 被阅读0次

    OpenGLES(三)- GLKit: 多边形纹理、旋转

    本文中会省略关于GLKit最基本的API的注释,如果需要详细注释可以看另一篇OpenGLES(二)- 纹理贴图

    展示效果

    • 在本案例中增加了固定光源,让物体更加逼真。
    1. 上下文创建

    不同于上文中的GLKView的创建方式。使用这种initWithFrame方式可以不用依赖GLKViewController。

        content = [[EAGLContext alloc] initWithAPI:kEAGLRenderingAPIOpenGLES3];
        if(!content){return;}
        [EAGLContext setCurrentContext:content];
        
    //GLKView创建
        glkView = [[GLKView alloc] initWithFrame:CGRectMake(0, 100, UIScreen.mainScreen.bounds.size.width, UIScreen.mainScreen.bounds.size.height) context:content];
    //必须注册代理
        glkView.delegate = self;
        self.view = glkView;
        
        glkView.drawableColorFormat = GLKViewDrawableColorFormatRGBA8888;
        glkView.drawableDepthFormat = GLKViewDrawableDepthFormat24;
        glClearColor(0.3, 0.1, 0.7, 1.0f);
        
    //这里相当于翻转 z 轴,使正方形朝屏幕外
        glDepthRangef(1, 0);
    /*
        //默认(0, 1)正方形朝屏幕内
        glDepthRangef(0, 1);
     */
    
    2.顶点创建

    正方形6个面,每个面由2个三角形组成,所以一共需要36个顶点。

    // 具体36个点的信息就不放出来了
        vertexs = malloc(sizeof(HRVertex) * 36);
    // 创建帧缓存区
        GLuint bufferId;
        glGenBuffers(1, &bufferId);
        glBindBuffer(GL_ARRAY_BUFFER, bufferId);
        glBufferData(GL_ARRAY_BUFFER, sizeof(HRVertex) * 36, vertexs, GL_STATIC_DRAW);
    
    //将顶点、纹理坐标、法线传入顶点着色器
      glEnableVertexAttribArray(GLKVertexAttribPosition);
      glVertexAttribPointer(GLKVertexAttribPosition, 3, GL_FLOAT, GL_FALSE, sizeof(HRVertex), NULL + offsetof(HRVertex, positionCoord));
        
      glEnableVertexAttribArray(GLKVertexAttribTexCoord0);
      glVertexAttribPointer(GLKVertexAttribTexCoord0, 2, GL_FLOAT, GL_FALSE, sizeof(HRVertex), NULL + offsetof(HRVertex, textureCoord));
        
      glEnableVertexAttribArray(GLKVertexAttribNormal);
      glVertexAttribPointer(GLKVertexAttribNormal, 3, GL_FLOAT, GL_FALSE, sizeof(HRVertex), NULL + offsetof(HRVertex, normal));
    
    • 法线: 垂直于一个平面的向量,可以用于反射光线的计算。法线是通过计算两个向量的叉乘来得到。
    • 向量A X 向量B = (AyBz-AzBy,AxBz-AzBx,AxBy-AyBx)
    3. 效果器创建、纹理图片加载
        NSString *file = [[NSBundle mainBundle] pathForResource:@"cat" ofType:@"jpg"];
        UIImage *image = [UIImage imageWithContentsOfFile:file];
        NSDictionary *option = @{GLKTextureLoaderOriginBottomLeft: @(YES)};
        
        GLKTextureInfo *info = [GLKTextureLoader textureWithCGImage:[image CGImage] options:option error:nil];
        
        effect = [[GLKBaseEffect alloc] init];
        effect.texture2d0.enabled = YES;
        effect.texture2d0.name = info.name;
        effect.texture2d0.target = info.target;
        //创建光线
        effect.light0.enabled = YES;
        //反射光线颜色
        effect.light0.diffuseColor = GLKVector4Make(1, 1, 1, 1);
        //光源位置
        effect.light0.position = GLKVector4Make(-0.5, 0.5, 5, 1);
    
    • baseEffect中可以支持3个默认光源。
    4. CADisplayLink创建
    disLink = [CADisplayLink displayLinkWithTarget:self selector:@selector(update)];
    
    [disLink addToRunLoop:[NSRunLoop mainRunLoop] forMode:NSRunLoopCommonModes];
    
    -(void)update{
        //1.计算旋转度数
        angle = (angle + 1) % 360;
        //2.修改baseEffect.transform.modelviewMatrix,完成旋转的视图变换
        effect.transform.modelviewMatrix = GLKMatrix4MakeRotation(GLKMathDegreesToRadians(angle), 0.3, 0.5, 0.7);
        //3.重新渲染
        [glkView display];
    }
    
    5. 代理
    - (void)glkView:(GLKView *)view drawInRect:(CGRect)rect{
        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
        glEnable(GL_DEPTH_TEST);
        [effect prepareToDraw];
        
        glDrawArrays(GL_TRIANGLES, 0, 36);
    }
    
    6. dealloc(销毁)
    - (void)dealloc
    {
        //displayLink 失效
        [disLink invalidate];
        disLink = nil;
        
        //重置content
        if ([EAGLContext currentContext] == [(GLKView *)self.view context] ) {
            [EAGLContext setCurrentContext:nil];
        }
        
        //顶点数组重置
        if(vertexs){
            free(vertexs);
            vertexs = nil;
        }
    }
    
    demo地址: GLKit-002GLKit物体旋转

    相关文章

      网友评论

          本文标题:OpenGLES(三)- GLKit: 多边形纹理、旋转

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