c++ - 无法在我的 Qt 应用程序中启用 GLSL 1.40

标签 c++ qt opengl qt5 shader

我想在 Qt 中从 VS2013 移植 Box2D 的演示项目。但我有一个不寻常的问题。当我在 VS 中运行演示项目时,我收到有关我的 openGL 配置信息的消息。

enter image description here

我用 QOpeGL 包装器替换了 Qt 上的代码并更改了着色器的初始化和 opengl 函数的调用。

首先,我像这样更改默认表面格式:

QSurfaceFormat format;
format.setVersion(3, 1);
format.setProfile(QSurfaceFormat::CoreProfile);
QSurfaceFormat::setDefaultFormat(format);

但是当我调试程序时,我的表面格式停留在 3.0。

enter image description here

当我尝试创建着色器时,我收到如下错误消息:

QOpenGLShader::compile(Vertex): ERROR: 0:1: '140' : version number not supported
ERROR: 0:2: 'layout' : syntax error 
*** Problematic Vertex shader source code ***
#version 140
#line 1
uniform mat4 projectionMatrix;
layout(location = 0) in vec2 v_position;
layout(location = 1) in vec4 v_color;
layout(location = 2) in float v_size;
out vec4 f_color;
void main(void)
{
    f_color = v_color;
    gl_Position = projectionMatrix * vec4(v_position, 0.0f, 1.0f);
gl_PointSize = v_size;
}

为什么 VS 可以创建着色器并与 OpenGL 3.1/GLSL 1.40 一起工作,但 Qt 不能这样做?

初始化 GL(m_functions - QOpenGLExtraFunctions)

void MainOpenGLWidget::initializeGL()
{
    makeCurrent();

    qDebug() << "OPENGL " << QSurfaceFormat::defaultFormat().majorVersion() <<
            "." << QSurfaceFormat::defaultFormat().minorVersion();

    m_functions.initializeOpenGLFunctions();
    m_functions.glClearColor(0, 0, 0, 0);

    g_camera.m_width = 1024;
    g_camera.m_height = 640;

    g_debugDraw.Create(&m_functions);
}

函数g_debugDraw.Create(...):

void Create(QOpenGLExtraFunctions *functions)
{
    const char *vs = \
                    "#version 140\n"
                    "uniform mat4 projectionMatrix;\n"
                    "layout(location = 0) in vec2 v_position;\n"
                    "layout(location = 1) in vec4 v_color;\n"
                    "layout(location = 2) in float v_size;\n"
                    "out vec4 f_color;\n"
                    "void main(void)\n"
                    "{\n"
                    "   f_color = v_color;\n"
                    "   gl_Position = projectionMatrix * vec4(v_position, 0.0f, 1.0f);\n"
                    "   gl_PointSize = v_size;\n"
                    "}\n";

    ...

    m_program.addShaderFromSourceCode(QOpenGLShader::Vertex, vs);

    ...

    m_functions = *functions;

    m_functions.glGenVertexArrays(1, &m_vaoId);
    m_functions.glGenBuffers(3, m_vboIds);

    m_functions.glBindVertexArray(m_vaoId);
    m_functions.glEnableVertexAttribArray(m_vertexAttribute);
    m_functions.glEnableVertexAttribArray(m_colorAttribute);
    m_functions.glEnableVertexAttribArray(m_sizeAttribute);

    ...
}

我在调用 m_program.addShaderFromSourceCode(QOpenGLShader::Vertex, vs); 时出错

最佳答案

如果您真的想坚持使用 GLSL #version 140,请替换以下行

layout(location = 0) in vec2 v_position;
layout(location = 1) in vec4 v_color;
layout(location = 2) in float v_size;

通过

in vec2 v_position;
in vec4 v_color;
in float v_size;

在#version 330 之前,显式属性位置不是 GLSL 的一部分。

在您的 C++ 代码中启用着色器之前,请小心查询着色器的属性位置。着色器编译器可能会也可能不会按照声明的顺序对它们进行排序。

const int POS_LOCATION = glGetAttribLocation(program_id, "v_position");
if(-1 != POS_LOCATION)
{
    glEnableVertexAttribArray(POS_LOCATION);
    ...
    glVertexAttribPointer(POS_LOCATION, ... );
    ...
}

我发现在 GLSL #version 140 的文档中没有提到 layout(location = x)。

https://www.khronos.org/registry/OpenGL/specs/gl/GLSLangSpec.1.40.pdf

直到第 35 页的#version 330 才提到。

https://www.khronos.org/registry/OpenGL/specs/gl/GLSLangSpec.3.30.pdf

在您的情况下,着色器编译器错误消息有点误导。也许如果您更新显卡驱动程序,您将获得更好的着色器编译器。

关于c++ - 无法在我的 Qt 应用程序中启用 GLSL 1.40,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/45211717/

相关文章:

c++ - 这个函数指针怎么可能不指向一个函数呢?

C++:在并行数组中保存数据

opengl - 如何对用三角形绘制的 "perfect cube"进行纹理处理?

c++ - 特征表达式模板比指数的手动循环慢

C++:成员和非成员函数之间的区别

qt - "c: Command not found"错误

qt - CDB 在 Qt 中崩溃

c++ - 即时翻译 Qt QML 应用程序

c++ - OpenGL,俯仰力偏航为0

qt - OpenGL资源共享策略