2015-12-23 3 views
1

Недавно я перешел из LWJGL (с которым я столкнулся) в OpenGL API C++. Я столкнулся с this tutorial, так как не смог заставить мои классы vbo работать правильно. Код ниже:В OpenGL (GLFW/GLEW) ничего не появляется

#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 Objects (VAO) является обязательным. То же самое относится к объектам программы. Вы должны указать свой собственный shaders и не можете использовать фиксированную функцию pipleline. Вызов glLoadIdentity относится к функции устаревших матричных стеков, которая также удаляется в профилях ядра.

Ваш звонок glDrawArrays должен генерировать GL_INVALID_OPERATION, потому что у вас нет программного объекта и нет привязки VAO во время вызова рисования. Обычно я рекомендую добавлять проверки ошибок GL, по крайней мере, для отладочных сборников. Если версия GL, на которую вы нацеливаетесь, поддерживает ее, я рекомендую вместо этого использовать debug context. Это значительно облегчит выявление ошибок при разработке.

Также обратите внимание, что ни одна из этих проблем не связана с переключением с java с LWJGL на C++. Если раньше вы использовали устаревший контекстный/основной профиль с java, вы также можете сделать это на C++ (хотя я настоятельно рекомендую вам изучить современный GL вместо этого), и вы бы увидели те же проблемы, если бы вы использовали современный контекст основного профиля с LWJGL.

+0

Просто уточнить: Это рабочий код, и хотя он использует массивы вершин, он по-прежнему является VBO? [Ссылка на Pastebin] (http://pastebin.com/fBw007D0) –

+0

@ZachGoethel: Этот вопрос не имеет смысла. По-видимому, это не рабочий код, и ответ объясняет, почему. «Даже если он использует вершинные массивы, это все еще VBO?» часть полностью вне меня. VBOs - это VBOs, потому что они _store_ массивы вершин. Не путайте массивы вершин с объектами массива вершин. Последние хранят только метаинформацию, а VBOs хранят реальные массивы вершин. – derhass

+0

«Этот код» относится к ссылке, которую я дал. И «Является ли это VBO», я хотел спросить, сохраняются ли данные на графическом процессоре или отправляется каждый кадр. –

Смежные вопросы