Почему мое приложение OpenGL 3.3 ничего не рисует? - PullRequest
1 голос
/ 18 марта 2012

Я пытаюсь разобраться с VAO / VBO OpenGL, и концептуально Я здесь, но по какой-то причине это приложение ничего не рисует на экране.Я работаю в контексте 4.2, но я пишу только для ядра 3.3.

Вот объявления для соответствующих переменных:

// Tetrahedron vertices
GLfloat tetra_vertices[12];
GLuint tetra_vao;
GLuint tetra_vbo;

В функции с именем init_scene Iиметь следующее:

glGenVertexArrays(1, &tetra_vao);
glBindVertexArray(tetra_vao);
glGenBuffers(1, &tetra_vbo); // One for vertex locations
glBindBuffer(GL_ARRAY_BUFFER, tetra_vbo); // Bind vertex locations buffer
glBufferData(GL_ARRAY_BUFFER, 12 * sizeof(GLfloat), tetra_vertices, GL_STATIC_DRAW);
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 0, 0);
glEnableVertexAttribArray(0);

И где моя GLSL-программа связана:

for (int i = 0; i < num_shaders; ++i)
    glAttachShader(program, shaders[i]);
glBindAttribLocation(program, 0, "in_position");
glLinkProgram(program);

Я использую только один атрибут, и это позиция вершины.Программа связывается без ошибок.

Вот сама функция draw_scene:

glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glBindVertexArray(tetra_vao);
glDrawArrays(GL_TRIANGLE_STRIP, 0, 12);
glBindVertexArray(0);

И для моей веры, мой вершинный шейдер:

#version 330
in vec3 in_position;
uniform mat4 modelview_matrix;
void main(void) {
    gl_Position = vec4(in_position, 1.0f) * modelview_matrix;
}

modelview_matrixэто форма, которая на данный момент просто проходит в единичной матрице.Я на мгновение подумал, что можно нарисовать что-то, чего я просто не вижу, поэтому я установил свой чистый цвет на серый, и вот фрагментный шейдер, который должен просто выводить белый:

#version 330
out vec4 vFragColor;
void main(void)
{
vFragColor = vec4(1.0f);
}

Все, что я 'прочитав, прежде всего этот учебник и Superbible, проясните цепочку событий:

  • Создайте VAO
  • Связывайте VAO
  • Создание VBO
  • Привязка и заполнение VBO
  • Установка указателя атрибута

Я использовал glDEBugger, чтобы попытаться получить более четкое представление о том, почему это не такт работает.Я установил перерыв в ошибках GL, поэтому я знаю, что сами функции GL не вызывают никаких ошибок.Я могу видеть содержимое VBO, и это ожидаемые данные вершин.Единственное, в чем я не уверен, так это в том, как убедиться, что VBO связан как данные местоположения вершины с VAO, и что VAO действительно правильно привязан, когда я вызываю функцию рисования.

Если есть что-тоЯ оставил это необходимым, пожалуйста, дайте мне знать.Спасибо!

Обновление 1:

Вот массив, который предоставляет данные вершин, загруженные в VBO:

tetra_vertices = {
    0.7f, 0.7f, 0.7f,
    -0.7f, -0.7f, 0.7f,
    -0.7f, -0.7f, -0.7f,
    0.7f, -0.7f, 0.7f
};

Вот что все измои настройки контекста выглядят так:

glClearColor(0.2,0.2,0.2,0.0);
glClearDepth(1.0);
glViewport(0, 0, properties.size_x, properties.size_y);
glEnable(GL_DEPTH_TEST);
glCullFace(GL_BACK);
glEnable(GL_CULL_FACE);
glEnable(GL_VERTEX_ARRAY);
glEnable(GL_MULTISAMPLE);

Обновление 2:

Ответ Никола Боласа ниже поднял хороший вопрос об орфографической видимости, о которой я не думалоколо.К сожалению, не похоже, что это проблема.Я попробовал его список вершин, отключил любые отбраковки и попробовал эти вершины:

tetra_vertices = {
    -0.7f, -0.7f, 0.0f,
    -0.7f, 0.7f, 0.0f,
    0.7f, -0.7f, 0.0f,
    0.7f, 0.7f, 0.0f
};

Которые, я думаю, должны нарисовать квадрат, но все равно ничего.Я также заметил, что я звонил glDrawArrays с 12 элементами, когда их должно было быть четыре (12 координат = 4 x, y, z вершин), но это также не решило проблему.

Обновление 3 (или «Когда сообщения становятся слишком длинными»): Пошагово просматривая приложение в gDEBugger, я заметил кое-что, что показалось мне странным.В функции draw есть обычный цикл привязки текущей VAO, вызов glDrawArrays, привязка VAO 0, так что можно нарисовать еще одну вещь.Наблюдая за настройками состояния GL, как это происходит, похоже, что GL_VERTEX_ARRAY равно TRUE, когда мой VAO не связан (то есть VAO 0 связан), и FALSE, когда мой VAO связан.Это так, как должно быть?GL_VERTEX_ARRAY представляет состояние, которое заменено glBindVertexArray, а не дополнено им?Кроме того, изменение режима с GL_TRIANGLE_STRIP на GL_POINTS и установка glPointSize(5.0f) приводит к рисованию одной точки в 0, 0, поэтому создается впечатление, что точка создается, но не обрабатывается должным образом моим вершинным шейдером.

1 Ответ

4 голосов
/ 18 марта 2012
tetra_vertices = {
    0.7f, 0.7f, 0.7f,
    -0.7f, -0.7f, 0.7f,
    -0.7f, -0.7f, -0.7f,
    0.7f, -0.7f, 0.7f
};

Вы используете отографическую проекцию (поскольку ваша матрица идентична). Таким образом, в основном, мы можем игнорировать значения Z; они не имеют значения.

Вы рисуете это как полосу треугольника, так что получается два треугольника.

Ваш первый треугольник {(0.7f, 0.7f), (-0.7f, -0.7f), (-0.7f, -0.7f)}. Этот треугольник не имеет видимой площади поверхности, потому что две из точек являются одинаковыми . Треугольник без видимой площади поверхности невидим.

Ваш второй треугольник {(-0.7f, -0.7f), (-0.7f, -0.7f), (0.7f, -0.7f)}. Как и раньше, две точки совпадают, поэтому у треугольника нет видимой области.

Вы, вероятно, имели в виду что-то вроде этого:

tetra_vertices = {
    0.7f, 0.7f, 0.0f,
    -0.7f, 0.7f, 0.0f,
    -0.7f, -0.7f, 0.0f,
    0.7f, -0.7f, 0.0f
};

Это с большей вероятностью принесет вам что-нибудь полезное. Если вы по-прежнему ничего не видите, отключите отбор лица.

...