为啥三角形没有显示在屏幕上(OpenGL 3.3)?

Posted

技术标签:

【中文标题】为啥三角形没有显示在屏幕上(OpenGL 3.3)?【英文标题】:Why the triangle isn't showing on screen (OpenGL 3.3)?为什么三角形没有显示在屏幕上(OpenGL 3.3)? 【发布时间】:2013-01-17 20:38:39 【问题描述】:

我都试过了。遵循来自http://www.opengl-tutorial.org/beginners-tutorials/ 的 OpenGL 教程。 在教程 4 中,它被要求在你的身上做一个双重模型。但是我不能同时渲染三角形和立方体(三角形没有出现)。只是做同样的事情,更改与三角形相关的变量的名称。我没有在任何其他网站上找到关于这个 OPenGL 3.3 语法的答案,只是在完全不同的语法上找到了答案(我不想每次发现错误时都改变我做瘦的方式 - 这就像在任何事情之后改变一切错误。对我来说没有任何意义)。

代码有点大,但很多东西只是打开Window并运行主循环(和立方体坐标。它们不是VBO。我稍后会学习):

// Include standard headers
#include <stdio.h>
#include <stdlib.h>
// Include GLEW. Always include it before gl.h and glfw.h, since it's a bit magic.
#include <GL/glew.h>
// Include GLFW
#include <GL/glfw.h>
// Include GLM
#include <glm/glm.hpp>
#include "common/shader.hpp"
#include <iostream>
#include <glm/gtc/matrix_transform.hpp>
using namespace std;
using namespace glm;


// Include standard headers
#include <stdio.h>
#include <stdlib.h>

// Include GLEW
#include <GL/glew.h>

// Include GLFW
#include <GL/glfw.h>

// Include GLM
#include <glm/glm.hpp>
#include <glm/gtc/matrix_transform.hpp>
using namespace glm;

#include <common/shader.hpp>

