OpenGL-ES 学习(13) ---- Shader 编译和程序对象

目录

概述

在本节中,我们提供创建 Shader对象,并且编译链接到一个程序对象的完整流程,主要内容如下:

  • Shader 和程序对象概述
  • 创建和编译Shader
  • 创建和链接程序对象
  • 设置和获取统一变量
  • 获取和设置属性
  • Shader 编译器和程序二进制代码

想要用 Shader 进行渲染,必须创建两个基本的对象:Shader 对象和程序对象(program object);它们之间的关系类似于C语言链接程序和编译器

  1. C语言对象将一段源代码生成目标对象
  2. C链接程序将对象文件链接为最后的文件

Shader 对象是包含多个 Shader 的对象,源代码提供给 Shader 对象,Shader 对象被编译为一个目标形式(类似于 obj 文件),编译之后,Shader 对象可以连接到一个程序对象,一个程序对象可以连接多个 Shader 对象 ,在 OpenGL-ES 中,每个程序对象必须连接到一个 Vertex Shader 对象和 Fragment Shader.

之后使用 Shader 进行渲染,步骤如下:

创建和编译Shader

创建和编译Shader使用的 API如下:
glCreateShader (GLenum type)
glDeleteShader(GLuint shader)

说明:创建/删除 VertexShader or FragmentShader ,返回新 Shaderhandle

glShaderSource (GLuint shader, GLsizei count, const GLchar const string, const GLint *length)

说明:指定 Shadersrc_code 源代码

glCompileShader (GLuint shader)

说明:编译 Shader

glGetShaderiv (GLuint shader,GLenum pname,GLint * params)

说明:检查 Shader 是否编译成功

glGetShaderInfoLog (GLuint shader,GLsizei maxLength,GLsizei *length,GLchar *infoLog)

说明:获取编译 Shader log 信息

链接程序对象

链接程序对象使用的 API 如下:

API 说明
glCreateProgram() 创建程序对象
glDeleteProgram() 删除程序对象
glAttachShader() Shader 对象连接到程序对象
glDetachShader() Shader 对象从程序对象分离
glLinkPrigram() 链接程序对象
glGetProgramiv 查询Shader 链接信息
glGetProgramInfoLog 获取程序信息日志

绘制一个最简单的三角形

绘制一个基本三角形,示例输入顶点坐标和颜色坐标如下:

c 复制代码
	//R G B A
	GLfloat color[4] = { 0.0f, 1.0f, 0.0f, 1.0f };
	// 3 vertices, with (x,y,z) per-vertex
	GLfloat vertexPos[3 * 3] = {
		1.0f,  0.0f, 0.0f, // v0
		0.0f, 1.0f, 0.0f, // v1
		0.0f, 0.0f, 1.0f  // v2
	};

vertexPos 数组表示的是三个顶点的三维坐标,OpenGL-ES 中使用的坐标系如下图所示:

示例代码

c 复制代码
#include "esUtil.h"

typedef struct
{
	GLuint programObject;
} UserData;

static int Init(ESContext *esContext)
{
	UserData *userData = esContext->userData;
	const char vShaderStr[] =
		"#version 300 es                            \n"
		"layout(location = 0) in vec4 a_position;   \n"
		"layout(location = 1) in vec4 a_color;      \n"
		"out vec4 v_color;                          \n"
		"void main()                                \n"
		"{                                          \n"
		"    v_color = a_color;                     \n"
		"    gl_Position = a_position;              \n"
		"}";

	const char fShaderStr[] =
		"#version 300 es            \n"
		"precision mediump float;   \n"
		"in vec4 v_color;           \n"
		"out vec4 o_fragColor;      \n"
		"void main()                \n"
		"{                          \n"
		"    o_fragColor = v_color; \n"
		"}";

	GLuint programObject;

	// Create the program object
	programObject = esLoadProgram(vShaderStr, fShaderStr);

	if (programObject == 0) {
		return GL_FALSE;
	}

	// Store the program object
	userData->programObject = programObject;

	// R G B A
	glClearColor(1.0f, 1.0f, 1.0f, 0.5f);
	return GL_TRUE;
}

static void Shutdown(ESContext *esContext)
{
	UserData *userData = esContext->userData;
	glDeleteProgram(userData->programObject);
}


static void Draw(ESContext *esContext)
{
	UserData *userData = esContext->userData;
	//R G B A
	GLfloat color[4] = { 0.0f, 1.0f, 0.0f, 1.0f };
	// 3 vertices, with (x,y,z) per-vertex
	GLfloat vertexPos[3 * 3] =
	{
		1.0f,  0.0f, 0.0f, // v0
		0.0f, 1.0f, 0.0f, // v1
		0.0f, 0.0f, 1.0f  // v2
	};

	glViewport(0, 0, esContext->width, esContext->height);

	glClear(GL_COLOR_BUFFER_BIT);
	glUseProgram(userData->programObject);

	glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 0, vertexPos);
	glEnableVertexAttribArray(0);
	glVertexAttrib4fv(1, color);

	glDrawArrays(GL_TRIANGLES, 0, 3);
	glDisableVertexAttribArray(0);
}
相关推荐
jackson凌2 分钟前
【Java学习笔记】递归
java·笔记·学习
DisonTangor13 分钟前
Meta 推出 WebSSL 模型:探索 AI 无语言视觉学习,纯图训练媲美 OpenAI CLIP
人工智能·学习·计算机视觉
s_little_monster2 小时前
【Linux】线程池和线程补充内容
linux·运维·服务器·c++·笔记·学习·学习方法
Timmer丿2 小时前
kafka学习笔记(四、生产者(客户端)深入研究(二)——消费者协调器与_consumer_offsets剖析)
笔记·学习·kafka
李匠20243 小时前
C++负载均衡远程调用学习之Reactor事件触发机制
c++·学习
冰茶_3 小时前
WPF之Image控件详解
学习·microsoft·微软·c#·wpf·wpf控件
搏博4 小时前
结构模式识别理论与方法
人工智能·深度学习·学习·算法·机器学习
z35026037064 小时前
K8S学习笔记01
笔记·学习·kubernetes
小猪佩奇TONY4 小时前
OpenGL-ES 学习(12) ---- VBO EBO VAO
学习
梁下轻语的秋缘5 小时前
华为云loT物联网介绍与使用
物联网·学习·华为·华为云