Объект буфера вершин
Эта статья написана как руководство или руководство . ( март 2014 г. ) |
Объект буфера вершин ( VBO ) — это функция OpenGL , которая предоставляет методы для загрузки данных вершин ( положение , вектор нормали , цвет и т. д.) в видеоустройство для рендеринга в немгновенном режиме. VBO обеспечивают существенный прирост производительности по сравнению с рендерингом в немедленном режиме, главным образом потому, что данные находятся в памяти видеоустройства, а не в системной памяти, и поэтому они могут визуализироваться непосредственно видеоустройством. Они эквивалентны буферам вершин в Direct3D .
Спецификация объекта буфера вершин была стандартизирована Советом по обзору архитектуры OpenGL. Архивировано 24 ноября 2011 г. на Wayback Machine, начиная с OpenGL версии 1.5 (в 2003 г.). Аналогичная функциональность была доступна до стандартизации VBO через созданное Nvidia расширение «диапазон массива вершин». [1] или ATI «объект массива вершин» [2] расширение.
Основные функции VBO
[ редактировать ]Следующие функции составляют основу доступа и манипулирования VBO:
- В OpenGL 1.4 :
- glGenBuffersARB (sizei n, uint *buffers)
- Создает новый VBO и возвращает его идентификационный номер в виде целого числа без знака. Идентификатор 0 зарезервирован.
- glBindBufferARB (цель перечисления, буфер uint)
- Используйте ранее созданный буфер в качестве активного VBO.
- glBufferDataARB (цель перечисления, размер sizeiptrARB, const void *data, использование перечисления)
- Загрузите данные в активный VBO.
- glDeleteBuffersARB (sizei n, const uint *buffers)
- Удаляет указанное количество VBO из предоставленного массива или идентификатора VBO.
- В 2.1 OpenGL [3] OpenGL 3.x [4] и OpenGL 4.x : [5]
- glGenBuffers (sizei n, uint *buffers)
- Создает новый VBO и возвращает его идентификационный номер в виде целого числа без знака. Идентификатор 0 зарезервирован.
- glBindBuffer (цель перечисления, буфер uint)
- Используйте ранее созданный буфер в качестве активного VBO.
- glBufferData (цель перечисления, размер sizeiptrARB, const void *data, использование перечисления)
- Загрузите данные в активный VBO.
- glDeleteBuffers (sizei n, const uint *buffers)
- Удаляет указанное количество VBO из предоставленного массива или идентификатора VBO.
Пример использования
[ редактировать ]В C с использованием OpenGL 2.1.
[ редактировать ]//Initialise VBO - do only once, at start of program
//Create a variable to hold the VBO identifier
GLuint triangleVBO;
//Vertices of a triangle (counter-clockwise winding)
float data[] = {1.0, 0.0, 1.0, 0.0, 0.0, -1.0, -1.0, 0.0, 1.0};
//try float data[] = {0.0, 1.0, 0.0, -1.0, -1.0, 0.0, 1.0, -1.0, 0.0}; if the above doesn't work.
//Create a new VBO and use the variable id to store the VBO id
glGenBuffers(1, &triangleVBO);
//Make the new VBO active
glBindBuffer(GL_ARRAY_BUFFER, triangleVBO);
//Upload vertex data to the video device
glBufferData(GL_ARRAY_BUFFER, sizeof(data), data, GL_STATIC_DRAW);
//Make the new VBO active. Repeat here in case it has changed since initialisation
glBindBuffer(GL_ARRAY_BUFFER, triangleVBO);
//Draw Triangle from VBO - do each time window, view point or data changes
//Establish its 3 coordinates per vertex with zero stride in this array; necessary here
glVertexPointer(3, GL_FLOAT, 0, NULL);
//Establish array contains vertices (not normals, colours, texture coords etc)
glEnableClientState(GL_VERTEX_ARRAY);
//Actually draw the triangle, giving the number of vertices provided
glDrawArrays(GL_TRIANGLES, 0, sizeof(data) / sizeof(float) / 3);
//Force display to be drawn now
glFlush();
В C с использованием OpenGL 3.x и OpenGL 4.x.
[ редактировать ]Вершинный шейдер:
/*----------------- "exampleVertexShader.vert" -----------------*/
#version 150 // Specify which version of GLSL we are using.
// in_Position was bound to attribute index 0("shaderAttribute")
in vec3 in_Position;
void main()
{
gl_Position = vec4(in_Position.x, in_Position.y, in_Position.z, 1.0);
}
/*--------------------------------------------------------------*/
Фрагментный шейдер:
/*---------------- "exampleFragmentShader.frag" ----------------*/
#version 150 // Specify which version of GLSL we are using.
precision highp float; // Video card drivers require this line to function properly
out vec4 fragColor;
void main()
{
fragColor = vec4(1.0,1.0,1.0,1.0); //Set colour of each fragment to WHITE
}
/*--------------------------------------------------------------*/
Основная программа OpenGL:
/*--------------------- Main OpenGL Program ---------------------*/
/* Create a variable to hold the VBO identifier */
GLuint triangleVBO;
/* This is a handle to the shader program */
GLuint shaderProgram;
/* These pointers will receive the contents of our shader source code files */
GLchar *vertexSource, *fragmentSource;
/* These are handles used to reference the shaders */
GLuint vertexShader, fragmentShader;
const unsigned int shaderAttribute = 0;
/* Vertices of a triangle (counter-clockwise winding) */
float data[3][3] = {
{ 0.0, 1.0, 0.0 },
{ -1.0, -1.0, 0.0 },
{ 1.0, -1.0, 0.0 }
};
/*---------------------- Initialise VBO - (Note: do only once, at start of program) ---------------------*/
/* Create a new VBO and use the variable "triangleVBO" to store the VBO id */
glGenBuffers(1, &triangleVBO);
/* Make the new VBO active */
glBindBuffer(GL_ARRAY_BUFFER, triangleVBO);
/* Upload vertex data to the video device */
glBufferData(GL_ARRAY_BUFFER, sizeof(data), data, GL_STATIC_DRAW);
/* Specify that our coordinate data is going into attribute index 0(shaderAttribute), and contains three floats per vertex */
glVertexAttribPointer(shaderAttribute, 3, GL_FLOAT, GL_FALSE, 0, 0);
/* Enable attribute index 0(shaderAttribute) as being used */
glEnableVertexAttribArray(shaderAttribute);
/* Make the new VBO active. */
glBindBuffer(GL_ARRAY_BUFFER, triangleVBO);
/*-------------------------------------------------------------------------------------------------------*/
/*--------------------- Load Vertex and Fragment shaders from files and compile them --------------------*/
/* Read our shaders into the appropriate buffers */
vertexSource = filetobuf("exampleVertexShader.vert");
fragmentSource = filetobuf("exampleFragmentShader.frag");
/* Assign our handles a "name" to new shader objects */
vertexShader = glCreateShader(GL_VERTEX_SHADER);
fragmentShader = glCreateShader(GL_FRAGMENT_SHADER);
/* Associate the source code buffers with each handle */
glShaderSource(vertexShader, 1, (const GLchar**)&vertexSource, 0);
glShaderSource(fragmentShader, 1, (const GLchar**)&fragmentSource, 0);
/* Free the temporary allocated memory */
free(vertexSource);
free(fragmentSource);
/* Compile our shader objects */
glCompileShader(vertexShader);
glCompileShader(fragmentShader);
/*-------------------------------------------------------------------------------------------------------*/
/*-------------------- Create shader program, attach shaders to it and then link it ---------------------*/
/* Assign our program handle a "name" */
shaderProgram = glCreateProgram();
/* Attach our shaders to our program */
glAttachShader(shaderProgram, vertexShader);
glAttachShader(shaderProgram, fragmentShader);
/* Bind attribute index 0 (shaderAttribute) to in_Position*/
/* "in_Position" will represent "data" array's contents in the vertex shader */
glBindAttribLocation(shaderProgram, shaderAttribute, "in_Position");
/* Link shader program*/
glLinkProgram(shaderProgram);
/*-------------------------------------------------------------------------------------------------------*/
/* Set shader program as being actively used */
glUseProgram(shaderProgram);
/* Set background colour to BLACK */
glClearColor(0.0, 0.0, 0.0, 1.0);
/* Clear background with BLACK colour */
glClear(GL_COLOR_BUFFER_BIT);
/* Actually draw the triangle, giving the number of vertices provided by invoke glDrawArrays
while telling that our data is a triangle and we want to draw 0-3 vertexes
*/
glDrawArrays(GL_TRIANGLES, 0, (sizeof(data) / 3) / sizeof(GLfloat));
/*---------------------------------------------------------------*/
Ссылки
[ редактировать ]- ^ "GL_NV_vertex_array_range Технический документ" . Архивировано из оригинала 17 августа 2004 г. Проверено 24 июня 2024 г.
{{cite web}}
: CS1 maint: bot: исходный статус URL неизвестен ( ссылка ) - ^ «ATI_vertex_array_object» . Архивировано из оригинала 4 июля 2012 г. Проверено 12 августа 2011 г.
- ^ «Справочник по функциям OpenGL 2.1» .
- ^ «Справочник по функциям OpenGL 3.3» .
- ^ «Справочник по функциям OpenGL 4.2» .