C++ Opengl Lighting不起作用

C++ Opengl Lighting doesnt work

本文关键字:不起作用 Lighting Opengl C++      更新时间:2023-10-16

我已经搜索了解决方案,但没有一个奏效。我已经启动了光照,除了对象之外,所有物体都保持未点亮状态。

当我下载示例时,它们可以工作,但是当我尝试在我的上面启用照明时不行。

这是代码:

#include <GLFW/glfw3.h>
#include <glmgtxtransform.hpp>
#include <iostream>
#include <string>
#include <vector>
#include <GLglut.h>
#include "Camera.h"
#define windowWidth 1024
#define windowHeight 620
#define CAMERA_SPEED 0.1
GLFWwindow* Window;
CCamera Camera;
bool aPressed = false;
bool dPressed = false;
bool wPressed = false;
bool sPressed = false;
bool ePressed = false;
bool qPressed = false;
bool spacePressed = false;
static void keyEvent(GLFWwindow* window_, int key, int scancode, int action, int mods)
{
    if(key == GLFW_KEY_ESCAPE && action == GLFW_PRESS)
        glfwSetWindowShouldClose(Window, GL_TRUE);
    if(key == GLFW_KEY_A && action == GLFW_PRESS)
        aPressed=true;
    if(key == GLFW_KEY_D && action == GLFW_PRESS)
        dPressed=true;
    if(key == GLFW_KEY_W && action == GLFW_PRESS)
        wPressed=true;
    if(key == GLFW_KEY_S && action == GLFW_PRESS)
        sPressed=true;
    if(key == GLFW_KEY_E && action == GLFW_PRESS)
        ePressed=true;
    if(key == GLFW_KEY_Q && action == GLFW_PRESS)
        qPressed=true;
    if(key == GLFW_KEY_SPACE && action == GLFW_PRESS)
        spacePressed=true;
    if(key == GLFW_KEY_A && action == GLFW_RELEASE)
        aPressed=false;
    if(key == GLFW_KEY_D && action == GLFW_RELEASE)
        dPressed=false;
    if(key == GLFW_KEY_W && action == GLFW_RELEASE)
        wPressed=false;
    if(key == GLFW_KEY_S && action == GLFW_RELEASE)
        sPressed=false;
    if(key == GLFW_KEY_E && action == GLFW_RELEASE)
        ePressed=false;
    if(key == GLFW_KEY_Q && action == GLFW_RELEASE)
        qPressed=false;
    if(key == GLFW_KEY_SPACE && action == GLFW_RELEASE)
        spacePressed=false;
}
int main()
{
    if(!glfwInit())
    {
        exit(EXIT_FAILURE);
    }
    Window = glfwCreateWindow(windowWidth, windowHeight, "3D 2.0", NULL, NULL);
    if(!Window)
    {
        glfwTerminate();
        exit(EXIT_FAILURE);
    }
    glClearColor (0.0, 0.0, 0.0, 0.0);
    GLfloat light_ambient[] =
    {0.0, 0.0, 0.0, 1.0};
    GLfloat light_diffuse[] =
    {1.0, 0.0, 0.0, 1.0};
    GLfloat light_specular[] =
    {1.0, 1.0, 1.0, 1.0};
/* light_position is NOT default value */
    GLfloat light_position[] =
    {1.0, 1.0, 1.0, 0.0};
    glLightfv(GL_LIGHT0, GL_AMBIENT, light_ambient);
    glLightfv(GL_LIGHT0, GL_DIFFUSE, light_diffuse);
    glLightfv(GL_LIGHT0, GL_SPECULAR, light_specular);
    glLightfv(GL_LIGHT0, GL_POSITION, light_position);
    glEnable(GL_LIGHT0);
    glDepthFunc(GL_LESS);
    glEnable(GL_DEPTH_TEST);
    glEnable(GL_LIGHTING);
    glfwMakeContextCurrent(Window);
    glfwSwapInterval(1);
    glfwSetKeyCallback(Window, keyEvent);
    while(!glfwWindowShouldClose(Window))
    {
        glViewport(0, 0, (double)windowWidth, (double)windowHeight);
        //glClearColor(0.0,0.5,1.0,1.0);
        glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
        glMatrixMode(GL_PROJECTION_MATRIX);
        glLoadIdentity();

        gluPerspective( 90, (double)windowWidth / (double)windowHeight, 0.1, 100 );
        gluLookAt(0,0,5,0,0,-0.1,0.0,1.0,0.0);

        glMatrixMode(GL_MODELVIEW_MATRIX);

        if(aPressed)
            Camera.StrafeRight(-CAMERA_SPEED);
        if(dPressed)
            Camera.StrafeRight(CAMERA_SPEED);
        if(wPressed)
            Camera.MoveForward(-CAMERA_SPEED);
        if(sPressed)
            Camera.MoveForward(CAMERA_SPEED);
        if(ePressed)
            Camera.MoveUpward(CAMERA_SPEED);
        if(qPressed)
            Camera.MoveUpward(-CAMERA_SPEED);
        /* Draw Here */
        Camera.Render();
        /* Draw Cube */
        glPushMatrix();
        glTranslated(0.0,0.0,0.0);
        glColor3f(0.0,0.0,0.0);
        glLineWidth(4);
        //glutWireCube(1);
        glColor3f(0.0,0.3,1.0);
        glNormal3f(0.0,0.0,1.0);
        glutSolidCube(1);
        glPopMatrix();
        /* Draw Teapot */
        glPushMatrix();
        glTranslated(3.0,0.0,0.0);
        glColor3f(0.0,0.0,0.0);
        glLineWidth(4);
        glutWireTeapot(1);
        glColor3f(0.6,0.3,0.0);
        glutSolidTeapot(1);
        glPopMatrix();
        /* Draw Torus */
        glPushMatrix();
        glTranslated(-3.0,0.0,0.0);
        glColor3f(0.0,0.0,0.0);
        glLineWidth(4);
        glutWireTorus(0.25, 1, 16, 16);
        glColor3f(0.6,0.3,0.3);
        glutSolidTorus(0.25, 1, 16, 16);
        glPopMatrix();

        glfwSwapBuffers(Window);
        glfwPollEvents();
    }
    glfwDestroyWindow(Window);
    glfwTerminate();
    exit(EXIT_SUCCESS);
}

