OpenGL VBO、VAO、EBO简单例子

文章目录

  • VBO使用glDrawArrays()函数画梯形
    • 在上一个例子的基础上改变背景颜色
  • VBO+VAO使用glDrawArrays()函数画梯形
  • VBO+VAO+片段着色器给梯形着色
  • EBO+VBO+VAO画两个三角形

My Github Link
写再最开头:learnOpengl网站用的gflw3和glad两个库,由于我自己配置的环境是glut+glew两个库,所以我把那些例子改为了能在glut+glew两个库下运行的代码。

顶点数组对象:Vertex Array Object,VAO
顶点缓冲对象:Vertex Buffer Object,VBO
索引缓冲对象:Element Buffer Object,EBO或Index Buffer Object,IBO

参考
https://blog.csdn.net/dcrmg/article/details/53556664
learnOpenGL网站实例代码
learnOpenGLl中文网站(个人认为最适合新手的教程)

VBO使用glDrawArrays()函数画梯形

#include 
#include
#include
#include
void userInit();  //自定义初始化
void display(void);

GLuint vboId;//vertex buffer object句柄    
GLuint vaoId;//vertext array object句柄    
GLuint programId;//shader program 句柄 
int main(int argc, char** argv)
{
	glutInit(&argc, argv);
	glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE);
	glutInitWindowPosition(100, 100);
	glutInitWindowSize(512, 512);
	glutCreateWindow("Rectangle demo");

	//使用glew,需要执行glewInit,不然运行过程会报错
	//glewInit要放在glut完成了基本的初始化之后执行
	glewInit();

	//自定义初始化,生成VAO,VBO对象
	userInit();


	glutDisplayFunc(display);

	glutMainLoop();
	return 0;
}

void userInit()
{
	glClearColor(0.0, 0.0, 0.0, 0.0);
	//创建顶点数据    
	const GLfloat vertices[] = {
		-0.5f,-0.5f,0.0f,1.0f,
		0.5f,-0.5f,0.0f,1.0f,
		0.25f,0.5f,0.0f,1.0f,
		-0.25f,0.5f,0.0f,1.0f,
	};


	//创建VBO对象	
	glGenBuffers(1, &vboId);
	glBindBuffer(GL_ARRAY_BUFFER, vboId);
	//传入VBO数据
	glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);
	//解除VBO绑定
	glBindBuffer(GL_ARRAY_BUFFER, 0);
}

//绘制回调函数    
void display(void)
{
	glClear(GL_COLOR_BUFFER_BIT);

	//绑定VBO
	glBindBuffer(GL_ARRAY_BUFFER, vboId);
	glEnableVertexAttribArray(0);

	//解释顶点数据方式
	glVertexAttribPointer(0, 4, GL_FLOAT, GL_FALSE, 0, 0);

	//绘制模型
	glDrawArrays(GL_TRIANGLE_FAN, 0, 4);

	glBindBuffer(GL_ARRAY_BUFFER, 0);
	glDisableVertexAttribArray(0);

	glutSwapBuffers();
}

result:
OpenGL VBO、VAO、EBO简单例子_第1张图片

在上一个例子的基础上改变背景颜色

数据类型由RGBA改为RGB

void userInit();  //自定义初始化
void display(void);

GLuint vboId;//vertex buffer object句柄    
GLuint vaoId;//vertext array object句柄    
GLuint programId;//shader program 句柄 
int main(int argc, char** argv)
{
	glutInit(&argc, argv);
	glutInitDisplayMode(GLUT_RGB | GLUT_DOUBLE);
	glutInitWindowPosition(100, 100);
	glutInitWindowSize(512, 512);
	glutCreateWindow("Rectangle demo");

	//使用glew,需要执行glewInit,不然运行过程会报错
	//glewInit要放在glut完成了基本的初始化之后执行
	glewInit();

	//自定义初始化,生成VAO,VBO对象
	userInit();


	glutDisplayFunc(display);

	glutMainLoop();
	return 0;
}

void userInit()
{
	glClearColor(1.0f, 0.3f, 0.3f, 1.0f);//背景颜色
	//创建顶点数据    
	const GLfloat vertices[] = {
		-0.5f,-0.5f,0.0f,
		0.5f,-0.5f,0.0f,
		0.25f,0.5f,0.0f,
		-0.25f,0.5f,0.0f
	};


	//创建VBO对象	
	glGenBuffers(1, &vboId);
	glBindBuffer(GL_ARRAY_BUFFER, vboId);
	//传入VBO数据
	glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);
	//解除VBO绑定
	glBindBuffer(GL_ARRAY_BUFFER, 0);
}

//绘制回调函数    
void display(void)
{
	glClear(GL_COLOR_BUFFER_BIT);

	//绑定VBO
	glBindBuffer(GL_ARRAY_BUFFER, vboId);
	glEnableVertexAttribArray(0);

	//解释顶点数据方式
	glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), 0);

	//绘制模型
	glDrawArrays(GL_TRIANGLE_FAN, 0, 4);

	glBindBuffer(GL_ARRAY_BUFFER, 0);
	glDisableVertexAttribArray(0);

	glutSwapBuffers();
}

