用 OpenGL 绘制的立方体缺乏深度/透视?

问题描述 投票:0回答:2

我正在尝试在 OpenGL 和 GLFW 中绘制一个简单的立方体。

在下面的代码中,我可以绘制立方体,但它只是显示为一个简单的矩形。这里发生了什么?

#if defined(_WIN32) || defined(_WIN64)
#include <windows.h>
#endif

#include <stdio.h>
#include <stdlib.h>
#include <iostream>
#include <fstream>

#define GLEW_STATIC
#include <GL/glew.h>
#include <GL/gl.h>
#include <GLFW/glfw3.h>

const char* gameTitle = "TEST";
GLFWwindow* window;

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,
-1, -1, -1,   -1, -1,  1,    1, -1,  1,    1, -1, -1,
-1,  1, -1,   -1,  1,  1,    1,  1,  1,    1,  1, -1,
-1, -1, -1,   -1,  1, -1,    1,  1, -1,    1, -1, -1,
-1, -1,  1,   -1,  1,  1,    1,  1,  1,    1, -1,  1
};

GLfloat colors[] =
{
0, 0, 0,   0, 0, 1,   0, 1, 1,   0, 1, 0,
1, 0, 0,   1, 0, 1,   1, 1, 1,   1, 1, 0,
0, 0, 0,   0, 0, 1,   1, 0, 1,   1, 0, 0,
0, 1, 0,   0, 1, 1,   1, 1, 1,   1, 1, 0,
0, 0, 0,   0, 1, 0,   1, 1, 0,   1, 0, 0,
0, 0, 1,   0, 1, 1,   1, 1, 1,   1, 0, 1
};

static void controls(GLFWwindow* window, int key, int scancode, int action, int mods)
{
    if(action == GLFW_PRESS)
        if(key == GLFW_KEY_ESCAPE)
            glfwSetWindowShouldClose(window, GL_TRUE);
}

bool initWindow(const int resX, const int resY)
{
    if(!glfwInit())
    {
        fprintf(stderr, "Failed to initialize GLFW\n");
        return false;
    }
    glfwWindowHint(GLFW_SAMPLES, 4); // 4x antialiasing

    // Open a window and create its OpenGL context
    window = glfwCreateWindow(resX, resY, gameTitle, NULL, NULL);

    if(window == NULL)
    {
        fprintf(stderr, "Failed to open GLFW window.\n");
        glfwTerminate();
        return false;
    }

    glfwMakeContextCurrent(window);
    glfwSetKeyCallback(window, controls);

    // Get info of GPU and supported OpenGL version
    printf("Renderer: %s\n", glGetString(GL_RENDERER));
    printf("OpenGL version supported %s\n", glGetString(GL_VERSION));

    glEnable(GL_DEPTH_TEST); // Depth Testing
    glDepthFunc(GL_LEQUAL);
    glDisable(GL_CULL_FACE);
    glCullFace(GL_BACK);
    return true;
}

static void drawCube()
{
    static float alpha = 0;
    glMatrixMode(GL_PROJECTION_MATRIX);
    glLoadIdentity();
    glTranslatef(0,0,-2);
    glMatrixMode(GL_MODELVIEW_MATRIX);
    //attempt to rotate cube
    //glRotatef(alpha, 1, 0, 0);

    /* We have a color array and a vertex array */
    glEnableClientState(GL_VERTEX_ARRAY);
    glEnableClientState(GL_COLOR_ARRAY);
    glVertexPointer(3, GL_FLOAT, 0, vertices);
    glColorPointer(3, GL_FLOAT, 0, colors);

    /* Send data : 24 vertices */
    glDrawArrays(GL_QUADS, 0, 24);

    /* Cleanup states */
    glDisableClientState(GL_COLOR_ARRAY);
    glDisableClientState(GL_VERTEX_ARRAY);
    alpha += 0.1;
}

static void display()
{
    glClearColor(0.0, 0.8, 0.3, 1.0);
    while(!glfwWindowShouldClose(window))
    {
        // Draw stuff
        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
        drawCube();

        // Update Screen
        //glFlush();
        glfwSwapBuffers(window);

        // Check for any input, or window movement
        glfwPollEvents();

        // Scale to window size
        GLint windowWidth, windowHeight;
        glfwGetWindowSize(window, &windowWidth, &windowHeight);
        glViewport(0, 0, windowWidth, windowHeight);
    }
}

int main(int argc, char** argv)
{
    if(initWindow(1024, 620))
    {
        display();
    }
    printf("Goodbye!\n");
    glfwDestroyWindow(window);
    glfwTerminate();
    return 0;
}

