启用DEPTH_TEST时,OpenGL屏幕闪烁

时间:2017-05-13 14:38:55

标签: c++ opengl sdl-2

我的OpenGL应用程序出现问题。当我没有启用DEPTH_TEST时,它绘制正常(除了错误的绘制顺序),但如果我启用它,一切都开始闪烁。 OpenGL不会给出任何错误。我也没有忘记glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);。我对导致问题的原因一无所知。任何帮助,将不胜感激。

Flickering rectangles

的main.cpp

#include <iostream>

#include <SDL2\SDL.h>
#include <GL\glew.h>

#include <glm\glm.hpp>
#include <glm\gtc\matrix_transform.hpp>

#include <fstream>
#include <string>

#include "vertexdata.h"

#define WIDTH 800
#define HEIGHT 600

std::string filetobuf(const char*);

int main(int, char**) {

    // Init the window with an OpenGL context
    SDL_Window *window;
    SDL_Init(SDL_INIT_EVERYTHING);
    window = SDL_CreateWindow("SDL window", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, WIDTH, HEIGHT, SDL_WINDOW_OPENGL);
    SDL_GLContext context = SDL_GL_CreateContext(window);
    glewInit();

    // Create the shaders
    std::string vertexsourceString = filetobuf("tutorial2.vert");
    std::string fragmentsourceString = filetobuf("tutorial2.frag");
    const char* vertexsource = vertexsourceString.c_str();
    const char* fragmentsource = fragmentsourceString.c_str();
    GLuint vertexshader = glCreateShader(GL_VERTEX_SHADER);
    glShaderSource(vertexshader, 1, (const GLchar**)&vertexsource, 0);
    glCompileShader(vertexshader);
    GLuint fragmentshader = glCreateShader(GL_FRAGMENT_SHADER);
    glShaderSource(fragmentshader, 1, (const GLchar**)&fragmentsource, 0);
    glCompileShader(fragmentshader);
    GLuint shaderprogram = glCreateProgram();
    glAttachShader(shaderprogram, vertexshader);
    glAttachShader(shaderprogram, fragmentshader);
    glBindAttribLocation(shaderprogram, 0, "in_Position");
    glBindAttribLocation(shaderprogram, 1, "in_Color");
    glLinkProgram(shaderprogram);
    glUseProgram(shaderprogram);

    // Setup rectangles
    GLuint vao;
    glGenVertexArrays(1, &vao);
    glBindVertexArray(vao);
    GLuint vbo[3];
    glGenBuffers(3, vbo);
    glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, vbo[0]);
    glBufferData(GL_ELEMENT_ARRAY_BUFFER, INDICES_SIZE, indices, GL_STATIC_DRAW);
    glBindBuffer(GL_ARRAY_BUFFER, vbo[1]);
    glBufferData(GL_ARRAY_BUFFER, VERTEX_BUFFER_SIZE, vertices, GL_STATIC_DRAW);
    glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 0, 0);
    glEnableVertexAttribArray(0);
    glBindBuffer(GL_ARRAY_BUFFER, vbo[2]);
    glBufferData(GL_ARRAY_BUFFER, COLOR_BUFFER_SIZE, colors, GL_STATIC_DRAW);
    glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 0, 0);
    glEnableVertexAttribArray(1);

    GLint projectionMatrixLocation = glGetUniformLocation(shaderprogram, "projectionMatrix");
    glm::mat4 projectionMatrix = glm::perspective(70.0f, (float)WIDTH / (float)HEIGHT, 0.0f, 100.0f);
    glUniformMatrix4fv(projectionMatrixLocation, 1, GL_FALSE, &projectionMatrix[0][0]);

    GLint modelMatrixLocation = glGetUniformLocation(shaderprogram, "modelMatrix");

    glClearColor(0, 0, 1, 1);

    glEnable(GL_DEPTH_TEST);

    bool running = true;
    while (running) {
        SDL_Event e;
        while (SDL_PollEvent(&e)) {
            if (e.type == SDL_QUIT) {
                running = false;
            }
        }

        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

        glm::mat4 modelMatrix(1);
        modelMatrix = glm::translate(modelMatrix, glm::vec3(0, 0, -5));
        modelMatrix = glm::rotate(modelMatrix, SDL_GetTicks() / 500.0f, glm::vec3(0, 1, 0));
        glUniformMatrix4fv(modelMatrixLocation, 1, GL_FALSE, &modelMatrix[0][0]);

        glDrawElements(GL_TRIANGLES, INDICES_SIZE, GL_UNSIGNED_BYTE, 0);

        SDL_GL_SwapWindow(window);
    }

    SDL_GL_DeleteContext(context);
    SDL_DestroyWindow(window);
    SDL_Quit();

    return 0;
}

std::string filetobuf(const char* path)
{
    if (path == nullptr) {
        std::cout << "No file specified!" << std::endl;
        return 0;
    }

    std::ifstream file(path);
    if (!file.is_open()) {
        std::cout << "File not found! '" << path << "'" << std::endl;
        return 0;
    }

    std::string source;
    std::string line;

    while (file.good()) {
        std::getline(file, line);
        source += line + "\n";
    }
    file.close();

    return source;
}

vertexdata.h

#pragma once

#include <GL\GL.h>

#define INDICES_SIZE        12
#define COLOR_VECTOR_SIZE   3
#define VERTEX_VECTOR_SIZE  3
#define VERTEX_COUNT        8
#define COLOR_BUFFER_SIZE   COLOR_VECTOR_SIZE * VERTEX_COUNT * sizeof(GLfloat)
#define VERTEX_BUFFER_SIZE  VERTEX_VECTOR_SIZE * VERTEX_COUNT * sizeof(GLfloat)

static GLubyte indices[] = {
    0, 1, 2,
    2, 3, 0,

    4, 5, 6,
    6, 7, 4,
};

static GLfloat colors[] = {
    1, 0, 0,
    1, 0, 0,
    1, 0, 0,
    1, 0, 0,

    0, 1, 0,
    0, 1, 0,
    0, 1, 0,
    0, 1, 0,
};

static GLfloat vertices[] = {
    1,  1, 1,
    1, -1, 1,
    -1, -1, 1,
    -1,  1, 1,

    1,  1, -1,
    1, -1, -1,
    -1, -1, -1,
    -1,  1, -1,
};

注意:我从main.cpp文件中删除了错误检查以减小文件大小。

1 个答案:

答案 0 :(得分:3)

您无法将近平面设置为零。放一些合理的东西,比如0.1f

glm::mat4 projectionMatrix = glm::perspective(70.0f, (float)WIDTH / (float)HEIGHT, 0.1f, 100.0f);