result:
OpenGL VBO、VAO、EBO简单例子_第2张图片

VBO+VAO使用glDrawArrays()函数画梯形

VAO与VBO的关系,VAO利用VBO加载数据
OpenGL VBO、VAO、EBO简单例子_第3张图片

#include 
#include
#include
#include

void userInit();  //自定义初始化
void display(void);
  
GLuint VAO;
GLuint VBO;
unsigned int fragmentShader;
unsigned int vertexShader;
unsigned int shaderProgram;
const GLfloat vertices[] = {
		-0.5f,-0.5f,0.0f,
		0.5f,-0.5f,0.0f,
		0.25f,0.5f,0.0f,
		-0.25f,0.5f,0.0f,
};

int main(int argc, char** argv)
{
	glutInit(&argc, argv);
	glutInitDisplayMode(GLUT_RGB | GLUT_DOUBLE);
	glutInitWindowPosition(100, 100);
	glutInitWindowSize(512, 512);
	glutCreateWindow("Rectangle demo");

	//使用glew,需要执行glewInit,不然运行过程会报错
	//glewInit要放在glut完成了基本的初始化之后执行
	glewInit();

	//自定义初始化,生成VAO,VBO对象
	userInit();


	glutDisplayFunc(display);

	glutMainLoop();
	glDeleteVertexArrays(1, &VAO);
	glDeleteProgram(shaderProgram);
	return 0;
}

void userInit()
{
	glClearColor(1.0f, 0.3f, 0.3f, 1.0f);//背景颜色
	//创建VAO对象	
	glGenVertexArrays(1, &VAO);
	//VAO绑定
	glBindVertexArray(VAO);
	//创建VBO对象
	glGenBuffers(1, &VBO);
	//VBO绑定
	glBindBuffer(GL_ARRAY_BUFFER, VBO);
	//给VBO传入数据
	glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);
	glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), (void*)0);
	glEnableVertexAttribArray(0);
	//解绑VAO
	glBindVertexArray(0);
	//解绑VBO
	glBindBuffer(GL_ARRAY_BUFFER, 0);
}

//绘制回调函数    
void display(void)
{

	//绑定VA0
	glBindVertexArray(VAO);
	glClearColor(0.2f, 0.3f, 0.3f, 1.0f);
	glClear(GL_COLOR_BUFFER_BIT);
	glBindVertexArray(VAO); // 这里仅仅绑定了VAO,无需再绑定VBO
	glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
	glBindVertexArray(0);
	glutSwapBuffers();
}

result:
OpenGL VBO、VAO、EBO简单例子_第4张图片

VBO+VAO+片段着色器给梯形着色

#include 
#include
#include
#include

void userInit();  //自定义初始化
void display(void);
  
GLuint VAO;
GLuint VBO;
unsigned int fragmentShader;
unsigned int vertexShader;
unsigned int shaderProgram;
const GLfloat vertices[] = {
		-0.5f,-0.5f,0.0f,
		0.5f,-0.5f,0.0f,
		0.25f,0.5f,0.0f,
		-0.25f,0.5f,0.0f,
};
const GLchar* vertexShaderSource = "#version 330 core\n"
"layout (location = 0) in vec3 position;\n"
"void main()\n"
"{\n"
"gl_Position = vec4(position.x, position.y, position.z, 1.0);\n"
"}\0";
const GLchar* fragmentShaderSource = "#version 330 core\n"
"out vec4 color;\n"
"void main()\n"
"{\n"
"color = vec4(1.0f, 0.5f, 0.2f, 1.0f);\n"
"}\n\0";

int main(int argc, char** argv)
{
	glutInit(&argc, argv);
	glutInitDisplayMode(GLUT_RGB | GLUT_DOUBLE);
	glutInitWindowPosition(100, 100);
	glutInitWindowSize(512, 512);
	glutCreateWindow("Rectangle demo");

	//使用glew,需要执行glewInit,不然运行过程会报错
	//glewInit要放在glut完成了基本的初始化之后执行
	glewInit();

	//自定义初始化,生成VAO,VBO对象
	userInit();


	glutDisplayFunc(display);

	glutMainLoop();
	glDeleteVertexArrays(1, &VAO);
	glDeleteProgram(shaderProgram);
	return 0;
}