int main(int argc, char *argv[] )

    // Initialise GLFW
    if( !glfwInit() )
    
        fprintf( stderr, "Failed to initialize GLFW\n" );
        return -1;
    
    glfwOpenWindowHint(GLFW_FSAA_SAMPLES, 4); // 4x antialiasing
    glfwOpenWindowHint(GLFW_OPENGL_VERSION_MAJOR, 3); // We want OpenGL 3.3
    glfwOpenWindowHint(GLFW_OPENGL_VERSION_MINOR, 3);
    glfwOpenWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE); //We don't want the old OpenGL

    // Open a window and create its OpenGL context
    if( !glfwOpenWindow( 1024, 768, 0,0,0,0, 32,0, GLFW_WINDOW ) )
    
        fprintf( stderr, "Failed to open GLFW window\n" );
        glfwTerminate();
        return -1;
    



    // Initialize GLEW
    if (glewInit() != GLEW_OK) 
        fprintf(stderr, "Failed to initialize GLEW\n");
        return -1;
    

    // Enable depth test
    glEnable(GL_DEPTH_TEST);
    // Accept fragment if it closer to the camera than the former one
    glDepthFunc(GL_LESS);

    GLuint VertexArrayID;
    glGenVertexArrays(1, &VertexArrayID);
    glBindVertexArray(VertexArrayID);

    // Create and compile our GLSL program from the shaders
    GLuint programID = LoadShaders( "TransformVertexShader.vertexshader", "ColorFragmentShader.fragmentshader" );


    //Perspective Matrix

   // Projection matrix : 45° Field of View, 4:3 ratio, display range : 0.1 unit <-> 100 units
    mat4 Projection = perspective(45.0f, 4.0f/3.0f, 0.1f, 100.0f);
    // Camera matrix
    mat4 View = lookAt(
    vec3(4,3,-3), // Camera is at (4,3,3), in World Space
    vec3(0,0,0), // and looks at the origin
    vec3(0,1,0)  // Head is up (set to 0,-1,0 to look upside-down)
    );
    // Model matrix : an identity matrix (model will be at the origin)
    mat4 Model = mat4(1.0f);  // Changes for each model !
    // Our ModelViewProjection : multiplication of our 3 matrices
    mat4 MVP = Projection * View * Model; // Remember, matrix multiplication is the other way around


    // Get a handle for our "MVP" uniform.
    // Only at initialisation time.
    GLuint MatrixID = glGetUniformLocation(programID, "MVP");

    // Send our transformation to the currently bound shader,
    // in the "MVP" uniform
    // For each model you render, since the MVP will be different (at least the M part)
    glUniformMatrix4fv(MatrixID, 1, GL_FALSE, &MVP[0][0]);


    mat4 triangle_Model = mat4(1.0f);
    mat4 triangle_MPV = Projection * View * triangle_Model;
    GLuint triangle_MatrixID = glGetUniformLocation(programID, "MPV");
    glUniformMatrix4fv(triangle_MatrixID, 1, GL_FALSE, &triangle_MPV[0][0]);






    static const GLfloat triangle_buffer_data[] = 
        -2.0f, -3.0f, 1.0f,
         2.0f, -3.0f, 1.0f,
         0.0f,  3.0f,-1.0f
    ;
    // This will identify our vertex buffer
    GLuint triangle_vertexbuffer;
    // Generate 1 buffer, put the resulting identifier in vertexbuffer
    glGenBuffers(1, &triangle_vertexbuffer);
    // The following commands will talk about our 'vertexbuffer' buffer
    glBindBuffer(GL_ARRAY_BUFFER, triangle_vertexbuffer);
    // Give our vertices to OpenGL.
    glBufferData(GL_ARRAY_BUFFER, sizeof(triangle_buffer_data), triangle_buffer_data, GL_STATIC_DRAW);







    // Our vertices. Tree consecutive floats give a 3D vertex; Three consecutive vertices give a triangle.
    // A cube has 6 faces with 2 triangles each, so this makes 6*2=12 triangles, and 12*3 vertices
    static const GLfloat g_vertex_buffer_data[] = 
       -1.0f,-1.0f,-1.0f, // triangle 1 : begin
       -1.0f,-1.0f, 1.0f,
       -1.0f, 1.0f, 1.0f, // triangle 1 : end
        1.0f, 1.0f,-1.0f, // triangle 2 : begin
       -1.0f,-1.0f,-1.0f,
       -1.0f, 1.0f,-1.0f, // triangle 2 : end
        1.0f,-1.0f, 1.0f,
       -1.0f,-1.0f,-1.0f,
        1.0f,-1.0f,-1.0f,
        1.0f, 1.0f,-1.0f,
        1.0f,-1.0f,-1.0f,
       -1.0f,-1.0f,-1.0f,
       -1.0f,-1.0f,-1.0f,
       -1.0f, 1.0f, 1.0f,
       -1.0f, 1.0f,-1.0f,
        1.0f,-1.0f, 1.0f,
       -1.0f,-1.0f, 1.0f,
       -1.0f,-1.0f,-1.0f,
       -1.0f, 1.0f, 1.0f,
       -1.0f,-1.0f, 1.0f,
        1.0f,-1.0f, 1.0f,
        1.0f, 1.0f, 1.0f,
        1.0f,-1.0f,-1.0f,
        1.0f, 1.0f,-1.0f,
        1.0f,-1.0f,-1.0f,
        1.0f, 1.0f, 1.0f,
        1.0f,-1.0f, 1.0f,
        1.0f, 1.0f, 1.0f,
        1.0f, 1.0f,-1.0f,
       -1.0f, 1.0f,-1.0f,
        1.0f, 1.0f, 1.0f,
       -1.0f, 1.0f,-1.0f,
       -1.0f, 1.0f, 1.0f,
        1.0f, 1.0f, 1.0f,
       -1.0f, 1.0f, 1.0f,
        1.0f,-1.0f, 1.0f
    ;
    // This will identify our vertex buffer
    GLuint vertexbuffer;
    // Generate 1 buffer, put the resulting identifier in vertexbuffer
    glGenBuffers(1, &vertexbuffer);
    // The following commands will talk about our 'vertexbuffer' buffer
    glBindBuffer(GL_ARRAY_BUFFER, vertexbuffer);
    // Give our vertices to OpenGL.
    glBufferData(GL_ARRAY_BUFFER, sizeof(g_vertex_buffer_data), g_vertex_buffer_data, GL_STATIC_DRAW);

    // One color for each vertex. They were generated randomly.
    static const GLfloat g_color_buffer_data[] = 
        0.583f,  0.771f,  0.014f,
        0.609f,  0.115f,  0.436f,
        0.327f,  0.483f,  0.844f,
        0.822f,  0.569f,  0.201f,
        0.435f,  0.602f,  0.223f,
        0.310f,  0.747f,  0.185f,
        0.597f,  0.770f,  0.761f,
        0.559f,  0.436f,  0.730f,
        0.359f,  0.583f,  0.152f,
        0.483f,  0.596f,  0.789f,
        0.559f,  0.861f,  0.639f,
        0.195f,  0.548f,  0.859f,
        0.014f,  0.184f,  0.576f,
        0.771f,  0.328f,  0.970f,
        0.406f,  0.615f,  0.116f,
        0.676f,  0.977f,  0.133f,
        0.971f,  0.572f,  0.833f,
        0.140f,  0.616f,  0.489f,
        0.997f,  0.513f,  0.064f,
        0.945f,  0.719f,  0.592f,
        0.543f,  0.021f,  0.978f,
        0.279f,  0.317f,  0.505f,
        0.167f,  0.620f,  0.077f,
        0.347f,  0.857f,  0.137f,
        0.055f,  0.953f,  0.042f,
        0.714f,  0.505f,  0.345f,
        0.783f,  0.290f,  0.734f,
        0.722f,  0.645f,  0.174f,
        0.302f,  0.455f,  0.848f,
        0.225f,  0.587f,  0.040f,
        0.517f,  0.713f,  0.338f,
        0.053f,  0.959f,  0.120f,
        0.393f,  0.621f,  0.362f,
        0.673f,  0.211f,  0.457f,
        0.820f,  0.883f,  0.371f,
        0.982f,  0.099f,  0.879f
    ;

    GLuint colorbuffer;
    glGenBuffers(1, &colorbuffer);
    glBindBuffer(GL_ARRAY_BUFFER, colorbuffer);
    glBufferData(GL_ARRAY_BUFFER, sizeof(g_color_buffer_data), g_color_buffer_data, GL_STATIC_DRAW);

    glfwSetWindowTitle( "Tutorials" );


    // Dark blue background
    glClearColor(0.0f, 0.0f, 0.3f, 0.0f);



    // Ensure we can capture the escape key being pressed below
    glfwEnable( GLFW_STICKY_KEYS );


    //main loop
    do
        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

        // Use our shader
        glUseProgram(programID);

        //First Attribute: Draw a Cube
        glEnableVertexAttribArray(0);
        glBindBuffer(GL_ARRAY_BUFFER, vertexbuffer);
        glVertexAttribPointer(
           0,                  // attribute 0. No particular reason for 0, but must match the layout in the shader.
           3,                  // size
           GL_FLOAT,           // type
           GL_FALSE,           // normalized?
           0,                  // stride
           (void*)0            // array buffer offset
        );

        // 2nd attribute buffer : colors
        glEnableVertexAttribArray(1);
        glBindBuffer(GL_ARRAY_BUFFER, colorbuffer);
        glVertexAttribPointer(
            1,                                // attribute. No particular reason for 1, but must match the layout in the shader.
            3,                                // size
            GL_FLOAT,                         // type
            GL_FALSE,                         // normalized?
            0,                                // stride
            (void*)0                          // array buffer offset
        );



        // Draw the triangle !
        glDrawArrays(GL_TRIANGLES, 0, 12*3); // 12*3 indices starting at 0 -> 12 triangles -> 6 squares

        glDisableVertexAttribArray(0);


        //3rd attribute: draw a triangle
        glEnableVertexAttribArray(2);
        glBindBuffer(GL_ARRAY_BUFFER, triangle_vertexbuffer);
        glVertexAttribPointer(
           2,
           3,
           GL_FLOAT,
           GL_FALSE,
           0,
           (void*)0
        );

        glDrawArrays(GL_TRIANGLES,0,3);

        glDisableVertexAttribArray(2);




        // Send our transformation to the currently bound shader,
        // in the "MVP" uniform
        // For each model you render, since the MVP will be different (at least the M part)
        glUniformMatrix4fv(MatrixID, 1, GL_FALSE, &MVP[0][0]);

        glUniformMatrix4fv(triangle_MatrixID, 1 ,GL_FALSE, &triangle_MPV[0][0]);


        // Swap buffers
        glfwSwapBuffers();

     // Check if the ESC key was pressed or the window was closed
    while( glfwGetKey( GLFW_KEY_ESC ) != GLFW_PRESS &&
    glfwGetWindowParam( GLFW_OPENED ) );

    glfwTerminate();

    // Cleanup VBO
    glDeleteBuffers(1, &vertexbuffer);
    glDeleteVertexArrays(1, &VertexArrayID);
    glDeleteBuffers(1, &triangle_vertexbuffer);
    glDeleteBuffers(1, &colorbuffer);


