如何启用两个对象的不同 GL_POSITION
Posted
技术标签:
【中文标题】如何启用两个对象的不同 GL_POSITION【英文标题】:How to enable different GL_POSITION of two objects 【发布时间】:2019-08-10 05:36:32 【问题描述】:我想创建两个具有不同灯光位置的对象。但是即使我设置了不同的位置参数,第二个物体(金球)的光位置总是与第一个物体(银球)相同。
我已经启用了一个又一个对象的光。但是第二个总是和第一个/上面的一样。
// light from top right
GLfloat light_position_top_right[] = 1.0, 1.0, 1.0, 0.0 ;
// light from bottom left
GLfloat light_position_bottom_left[] = -1.0, -1.0, 1.0, 0.0 ;
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glLightfv(GL_LIGHT0, GL_POSITION, light_position_top_right);
glLightfv(GL_LIGHT1, GL_POSITION, light_position_bottom_left);
glEnable(GL_LIGHTING);
glEnable(GL_LIGHT0);
glEnable(GL_LIGHT1);
glEnable(GL_DEPTH_TEST);
你可以在这个gist找到完整的代码。
我希望第二个对象的位置从左下角开始。但它从右上角显示为第一个对象。
【问题讨论】:
【参考方案1】:您的灯光位置的第四个坐标必须是1.0
而不是0.0
,否则由于投影变换的工作原理,灯光会表现得好像它们在指定方向上无限远。
第四个坐标为0.0
:
第四个坐标为1.0
:
至于为什么有两个高光而不是只有一个,您忘记为您的灯光设置正确的glLight*
设置。默认情况下,GL_LIGHT0
以白色漫反射和高光颜色开头,但所有其他灯光默认具有黑色漫反射和高光颜色。
编辑:
如果您希望单独的球体使用单独的灯光,则需要在 init()
期间初始化灯光。但是,不要马上glEnable
ing 灯,而是执行以下操作:
void display(void)
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glPushMatrix();
glTranslatef(1.0, 0.0, -1.0);
glEnable(GL_LIGHT0);
drawGraySphere();
glutSolidSphere(0.5, 50, 50);
glDisable(GL_LIGHT0);
glPopMatrix();
glPushMatrix();
glTranslatef(-0.75, -0.8, 0.0);
glEnable(GL_LIGHT1);
drawGoldSphere();
glutSolidSphere(0.5, 50, 50);
glDisable(GL_LIGHT1);
glPopMatrix();
glFlush();
或者,在渲染每个球体之前,您可以选择只使用单个灯光,并在每帧使用glLight*
更改其参数。如果您打算拥有一堆对象,每个对象都有自己的光,这是更好的选择。
【讨论】:
对不起,但不是很清楚。GLfloat light_position_top_right[] = 1.0, 1.0, 1.0, 1.0 ;
和GLfloat light_position_bottom_left[] = -1.0, -1.0, 1.0, 1.0 ;
我已经更新了第四个坐标,但是结果却不如预期。
我刚刚通过添加我的期望更新了我的要点。
啊,你想对第一个对象使用 GL_LIGHT0,对第二个对象使用 GL_LIGHT1?在这种情况下,您需要在两个对象之间正确使用glEnable(GL_LIGHT*)
和glDisable(GL_LIGHT*)
。不用担心,重新启用后,您无需再次设置灯光参数。
或者,您可以一直重复使用GL_LIGHT0
,并始终根据需要在对象之间设置参数。
是的,我的第一个对象是 GL_LIGHT0,第二个对象是 GL_LIGHT1。但是,我尝试像这样启用和禁用灯光,但没有运气。它根本没有光。 glEnable(GL_LIGHTING);glEnable(GL_LIGHT0);glDisable(GL_LIGHT0);glEnable(GL_LIGHT1);glDisable(GL_LIGHT1);glEnable(GL_DEPTH_TEST);
【参考方案2】:
这是您的代码,已修改为您希望它执行的操作:
#include<windows.h>
#include <GL/glut.h>
#include <GL/glu.h>
#include <GL/gl.h>
#include <stdio.h>
#include <math.h>
#include <stdlib.h>
void drawGoldSphere()
GLfloat mat_specular[] = 0.628281, 0.555802, 0.366065, 1.0 ;
GLfloat mat_shininess[] = 51.2 ;
GLfloat mat_ambient[] = 0.24725, 0.1995, 0.0745, 1.0 ;
GLfloat mat_diffuse[] = 0.75164, 0.60648, 0.22648, 1.0 ;
//Material Properties
glMaterialfv(GL_FRONT, GL_AMBIENT, mat_ambient);
glMaterialfv(GL_FRONT, GL_DIFFUSE, mat_diffuse);
glMaterialfv(GL_FRONT, GL_SPECULAR, mat_specular);
glMaterialfv(GL_FRONT, GL_SHININESS, mat_shininess);
void drawGraySphere()
GLfloat mat_specular[] = 1.0, 1.0, 1.0, 1.0 ;
GLfloat mat_shininess[] = 50.0 ;
glMaterialfv(GL_FRONT, GL_SPECULAR, mat_specular);
glMaterialfv(GL_FRONT, GL_SHININESS, mat_shininess);
void init(void)
// light from middle left
//GLfloat light_position[] = 0.0, 0.0, 0.0, 1.0 ;
// light from top right
GLfloat light_position_top_right[] = 1.0, 1.0, 1.0, 0.0 ;
// light from bottom left
GLfloat light_position_bottom_left[] = -1.0, -1.0, 1.0, 0.0 ;
// light from bottom left
//GLfloat light_position[] = -0.1, -0.1, -0.1, 0.0 ;
// light from middle top
//GLfloat light_position[] = 0.0, 1.0, 0.0, 0.0 ;
// light from middle right
//GLfloat light_position[] = 1.0, 0.0, 0.0, 0.0 ;
// light from middle middle
//GLfloat light_position[] = 0.0, 0.0, 1.0, 0.0 ;
// light from middle bottom
//GLfloat light_position[] = 0.0, -1.0, 1.0, 0.0 ;
GLfloat no_mat[] = 0.0, 0.0, 0.0, 1.0 ;
GLfloat light_diffuse[] = 1.0, 1.0, 1.0, 1.0 ;
GLfloat light_specular[] = 1.0, 1.0, 1.0, 1.0 ;
GLfloat high_shininess[] = 100.0 ;
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glLightfv(GL_LIGHT0, GL_DIFFUSE, light_diffuse);
glLightfv(GL_LIGHT0, GL_SPECULAR, light_specular);
glLightfv(GL_LIGHT0, GL_POSITION, light_position_top_right);
glLightfv(GL_LIGHT1, GL_DIFFUSE, light_diffuse);
glLightfv(GL_LIGHT1, GL_SPECULAR, light_specular);
glLightfv(GL_LIGHT1, GL_POSITION, light_position_bottom_left);
glEnable(GL_LIGHTING);
glEnable(GL_DEPTH_TEST);
void display(void)
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
glPushMatrix();
glTranslatef(1.0, 0.0, -1.0);
glEnable(GL_LIGHT0);
drawGraySphere();
glutSolidSphere(0.5, 50, 50);
glDisable(GL_LIGHT0);
glPopMatrix();
glPushMatrix();
glTranslatef(-0.75, -0.8, 0.0);
glEnable(GL_LIGHT1);
drawGoldSphere();
glutSolidSphere(0.5, 50, 50);
glDisable(GL_LIGHT1);
glPopMatrix();
glFlush();
void reshape(int w, int h)
glViewport(0, 0, (GLsizei) w, (GLsizei) h);
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
if (w <= h)
glOrtho(-1.5, 1.5, -1.5*(GLfloat)h/(GLfloat)w,
1.5*(GLfloat)h/(GLfloat)w, -10.0, 10.0);
else
glOrtho(-1.5*(GLfloat)w/(GLfloat)h,
1.5*(GLfloat)w/(GLfloat)h, -1.5, 1.5, -10.0, 10.0);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
int main(int argc, char** argv)
glutInit(&argc, argv);
glutInitDisplayMode(GLUT_SINGLE | GLUT_RGB | GLUT_DEPTH);
glutInitWindowSize(500, 500);
glutInitWindowPosition(100, 100);
glutCreateWindow(argv[0]);
init();
glutDisplayFunc(display);
glutReshapeFunc(reshape);
glutMainLoop();
return 0;
渲染结果:
【讨论】:
以上是关于如何启用两个对象的不同 GL_POSITION的主要内容,如果未能解决你的问题,请参考以下文章
将源自不同表的两个 postgresql tsvector 字段连接到单个 postgresql 视图中,以启用联合全文搜索