前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >OpenGLES(七)-GLSL案例:纹理颜色混合OpenGLES(七)-GLSL案例:纹理颜色混合

OpenGLES(七)-GLSL案例:纹理颜色混合OpenGLES(七)-GLSL案例:纹理颜色混合

作者头像
用户8893176
发布2021-08-09 11:18:50
6150
发布2021-08-09 11:18:50
举报
文章被收录于专栏:小黑娃Henry

OpenGLES(七)-GLSL案例:纹理颜色混合

首先放出效果

效果图

原图:

原图

通过对比可以看出纹理和颜色进行了混合效果,下面就放出实现过程.

  1. vsh
代码语言:javascript
复制
attribute vec4 position;
attribute vec4 positionColor;
attribute vec2 textureCoord;

varying lowp vec2 varyingTexCoord;
varying vec4 varyingColor;

void main() {
    varyingColor = positionColor;
    varyingTexCoord = textureCoord;
    gl_Position = position;
}
  • 由于片元着色器无法接受外部的顶点数据和顶点颜色,当然可以通过uniform关键词,直接将混合颜色传入片元着色器。
  • fsh
代码语言:javascript
复制
precision highp float;
varying lowp vec2 varyingTexCoord;
varying vec4 varyingColor;
uniform sampler2D colorMap;
uniform lowp float alpha;

void main() {
    vec4 vTexColor = texture2D(colorMap, varyingTexCoord);
    vec4 vColor = varyingColor;
    gl_FragColor = vTexColor * (1.0 - alpha) + vColor * alpha;
}
  • 可以看到在获取的纹理中的纹素之后并没有直接传递给内奸变量gl_FragColor,而是进行了计算vTexColor * (1.0 - alpha) + vColor * alpha
  • 如果纹理和颜色都是不透明的,则无法进行混合,只会进行覆盖.所以我们自定义了一个透明度。
  • 这里的计算公式是根据OpenGL中的颜色混合参数得到的:glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA),如果对这个公式陌生可以看看这篇文章:OpenGL(七)- 渲染技巧:颜色混合
  • content、layer、renderbuffer、framebuffer、shader初始化,图片加载都与这篇文章一致.传送门
  • render放出最核心的代码
代码语言:javascript
复制
    //初始化s顶点缓存区
    GLuint buffer;
    glGenBuffers(1, &buffer);
    glBindBuffer(GL_ARRAY_BUFFER, buffer);
    glBufferData(GL_ARRAY_BUFFER, sizeof(vertex), &vertex, GL_DYNAMIC_DRAW);
    //将顶点数据传入着色器
    GLuint position = glGetAttribLocation(self.myProgram, "position");
    glEnableVertexAttribArray(position);
    glVertexAttribPointer(position, 3, GL_FLOAT, GL_FALSE, sizeof(GLfloat) * 8, (GLfloat*)NULL + 0);
    //将纹理坐标传入着色器
    GLuint texCoord = glGetAttribLocation(self.myProgram, "textureCoord");
    glEnableVertexAttribArray(texCoord);
    glVertexAttribPointer(texCoord, 2, GL_FLOAT, GL_FALSE, sizeof(GLfloat) * 8, (GLfloat*)NULL + 3);
    //将颜色传入着色器
    GLuint positionColor = glGetAttribLocation(self.myProgram, "positionColor");
    glEnableVertexAttribArray(positionColor);
    glVertexAttribPointer(positionColor, 3, GL_FLOAT, GL_FALSE, sizeof(GLfloat) * 8, (GLfloat*)NULL + 5);

    //加载纹理并传入片元着色器
    GLuint texture = [self loadImage];
    glActiveTexture(texture);
    glUniform1i(glGetUniformLocation(self.myProgram, "colorMap"), 0);
    glUniform1f(glGetUniformLocation(self.myProgram, "alpha"), 0.3);
    //使用索引绘图
    glDrawElements(GL_TRIANGLES, sizeof(indices) / sizeof(indices[0]), GL_UNSIGNED_INT, indices);
    
    [self.myContent presentRenderbuffer:GL_RENDERBUFFER];
  • 与之前的纹理加载相比,代码上只是多传了一组颜色值,别无其他区别
如果想要了解索引绘图和顶点绘图的区别可以移步:OpenGLES(六)-综合案例:索引绘图(https://cloud.tencent.com/developer/article/1857995

完整DEMO地址: Github

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2020/8/16 下,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • OpenGLES(七)-GLSL案例:纹理颜色混合
    • 完整DEMO地址: Github
    领券
    问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档