return EXIT_SUCCESS;

而且,我不认为这是问题所在(教程说它需要 1 个着色器,并且在立方体上它工作得很好),但我也会在这里发布着色器代码:

Collor Fragment shader:

 #version 330 core

 // Interpolated values from the vertex shaders
 in vec3 fragmentColor;

 // Ouput data
 out vec3 color;


 void main()

 // Output color = color specified in the vertex shader, 
 // interpolated between all 3 surrounding vertices
color = fragmentColor;






TransformVertexShadder:

#version 330 core

// Input vertex data, different for all executions of this shader.
layout(location = 0) in vec3 vertexPosition_modelspace;
layout(location = 1) in vec3 vertexColor;

// Output data ; will be interpolated for each fragment.
out vec3 fragmentColor;
// Values that stay constant for the whole mesh.
uniform mat4 MVP;

void main()    

// Output position of the vertex, in clip space : MVP * position
gl_Position =  MVP * vec4(vertexPosition_modelspace,1);

// The color of each vertex will be interpolated
// to produce the color of each fragment
fragmentColor = vertexColor;

谁能帮帮我?

【问题讨论】:

【参考方案1】:

我认为你不能将片段颜色输出为 vec3,我在大多数情况下使用 vec4(color, 1.0)。

【讨论】:

你确实不能,而且着色器根本不应该编译。如果你不检查错误代码,你当然不会注意到这一点。 这很奇怪。在立方体上它适用于 vec3。在教程中它说绘制另一个对象可以使用相同的着色器。

以上是关于为啥三角形没有显示在屏幕上(OpenGL 3.3)?的主要内容,如果未能解决你的问题,请参考以下文章

为啥我的三角形对象没有被绘制?

OpenGL几何着色器三角形不会没有错误地绘制

为啥 glColorPointer 不给三角形着色 - 以及 opengl es 的其他奇怪的东西

C OpenGL glfw3三角形不显示

OpenGL程序没有显示三角形

为啥绘制我的 OpenGL-ES VBO 网格会阻止其他三角形显示?