您正在使用glut函数,而无需先调用glutInit

main(int argc, char *argv[])
{
    glutInit(&argc, argv);
    ...

而且glfwMakeContextCurrent(Window);必须在任何OpenGL函数之前调用。

为了获得正确的照明,请考虑调整光照方向 (-1,-1,-1,0) 会更好地使用实际视图矩阵。

gluLookAt()用于

构建视图矩阵。因此,必须在GL_MODELVIEW矩阵模式下指定它。初始转换设置的调用顺序应为:

glMatrixMode(GL_PROJECTION_MATRIX);
glLoadIdentity();
gluPerspective(90.0, (double)windowWidth / (double)windowHeight, 0.1, 100.0);
glMatrixMode(GL_MODELVIEW_MATRIX);
glLoadIdentity();
gluLookAt(0.0, 0.0, 5.0, 0.0, 0.0, -0.1, 0.0, 1.0, 0.0);

实际上,您可以将此调用序列移到事件循环之外。无需为每一帧重复此操作。好吧,gluPerspective()调用取决于窗口大小,因此您应该在窗口大小更改时重复它。但看起来您的代码中硬连线了窗口大小。

您可能还想考虑使用 glMaterialfv() 设置材料属性。启用照明后,用于设置颜色的glColor3f()调用将不会产生所需的效果。

当然,正如在另一个答案中已经指出的那样,您需要在进行任何OpenGL调用之前调用glfwMakeContextCurrent()

我希望您知道您正在使用的大多数OpenGL功能已被弃用,并且在最新版本的OpenGL(Core Profile以及OpenGL ES 2.0及更高版本)中不再可用。