通过GLSL实现一个自动旋转的金字塔,并对金字塔进行 颜色和纹理 的混合。效果如下:
QQ20190615-104927-HD.gif整体流程与GLSL实现对Shader编译链接
里的Demo类似,区别是从顶点数据开始,顶点数据多了颜色值,并且需要对顶点数据进行计算,计算出投影视图矩阵并传给着色器程序。
所以需要在顶点着色器程序中添加三个变量:顶点颜色、模型视图矩阵、投影矩阵
attribute vec4 positionColor;
uniform lowp mat4 modelViewMatrix;
uniform lowp mat4 projectionMatrix;
1.准备顶点数据(这里使用索引绘图,每行8位分别对应 坐标 颜色 纹理坐标):
GLfloat attrArr[] =
{
-0.5f, 0.5f, 0.0f, 0.0f, 0.0f, 0.5f, 0.0f, 1.0f,//左上
0.5f, 0.5f, 0.0f, 0.0f, 0.5f, 0.0f, 1.0f, 1.0f,//右上
-0.5f, -0.5f, 0.0f, 0.5f, 0.0f, 1.0f, 0.0f, 0.0f,//左下
0.5f, -0.5f, 0.0f, 0.0f, 0.0f, 0.5f, 1.0f, 0.0f,//右下
0.0f, 0.0f, 1.0f, 1.0f, 1.0f, 1.0f, 0.5f, 0.5f,//顶点
};
//(2).索引数组
GLuint indices[] =
{
0, 3, 2,
0, 1, 3,
0, 2, 4,
0, 4, 1,
2, 3, 4,
1, 4, 3,
};
- 设置顶点颜色
//设置顶点颜色
GLuint positionColorLocation = glGetAttribLocation(self.myPrograme, "positionColor");
glEnableVertexAttribArray(positionColorLocation);
glVertexAttribPointer(positionColorLocation, 3, GL_FLOAT, GL_FALSE, sizeof(CGFloat) * 8, (CGFloat *)NULL + 3);
- 设置投影矩阵
GLuint projectionLocation = glGetUniformLocation(self.myPrograme, "projectionMatrix");
//获取透视矩阵
KSMatrix4 projectMatrix ;
ksMatrixLoadIdentity(&projectMatrix);
GLfloat w = self.bounds.size.width;
GLfloat h = self.bounds.size.height;
glViewport(0, 0, w, h);
ksPerspective(&projectMatrix, 30, w/h, 5, 100);
glUniformMatrix4fv(projectionLocation, 1, GL_FALSE, (GLfloat *)&projectMatrix.m[0][0]); //传递投影矩阵
- 获取模型视图矩阵
GLuint modelViewLocation = glGetUniformLocation(self.myPrograme, "modelViewMatrix");
//获取模型视图矩阵
KSMatrix4 modelViewMatrix;
ksMatrixLoadIdentity(&modelViewMatrix);
ksTranslate(&modelViewMatrix, 0, 0, -5); //平移
KSMatrix4 rotateMatrix;
ksMatrixLoadIdentity(&rotateMatrix);
// xDegree/yDegree/zDegree 分别通过三个按钮和一个timer控制自增
ksRotate(&rotateMatrix, xDegree, 1, 0, 0); //绕x轴旋转
ksRotate(&rotateMatrix, yDegree, 0, 1, 0); //绕y轴旋转
ksRotate(&rotateMatrix, zDegree, 0, 0, 1); //绕z轴旋转
ksMatrixMultiply(&modelViewMatrix, &rotateMatrix, &modelViewMatrix); //矩阵相乘获得模型视图矩阵
glUniformMatrix4fv(modelViewLocation, 1, GL_FALSE,(GLfloat *)&modelViewMatrix.m[0][0]); //传递模型视图矩阵
- 在顶点着色器程序中进行矩阵相乘
void main() {
varyTextCoor = textureCoor;
gl_Position = projectionMatrix * modelViewMatrix * position;
}
- 需要做颜色混合的话,我们还需要在片元着色器中定义一个varying类型的顶点颜色变量,并从顶点着色器程序传递给片元着色器程序
varying lowp vec4 varyColor;
然后再片元着色器中进行混合运算:
//纹理颜色
vec4 texColor = texture2D(colorMap, vTextCoor);
//顶点颜色
vec4 pColor = varyColor;
//混合因子比例
float alpha = 0.3;
//计算混合颜色值
vec4 tempColor = pColor * (1.0 - alpha) + texColor * alpha;
//设置混合完成后的颜色
gl_FragColor = tempColor;
大致核心流程就是这些了。
网友评论