【问题标题】:OpenGL Light changes : Ambient to Diffuse or Specular works but not the oppositeOpenGL 光照变化:环境到漫反射或镜面反射有效,但不是相反
【发布时间】:2012-04-16 20:27:23
【问题描述】:

我在 OpenGL 中遇到了灯光问题:

我用这段代码改变了我的球灯:

switch(option) {                                            
case ambient:                                               
  glLightfv(GL_LIGHT0,GL_AMBIENT,lum_ambient);              
  glMaterialfv(GL_FRONT,GL_SPECULAR,mat_ambient);           
  break;                                                    
case diffuse:                                               
  glLightfv(GL_LIGHT0,GL_DIFFUSE,lum_diffuse);              
  glMaterialfv(GL_FRONT,GL_DIFFUSE,mat_diffuse);            
  break;                                                    
case specular:                                              
  glLightfv(GL_LIGHT0,GL_SPECULAR,lum_speculaire);          
  glMaterialfv(GL_FRONT,GL_SPECULAR,mat_speculaire);        
  break;                                                    
}     

我可以从 Ambient 更改为漫反射或镜面反射。但是一旦我改变了,我就不能回到环境,更糟糕的是:要回到漫反射,我需要调用环境。

而且我不认为它来自这段代码:

   switch (key) {                              
   case 27:                                    
       exit(1);                                
   case '1':                                   
     option = ambient;                         
     glutPostRedisplay();                      
     break;                                    
   case '2':                                   
     option = diffuse;                         
     glutPostRedisplay();                      
     break;                                    
   case '3':                                   
     option = specular;                        
     glutPostRedisplay();                      
     break;                                    
   }  

知道我的问题来自哪里吗?

【问题讨论】:

    标签: opengl light


    【解决方案1】:

    问题来自这样一个事实,即状态不会因为您更改了一些 other 状态而消失。如果你有两个全局变量:

    int x;
    int y;
    

    更改y 不会影响x。如果你有这个 switch 语句:

    switch(option)
    {
    case ambient:
      x = 4;
      break;
    case diffuse:
      y = 6;
      break;
    ...
    }
    

    如果你用diffuse执行这个,然后用ambient执行它,y的值是多少? 还是 6。当然是,因为你没有改变它。

    OpenGL 中没有“环境”、“漫反射”或“镜面反射”光照。这些中的每一个都只是每个灯的照明模型中的不同术语。也就是说,OpenGL 总是为每个灯光执行所有这些。您看不到高光照明组件的任何效果的原因是初始高光材质颜色为。这会产生一个零镜面光照组件。

    一旦您更改了高光材质颜色,它将保持新值,直到您再次更改它。如果要“关闭”镜面光照,则需要将镜面材质颜色重置为零。其他人也一样。


    您正尝试在三种照明模型的设置和默认设置之间切换。所以你必须真正做到这一点:你必须将值重置为 OpenGL 默认值。这些可以在 OpenGL 规范中找到。

    除了材质颜色之外,您还必须设置光强度。

    如果您不想查看规范,这里是默认值:

    • 环境光:(0.0, 0.0, 0.0, 1.0)
    • 环境材质:(0.2, 0.2, 0.2, 1.0)
    • 漫射光:(1.0, 1.0, 1.0, 1.0)(仅适用于light0。所有其他灯光默认为(0.0 0.0, 0.0, 1.0)
    • 漫射材质:(0.8, 0.8, 0.8, 1.0)
    • 镜面光:(1.0, 1.0, 1.0, 1.0)(仅适用于light0。所有其他灯光默认为(0.0 0.0, 0.0, 1.0)
    • 镜面材质:(0.0 0.0, 0.0, 1.0)

    【讨论】:

    • 我开始明白了。但是我是否必须重置 glMaterial 或 glLight 或两者兼而有之?
    • @Matthieu: ahem "如果你想'关闭'高光照明,那么你需要重置高光材质 颜色归零。”
    • 嗯,这就是我所做的,但是用我的环境光和镜面光获得一个黑球。 (我将 GL_DIFFUSE 重置为 0.0,0.0,0.0,1.0)
    • @MatthieuRiegler:抱歉,请参阅我的编辑。我忘记了 OpenGL 的光照模型是愚蠢的。真的,切换到着色器;你会帮大家一个忙。
    【解决方案2】:

    首先,我会使用不同的灯光,而不仅仅是 Light0。另外,请尝试在打开新灯之前关闭所有灯:

    glDisable(GL_LIGHT0);
    

    一些帮助:Light source - OPENGL

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2015-02-05
      • 2018-06-18
      • 2018-04-30
      • 1970-01-01
      • 2018-07-09
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多