OpenGL SuperBible第6版(适用于OpenGL 4.3)的样本使用的顶点着色器没有顶点属性输入,但硬编码顶点,例如
#version 420 core
void main(void)
{
const vec4 vertices[] = vec4[](vec4( 0.4, -0.4, 0.5, 1.0),
vec4(-0.4, -0.4, 0.5, 1.0),
vec4( 0.4, 0.4, 0.5, 1.0));
gl_Position = vertices[gl_VertexID];
}
当我运行样本时,窗口被清除但没有其他事情发生。
通过实验,我发现当将空缓冲区绑定到上下文时,程序会按预期运行。以下是示例程序:
#include <stdio.h>
#include <stdlib.h>
#include <GL/glew.h> /
#include <GLFW/glfw3.h>
#define GLM_MESSAGES
#include <glm/glm.hpp>
#include <glm/gtc/matrix_transform.hpp>
#include <glm/gtc/type_ptr.hpp>
#include <glm/gtx/vector_angle.hpp>
int main(int argc, char* argv[]) {
GLuint program;
GLuint vao;
GLuint vbo;
glfwInit();
GLFWwindow* window = glfwCreateWindow(640, 480, "gl_InstanceID", NULL, NULL);
glfwMakeContextCurrent(window);
glewInit();
program = glCreateProgram();
GLuint vs = load("vertex.glsl", GL_VERTEX_SHADER, true);
GLuint fs = load("frag.glsl", GL_FRAGMENT_SHADER, true);
glAttachShader(program, vs);
glAttachShader(program, fs);
glLinkProgram(program);
glDeleteShader(vs);
glDeleteShader(fs);
glGenVertexArrays(1, &vao);
glBindVertexArray(vao);
//**************************************
//no triangle drawn when below these lines commented out
glGenBuffers(1, &vbo);
glBindBuffer(GL_ARRAY_BUFFER, vbo);
glBufferData(GL_ARRAY_BUFFER, 4, NULL, GL_DYNAMIC_COPY);
glVertexAttribPointer(0, 4, GL_FLOAT, GL_FALSE, 0, NULL);
glEnableVertexAttribArray(0);
//***************************************
do {
static const GLfloat green[] = { 0.0f, 0.2f, 0.0f, 1.0f };
glClearBufferfv(GL_COLOR, 0, green);
glUseProgram(program);
glDrawArrays(GL_TRIANGLES, 0, 3); //OR glDrawArraysInstanced(GL_TRIANGLES, 0, 3,1);
glfwSwapBuffers(window);
glfwPollEvents();
if (GLFW_PRESS == glfwGetKey(window, GLFW_KEY_ESCAPE)) {
glfwSetWindowShouldClose(window, 1);
}
} while (!glfwWindowShouldClose(window));
glfwTerminate();
return 0;
}
在 stars 之间添加代码时,会绘制三角形。没有缓冲区,不会绘制三角形。
此外,当顶点数组对象(VAO)被移除(或如上所述)时,三角形也不会显示。只有VAO和(空)VBO才会绘制三角形。
移除VAO但缓冲区显示三角形。没有缓冲没有三角形。 VAO似乎没有什么区别。
另请注意,顶点着色器没有输入。
发生了什么事?
其他可能有用的信息
片段着色器:
#version 420 core
out vec4 color;
void main(void)
{
color = vec4(1.0);
}
操作系统详细信息:
编译器详细信息
OpenGL详细信息:
在使用与Linux相同的图形卡的Windows中也会出现问题,即
我还记录了issue 984 on Unofficial AMD Bugzilla。但也许它在13.12修正。
但是,该程序可以运行(不使用空缓冲区和空缓冲区),在
上运行和
答案 0 :(得分:2)
不,信不信任glDrawArrays (...)
与哪个顶点缓冲区绑定无关。顶点缓冲区绑定仅在设置顶点指针时很重要,因为它定义了您传递的指针相对于的地址空间。从那时起,绑定的VBO就无关紧要了。 顺便说一下,如果你在一个严格的GLSL实现上运行这个片段着色器,它将警告/拒绝工作,因为没有#version
指令它应该假设片段着色器是针对GLSL 1.10规范,不支持out
阶段变量(需要gl_FragData [0]
代替)。
或者,简单地在顶点着色器中添加#version 420 core
...版本指令实际上比你想象的更重要,特别是因为在它缺席时发生的行为在供应商之间变化很大。这样做可能无法解决您的问题,但它仍然是您应该解决的问题。
关于移除VAO的问题,这是可以预料的。在核心OpenGL 3.2+上下文中,您必须具有非零VAO绑定才能使glDrawArrays (...)
起作用。实际上,VAO成为顶点绘制命令的上下文。如果没有一个限制,你就无法操作它们。
答案 1 :(得分:0)
请记住,顶点着色器只能操纵现有顶点。它无法创建它们。即使位置在着色器中是硬编码的,您仍然需要为它进行转换。
答案 2 :(得分:0)
不,看起来这是AMD Radeon HD 7600M系列驱动程序中的一个错误(13.4)
我安装了latest AMD driver,它解决了Windows和Linux中的问题。
Linux:已安装amd-catalyst-13.12-linux-x86.x86_64.zip
Windows:已安装amd_catalyst_13.11_mobility_betav9.5.exe
要在Linux上重新安装AMD驱动程序,我首先卸载AMD安装(amd-catalyst-previous-version.run --uninstall),删除所有包含名称fglrx的软件包(使用aptitude),将符号链接调整为/ usr / lib64(见下文),然后运行新的amd-catalyst-13.12-linux-x86.x86_64.run。
我遇到了这个页面AMD 13.1 64 bit drivers and the libGL.so.1 error,它解释了AMD安装程序放置libGL.so文件的位置
安装程序将lib文件放在/ usr / lib64中。但是,如果你有Ubuntu,那么64位库会进入/ usr / lib。我做了以下修复我的问题。
卸载驱动程序 sudo ./amd-driver-installer-catalyst-13.1-legacy-linux-x86.x86_64.run --uninstall
删除/ usr / lib64文件夹 sudo rm -Rf / usr / lib64
创建一个指向/ lib / usr的符号链接/ usr / lib64 sudo ln -s / usr / lib / usr / lib64
再次安装驱动程序 sudo ./amd-driver-installer-catalyst-13.1-legacy-linux-x86.x86_64.run --force
重新启动 sudo reboot