void userInit()
{
	//glClearColor(1.0f, 0.3f, 0.3f, 1.0f);//背景颜色
	//创建VAO对象	
	glGenVertexArrays(1, &VAO);
	//VAO绑定
	glBindVertexArray(VAO);
	//创建VBO对象
	glGenBuffers(1, &VBO);
	//VBO绑定
	glBindBuffer(GL_ARRAY_BUFFER, VBO);
	//给VBO传入数据
	glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);
	glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), (void*)0);
	glEnableVertexAttribArray(0);
	//解绑VAO
	glBindVertexArray(0);
	//解绑VBO
	glBindBuffer(GL_ARRAY_BUFFER, 0);

	vertexShader = glCreateShader(GL_VERTEX_SHADER);
	glShaderSource(vertexShader, 1, &vertexShaderSource, NULL);
	glCompileShader(vertexShader);
	// check for shader compile errors
	int success;
	char infoLog[512];
	glGetShaderiv(vertexShader, GL_COMPILE_STATUS, &success);
	if (!success)
	{
		glGetShaderInfoLog(vertexShader, 512, NULL, infoLog);
		std::cout << "ERROR::SHADER::VERTEX::COMPILATION_FAILED\n" << infoLog << std::endl;
	}
	// 片段着色器给三角形着色
	fragmentShader = glCreateShader(GL_FRAGMENT_SHADER);
	glShaderSource(fragmentShader, 1, &fragmentShaderSource, NULL);
	glCompileShader(fragmentShader);
	// check for shader compile errors
	glGetShaderiv(fragmentShader, GL_COMPILE_STATUS, &success);
	if (!success)
	{
		glGetShaderInfoLog(fragmentShader, 512, NULL, infoLog);
		std::cout << "ERROR::SHADER::FRAGMENT::COMPILATION_FAILED\n" << infoLog << std::endl;
	}
	// link shaders
	shaderProgram = glCreateProgram();
	glAttachShader(shaderProgram, vertexShader);
	glAttachShader(shaderProgram, fragmentShader);
	glLinkProgram(shaderProgram);
	// check for linking errors
	glGetProgramiv(shaderProgram, GL_LINK_STATUS, &success);
	if (!success) {
		glGetProgramInfoLog(shaderProgram, 512, NULL, infoLog);
		std::cout << "ERROR::SHADER::PROGRAM::LINKING_FAILED\n" << infoLog << std::endl;
	}
	glDeleteShader(vertexShader);
	glDeleteShader(fragmentShader);
}

//绘制回调函数    
void display(void)
{

	//绑定VA0
	glBindVertexArray(VAO);
	glClearColor(0.2f, 0.3f, 0.3f, 1.0f);
	glClear(GL_COLOR_BUFFER_BIT);

	glBindVertexArray(VAO); // 这里仅仅绑定了VAO,无需再绑定VBO

	glUseProgram(shaderProgram);
	glDrawArrays(GL_TRIANGLE_FAN, 0, 4);

	glBindVertexArray(0);
	glutSwapBuffers();
}

result:
OpenGL VBO、VAO、EBO简单例子_第5张图片

EBO+VBO+VAO画两个三角形

可以按照上一个例子给三角形着色

#include 
#include
#include
#include
void userInit();  //自定义初始化
void display(void);

GLuint VAO; 
GLuint VBO;
GLuint EBO; 
GLuint programId;
float vertices[] = {
	-1.0f, -0.5f, 0.0f,   
	 0.f, -0.5f, 0.0f,  
	-0.5f, 0.5f, 0.0f, 

	 1.0f,-0.5f,0.0f,   
	 0.5f,0.5f,0.0f
};

unsigned int indices[] = { // 注意索引从0开始! 
	0, 1, 2, // 第一个三角形
	1, 3, 4  // 第二个三角形
};
int main(int argc, char** argv)
{
	glutInit(&argc, argv);
	glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE);
	glutInitWindowPosition(100, 100);
	glutInitWindowSize(512, 512);
	glutCreateWindow("Rectangle demo");

	//使用glew,需要执行glewInit,不然运行过程会报错
	//glewInit要放在glut完成了基本的初始化之后执行
	glewInit();

	//自定义初始化,生成VAO,VBO对象
	userInit();


	glutDisplayFunc(display);

	glutMainLoop();
	return 0;
}

void userInit()
{
	
	glGenBuffers(1, &EBO);//创建EBO
	glGenVertexArrays(1, &VAO);//创建VAO
	glGenBuffers(1, &VBO);//创建VBO
	glBindVertexArray(VAO);//绑定VAO
	glBindBuffer(GL_ARRAY_BUFFER, VBO);//绑定VBO
	glBufferData(GL_ARRAY_BUFFER, sizeof(vertices), vertices, GL_STATIC_DRAW);
	glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, EBO);//绑定EBO
	glBufferData(GL_ELEMENT_ARRAY_BUFFER, sizeof(indices), indices, GL_STATIC_DRAW);//这里缓冲定义和之前不一样
	//解释顶点数据方式
	glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), (void*)0);
	glEnableVertexAttribArray(0);
	//解除VAO绑定
	glBindBuffer(GL_ARRAY_BUFFER, 0);
	glBindVertexArray(0);
}

//绘制回调函数    
void display(void)
{
	glClearColor(0.2f, 0.3f, 0.3f, 1.0f);
	glClear(GL_COLOR_BUFFER_BIT);

	//绑定VAO
	glBindVertexArray(VAO);


	//绘制模型
	glDrawElements(GL_TRIANGLES, 6, GL_UNSIGNED_INT, 0);

	glBindVertexArray(0);
	glDisableVertexAttribArray(0);

	glutSwapBuffers();
}

result:
OpenGL VBO、VAO、EBO简单例子_第6张图片

你可能感兴趣的:(OpenGL,c++,opengl,opengles)