我尝试过“glTransformf(0,0,-10);”,但如果我做任何小于-2的事情,立方体就会消失。在 -2 时,出现正面侧。在默认位置 0 处,我可以看到立方体的背面。

此外,当我尝试旋转它时,显示的只是一个从窗口顶部移动到底部的矩形。看起来很奇怪。

为什么程序会这样?

c++ opengl glfw
2个回答
15
投票
  1. 你永远不会设置一个(有意义的)投影矩阵。
  2. 不要滥用投影矩阵堆栈
  3. 不要将你的矩阵设置为
    drawCube()
    、单一责任原则等等。
  4. 在尝试绘制之前设置您的视口。
  5. C++ 有
  6. c
     前缀版本 (
    stdio.h
     -> 
    cstdio
    ) 的 C 头文件。使用那些来代替。
大家一起:

#include <GL/glew.h> #include <GLFW/glfw3.h> #include <cstdio> void controls(GLFWwindow* window, int key, int scancode, int action, int mods) { if(action == GLFW_PRESS) if(key == GLFW_KEY_ESCAPE) glfwSetWindowShouldClose(window, GL_TRUE); } GLFWwindow* initWindow(const int resX, const int resY) { if(!glfwInit()) { fprintf(stderr, "Failed to initialize GLFW\n"); return NULL; } glfwWindowHint(GLFW_SAMPLES, 4); // 4x antialiasing // Open a window and create its OpenGL context GLFWwindow* window = glfwCreateWindow(resX, resY, "TEST", NULL, NULL); if(window == NULL) { fprintf(stderr, "Failed to open GLFW window.\n"); glfwTerminate(); return NULL; } glfwMakeContextCurrent(window); glfwSetKeyCallback(window, controls); // Get info of GPU and supported OpenGL version printf("Renderer: %s\n", glGetString(GL_RENDERER)); printf("OpenGL version supported %s\n", glGetString(GL_VERSION)); glEnable(GL_DEPTH_TEST); // Depth Testing glDepthFunc(GL_LEQUAL); glDisable(GL_CULL_FACE); glCullFace(GL_BACK); return window; } void drawCube() { 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, -1, -1, -1, -1, -1, 1, 1, -1, 1, 1, -1, -1, -1, 1, -1, -1, 1, 1, 1, 1, 1, 1, 1, -1, -1, -1, -1, -1, 1, -1, 1, 1, -1, 1, -1, -1, -1, -1, 1, -1, 1, 1, 1, 1, 1, 1, -1, 1 }; GLfloat colors[] = { 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 0, 1, 0, 0, 1, 0, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 1, 0, 0, 0, 1, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 1, 0, 1, 1, 1, 1, 1, 1, 0, 1 }; static float alpha = 0; //attempt to rotate cube glRotatef(alpha, 0, 1, 0); /* We have a color array and a vertex array */ glEnableClientState(GL_VERTEX_ARRAY); glEnableClientState(GL_COLOR_ARRAY); glVertexPointer(3, GL_FLOAT, 0, vertices); glColorPointer(3, GL_FLOAT, 0, colors); /* Send data : 24 vertices */ glDrawArrays(GL_QUADS, 0, 24); /* Cleanup states */ glDisableClientState(GL_COLOR_ARRAY); glDisableClientState(GL_VERTEX_ARRAY); alpha += 1; } void display( GLFWwindow* window ) { while(!glfwWindowShouldClose(window)) { // Scale to window size GLint windowWidth, windowHeight; glfwGetWindowSize(window, &windowWidth, &windowHeight); glViewport(0, 0, windowWidth, windowHeight); // Draw stuff glClearColor(0.0, 0.8, 0.3, 1.0); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glMatrixMode(GL_PROJECTION_MATRIX); glLoadIdentity(); gluPerspective( 60, (double)windowWidth / (double)windowHeight, 0.1, 100 ); glMatrixMode(GL_MODELVIEW_MATRIX); glTranslatef(0,0,-5); drawCube(); // Update Screen glfwSwapBuffers(window); // Check for any input, or window movement glfwPollEvents(); } } int main(int argc, char** argv) { GLFWwindow* window = initWindow(1024, 620); if( NULL != window ) { display( window ); } glfwDestroyWindow(window); glfwTerminate(); return 0; }
    

5
投票
我相信你的问题是你基本上使用的是正交投影,或者肯定不是透视的东西,这会给立方体更多的“3D”外观,我认为你正在寻找。

尝试如下操作来设置正确的透视投影矩阵:

glMatrixMode(GL_PROJECTION_MATRIX); glLoadIdentity(); gluPerspective(45, windowWidth / windowHeight, 0.1f, 100.0f); // Draw calls.
    
© www.soinside.com 2019 - 2024. All rights reserved.