Ничего не появляется на экране в OpenGL (GLFW/GLEW)
Недавно я переходил от LWJGL (с которым у меня есть опыт работы) к C++ OpenGL API. Я использовал этот учебник, так как не мог заставить мои классы VBO работать правильно. Код ниже:
#include "GL/glew.h"
#include "GLFW/glfw3.h"
#include <stdlib.h>
#include <stdio.h>
using namespace std;
GLFWwindow* window;
void init()
{
}
static const GLfloat g_vertex_buffer_data[] =
{
-1.0f, -1.0f, 0.0f,
1.0f, -1.0f, 0.0f,
0.0f, 1.0f, 0.0f,
};
void render()
{
glViewport(0, 0, 640, 480);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glLoadIdentity();
GLuint vertexbuffer;
glGenBuffers(1, &vertexbuffer);
glBindBuffer(GL_ARRAY_BUFFER, vertexbuffer);
glBufferData(GL_ARRAY_BUFFER, sizeof(g_vertex_buffer_data), g_vertex_buffer_data, GL_STATIC_DRAW);
glEnableVertexAttribArray(0);
glBindBuffer(GL_ARRAY_BUFFER, vertexbuffer);
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 0, (void*)0);
glDrawArrays(GL_TRIANGLES, 0, 3);
glDisableVertexAttribArray(0);
glDeleteBuffers(1, &vertexbuffer);
glfwSwapBuffers(window);
glfwPollEvents();
}
static void errorCallback(int error, const char* desc)
{
fputs(desc, stderr);
}
static void keyCallback(GLFWwindow* window, int key, int scanCode, int action, int mods)
{
if (key == GLFW_KEY_ESCAPE && action == GLFW_RELEASE)
glfwSetWindowShouldClose(window, GL_TRUE);
}
void initWindow()
{
glfwSetErrorCallback(errorCallback);
if (!glfwInit())
exit(EXIT_FAILURE);
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 3);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
glfwWindowHint(GLFW_RESIZABLE, GL_FALSE);
window = glfwCreateWindow(640, 480, "Hello, world!", NULL, NULL);
if (!window)
{
glfwTerminate();
exit(EXIT_FAILURE);
}
glfwMakeContextCurrent(window);
glfwSwapInterval(1);
glfwSetKeyCallback(window, keyCallback);
glewExperimental = true;
if (glewInit() != GLEW_OK)
exit(EXIT_FAILURE);
}
void destroyWindow()
{
glfwDestroyWindow(window);
glfwTerminate();
exit(EXIT_SUCCESS);
}
int main(int argCount, char **args)
{
initWindow();
init();
while (!glfwWindowShouldClose(window))
render();
destroyWindow();
}
Я прочитал это снова и снова и просмотрел интернет. Однако другие посты, которые я прочитал, являются более очевидными ошибками. Я, вероятно, делаю здесь действительно очевидную ошибку, и я знаю, насколько неэффективен тот факт, что я создаю буфер для каждого кадра, однако это просто для проверки и проверки, смогу ли я заставить его работать. Буду признателен, если кто-нибудь скажет мне, что я здесь делаю неправильно!
1 ответ
Вы используете профиль ядра OpenGL 3.3. В таком контексте использование объектов Vertex Array (VAO) является обязательным. То же самое верно для программных объектов. Вы должны указать свои собственные шейдеры и не можете использовать фиксированную функцию pipleline. glLoadIdentity
Вызов относится к устаревшей функциональности стека матриц, которая также удалена из профилей ядра.
Ваш glDrawArrays
вызов должен генерировать GL_INVALID_OPERATION
потому что у вас нет программного объекта и нет привязки VAO во время вызова отрисовки. Я обычно рекомендую добавлять проверки ошибок GL хотя бы для отладочных сборок. Если версия GL, на которую вы ориентируетесь, поддерживает ее, я рекомендую вместо этого использовать контекст отладки. Это значительно облегчит обнаружение ошибок во время разработки.
Также обратите внимание, что ни одна из этих проблем не связана с переходом с Java с LWJGL на C++. Если бы вы использовали ранее унаследованный контекстный / основной профиль с java, вы могли бы сделать это и в C++ (хотя я настоятельно советую вам изучать современный GL), и вы бы столкнулись с такими же проблемами, если бы использовали современный базовый контекстный профиль с LWJGL.