919601-图形程序设计-5
合集下载
相关主题
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
glMaterialfv(GL_FRONT,GL_AMBIENT_AND_DIFFUSE,material_am biemt);
函数的第一个参数指定多边形的前面(GL_FRONT),背 面(GL_BACK)或者两面(GL_FRONT_AND_BACK) 具有指定的材质属性。第二个参数则指定当前设置的是哪 一种材质属性,这里我们用GL_AMBIENT_AND_DIFFUSE, 即设置环境光和漫反射光的值。最后一个参数是一个数组, 它包含了构成属性的RGBA值。
GLfloat light_position[]={1.0,1.0,1.0,0.0}; glLightfv(GL_LIGHT0,GL_POSITION,light_position);
光源位置坐标采用的齐次坐标(x, y, z, w),这里的w 为0,所以相应的光源是定向光,(x, y, z)描述光源的方 向,这个方向也要进行模型变换。GL_POSITION的缺 省值是(0.0, 0.0, 1.0, 0.0),它定义了一个方向指向Z负 轴的平行光源。若w非零,光源为定位光源。(x, y, z, w)指定光源在齐次坐标系下的具体位置,这个位置经
镜面光也具有一个特定的方向,被物体表面强烈 地反射到相反方向。例如一个点光源照射一个光滑金 属球时会在表面上形成一块特别亮的区域,即绘画艺 术中的“高光(Highlight)”,它是光源在金属球面上产 生的镜面反射光。对于较光滑物体如金属及塑料,其 镜面反射光的高光区域小而亮;相反,粗糙表面的镜 面如粉笔和毛巾反射光呈发散状态,几乎不存在镜面 光,只能够看到有光泽而已。
glLightf(GL_LIGHT0,GL_CONSTANT_ATTENUATION,2.0); glLightf(GL_LIGHT0,GL_LINEAR_ATTENUATION,1.0); glLightf(GL_LIGHT0,GL_QUADRATIC_ATTENUATION,0.5);
注意:环境光、漫反射光和镜面光的强度都衰减,只有 辐射光和全局环境光的强度不衰减。
glEnable(GL_COLOR_MATERIAL); glColorMaterial(GL_FRONT, GL_AMBIENT_AND_DIFFUSE);
5.2 创建光源
接下来,我们就可以动手创建第一个光源,使得 场景中的物体在光线的照射下具有真实感。光源的创 建涉及定位和衰减、个数以及光源的位置和方向等细 节。
思考:
尽管光源发出的光具有相同分布的频 率,但是它的环境、散射和镜面成分可能 不同。如果红色墙壁的房间内有一盏白色 的灯,请分析各种光的成分及颜色分别是 什么?
5.1.2 材料颜色
当我们使用光照来描述多边形,总是说它由具有 某些反射属性的材质组成,而不说它具有特殊的颜色。 这样我们指定物体的颜色,就必须指定物体材质对环 境光、漫反射光和镜面光源的反射属性。通常,我们 用材质对光的红、绿、蓝三原色的反射率来近似定义 材质属性。象光源一样,材质颜色也分成环境、漫反 射和镜面反射成分,它们决定了材质对环境光、漫反 射光和镜面反射光的反射程度。
5.2.1 定位和衰减
光源有无穷远光源和近光源两种形式。无穷远光 源又称作定向光源,即这种光到达物体时是平行光, 例如现实生活中的太阳光。近光源又称作定位光源, 光源在场景中的位置影响场景的光照效果,尤其影响 光到达物体的方向。台灯是定位光源的范例。在以前 所有与光照有关的例子里都采用的是定向光源,如:
1. 环境光(AMBIENT LIGHT)
环境光是指在环境中进行充分散射,无法分辨其 方向的光。它有光源,但是由于被周围的环境,如地 面、天空、墙壁等多次反射,无法确定它的来源具体 是什么。环境光均匀地从周围环境入射至景物表面并 等量地向各个方向反射出去。一般说来,房间里的环 境光成分要多一些,户外的相反要少得多,因为大部 分光按相同的方向照射,而在户外很少有其他物体反 射的光。如户外的探照灯能够包含的环境光成分就比 较少,绝大多数光线沿着一个方向照射,并且很少能 够遇到物体反射进入眼睛。
在进行光照计算时,物体的最终颜色是由其材质属性的 RGB值 和光照属性的RGB值共同决定的。例如,如果当 前的环境光源的RGB值为(0.5,1.0,0.5),而物体的 材质的环境反射成分的RGB值为(0.5,0.5,0.5),那 么物体最终的颜色为: (0.5×0.5,1.0×0.5,0.5×0.5)=(0.25,0.5,0.25) 即将每个环境光源的成分与材质的环境反射率相乘。这样, 物体表面的颜色为三项RGB值的叠加:材质对环境光的反 射率与环境光结合的RGB值;材质对漫反射光的反射率与 漫反射光结合的RGB值;材质对镜面光的反射率与镜面反 射光结合的RGB值。注意,当叠加的RGB中任何一个颜 色分量的值大于1.0,那么就用1.0计算。
注意,在大多数情况下,环境光和漫反射光的成分是相同 的,而一般不需要指定镜面反射指数,除非需要镜面亮斑。
第二种更常用的方法是使用颜色跟踪法。通过颜色跟踪法, 只需要通过调用glColor就可以设置材质属性。要使颜色跟 踪法有效,必须调用带有参数GL_COLOR_MATERIAL的 glEnable函数。然后用glColorMaterial函数指定多边形的哪 一个面使用颜色跟踪法。代码如下:
glLightf(GL_LIGHT0,GL_SPOT_CUTOFF,45.0);
3. 定义聚光方向。
聚光方向决定聚光光锥的轴,它使用齐次坐标定义,缺 省值为(0.0,0.0,-1.0),即指向Z负轴。聚光方向也要进行几 何变换,其结果保存在视点坐标系中。聚光方向是通过函 数glLightfv使用参数GL_SPOT_DIRECTION定义,如下面 一段代码:
在设置了光照模型之后,我们还需要设置绘制物体的材 质属性,使多边形能够反射光,这样就可以看到三棱锥了。 设置材质属性的方法有两种,一种是在绘制每个多边形或 者多边形集和之前利用glMaterial函数。
下面的代码指定了后面绘制的多边形都具有相同的材质属 性:
GLfloat material_ambiemt[]={0.75f, 0.75f, 0.75f, 1.0f};
由于真实感图形是通过景物表面的颜色和明暗色调来表 现景物的几何形状、空间位置以及表面材料的,而一个物体 表面所呈现的颜色是由表面向视线方向辐射的光能决定的。 在计算机图形学中,常采用一个既能表示光能大小又能表示 其颜色组成的物理量即光亮度(luminance)或光强 (intensity of light)来描述物体表面朝某方向辐射光能的颜 色。
采用这个物理量可以正确描述光在物体表面的反射、透 射和吸收现象,因而可以正确计算处物体表面在空间给定方 向上的光能颜色。
物体表面向空间给定方向辐射的光强可应用光照模型 进行计算。简单的光照模型通常假定物体表面是光滑的且 由理想材料构成,因此只考虑光源照射在物体表面产生的 反射光,所生成的图形可以模拟处不透明物体表面的明暗 过渡,具有一定的真实感效果。复杂的光照模型除了考虑 上述因素外,还要考虑周围环境的光对物体表面的影响。 如光亮平滑的物体表面会将环境中其它物体映像在表面上, 而通过透明物体也可看到其后的环境景象。这类光照模型 称为整体光照模型,它能模拟出镜面映像、透明等较精致 的光照效果。
5.2.2 聚光灯
定位光源可以定义成聚光灯形式,即将光的形状限制在一 个圆锥内。OpenGL中聚光的定义包括以下几步: 1. 定义聚光源位置。 因为聚光源也是定向光源,所以他的位置同一般定向光一 样。 2. 定义聚光截止角。 利用函数glLightf使用参数GL_SPOT_CUTOFF定义聚光 光锥的轴与中心线的夹角,也可说成是光锥顶角的一半。 缺省时,这个参数为180.0,即顶角为360度,光向所有的 方向发射,因此聚光关闭。一般在聚光启动情况下,聚光 截止角限制在[0.0,90.0]之间,如下面一行代码设置截止角 为45度:
GLfloat spot_direction[]={-1.0f, -1.0f, 0.0f}; glLightfv(GL_LIGHT0, GL_SPOT_DIRECTION, spot_direction);
4. 定义聚光指数。
参数GL_SPOT_EXPONENT控制光的集中程度,光锥中心 的光强最大,越靠边的光强越小,缺省时为0。如下面的代码:
glMaterialfv函数的第一个参数指定多边形的前面 (GL_FRONT),背面(GL_BACK)或者两面 (GL_FRONT_AND_BACK)具有指定的材质属性。第二 个参数则指定当前设置的是哪一种材质属性,这里我们使 用GL_AMBIENT_AND_DIFFUSE,即设置环境光和漫反射 光的值。最后一个参数是一个数组,它包含了构成属性的 RGBA值。
为了更真实的绘制图形,还要考虑物体表面的细节 纹理,这通常使用一种称为“纹理映射”(texture mapping) 的技术把已有的平面花纹图案映射到物体表面上,并在应 用光照模型时将这些花纹的颜色考虑进去,物体表面细节 的模拟使绘制的图形更接近自然景物。
5.1.1 发射光,环境光,漫反射光和镜面反射光
5.1 真实世界与OPENGL光照
真实感图形绘制是计算机图形学的一个重要组成 部分,它综合利用数学、物理学、计算机科学和其它科 学知识在计算机图形设备上生成象彩色照片那样的具有 真实感的图形。
一般说来,用计算机在图形设备上生成真实感图 形必须完成以下四个步骤:一是用建模,即用一定的数 学方法建立所需三维场景的几何描述,场景的几何描述 直接影响图形的复杂性和图形绘制的计算耗费;二是将 三维几何模型经过一定变换转为二维平面透视投影图; 三是确定场景中所有可见面,运用隐藏面消隐算法将视 域外或被遮挡住的不可见面消去;四是计算场景中可见 面的颜色,即根据基于光学物理的光照模型计算可见面 投射到观察者眼中的光亮度大小和颜色分量,并将它转 换成适合图形设备的颜色值,从而确定投影画面上每一 象素的颜色,最终生成图形。
当光照射到一个物Leabharlann Baidu表面上时,可能会出现如下情形: 首先,光可以通过物体表面向空间反射,产生反射光;其次, 对于透明物体,光可以穿透该物体并从另一端射出,产生透 射光;最后,部分光被物体表面吸收而转换成热。在这些光 中,人眼可以观察到的是反射光和透射光。物体体本身还有 可能发光,比如发光的灯泡。这里我们暂时不考虑透明物体, 这样场景中可能存在以下几种类型的光,即环境光、漫反射 光、镜面光和辐射光。
2.漫反射光(DIFFUSE LIGHT)
漫反射光来自某个方向。它从正面照射物体表面 时比倾斜时更明亮。一旦它照射到物体上,则在各个 方向上均匀地发散出去。因此无论观察点在任何位置, 看到的物体都是一样亮。。来自特定位置和特定方向 的任何光,都可能有散射成分。
3.镜面反射光(SPECULAR LIGHT)
过模型变换等在视点坐标系下保存下来。
真实的光,离光源越远则光强越小。因为定向光源 是无穷远光源,因此距离的变换对光强的影响几乎没有, 所以定向光没有衰减,而定位光有衰减。OpenGL的光 衰减是通过光源的发光量乘以衰减因子计算出来的。其 中缺省状态下,常数衰减因子是1.0,其余两个因子都 是0.0。用户也可以自己定义这些值,如:
4. 发射光
辐射光模拟源自某些物体的光,是最简单的一种 光。在光照模型中,物体表面发射光可增加物体的 亮度,它直接从物体发出并且不受任何光源影响。
在OpenGL中,场景中来自几个不同光源的光可以 单独打开或者关闭。房间内打开一盏电灯时,大多 数光直接来自于这个灯泡,但也有一些光从墙壁反 射过来,这种反射过来的光可称之为环境光,可认 为是均匀散布的,没有特定的方向。场景中也可以 有其他环境光,这些光线经过多次反射,无法确认 来源。当然光源本身还有可能发出发射光。由于我 们知道光是一种波,而颜色仅仅是我们可以看见的 一种光波,所以每种光照成分都是由RGBA值定义的。
函数的第一个参数指定多边形的前面(GL_FRONT),背 面(GL_BACK)或者两面(GL_FRONT_AND_BACK) 具有指定的材质属性。第二个参数则指定当前设置的是哪 一种材质属性,这里我们用GL_AMBIENT_AND_DIFFUSE, 即设置环境光和漫反射光的值。最后一个参数是一个数组, 它包含了构成属性的RGBA值。
GLfloat light_position[]={1.0,1.0,1.0,0.0}; glLightfv(GL_LIGHT0,GL_POSITION,light_position);
光源位置坐标采用的齐次坐标(x, y, z, w),这里的w 为0,所以相应的光源是定向光,(x, y, z)描述光源的方 向,这个方向也要进行模型变换。GL_POSITION的缺 省值是(0.0, 0.0, 1.0, 0.0),它定义了一个方向指向Z负 轴的平行光源。若w非零,光源为定位光源。(x, y, z, w)指定光源在齐次坐标系下的具体位置,这个位置经
镜面光也具有一个特定的方向,被物体表面强烈 地反射到相反方向。例如一个点光源照射一个光滑金 属球时会在表面上形成一块特别亮的区域,即绘画艺 术中的“高光(Highlight)”,它是光源在金属球面上产 生的镜面反射光。对于较光滑物体如金属及塑料,其 镜面反射光的高光区域小而亮;相反,粗糙表面的镜 面如粉笔和毛巾反射光呈发散状态,几乎不存在镜面 光,只能够看到有光泽而已。
glLightf(GL_LIGHT0,GL_CONSTANT_ATTENUATION,2.0); glLightf(GL_LIGHT0,GL_LINEAR_ATTENUATION,1.0); glLightf(GL_LIGHT0,GL_QUADRATIC_ATTENUATION,0.5);
注意:环境光、漫反射光和镜面光的强度都衰减,只有 辐射光和全局环境光的强度不衰减。
glEnable(GL_COLOR_MATERIAL); glColorMaterial(GL_FRONT, GL_AMBIENT_AND_DIFFUSE);
5.2 创建光源
接下来,我们就可以动手创建第一个光源,使得 场景中的物体在光线的照射下具有真实感。光源的创 建涉及定位和衰减、个数以及光源的位置和方向等细 节。
思考:
尽管光源发出的光具有相同分布的频 率,但是它的环境、散射和镜面成分可能 不同。如果红色墙壁的房间内有一盏白色 的灯,请分析各种光的成分及颜色分别是 什么?
5.1.2 材料颜色
当我们使用光照来描述多边形,总是说它由具有 某些反射属性的材质组成,而不说它具有特殊的颜色。 这样我们指定物体的颜色,就必须指定物体材质对环 境光、漫反射光和镜面光源的反射属性。通常,我们 用材质对光的红、绿、蓝三原色的反射率来近似定义 材质属性。象光源一样,材质颜色也分成环境、漫反 射和镜面反射成分,它们决定了材质对环境光、漫反 射光和镜面反射光的反射程度。
5.2.1 定位和衰减
光源有无穷远光源和近光源两种形式。无穷远光 源又称作定向光源,即这种光到达物体时是平行光, 例如现实生活中的太阳光。近光源又称作定位光源, 光源在场景中的位置影响场景的光照效果,尤其影响 光到达物体的方向。台灯是定位光源的范例。在以前 所有与光照有关的例子里都采用的是定向光源,如:
1. 环境光(AMBIENT LIGHT)
环境光是指在环境中进行充分散射,无法分辨其 方向的光。它有光源,但是由于被周围的环境,如地 面、天空、墙壁等多次反射,无法确定它的来源具体 是什么。环境光均匀地从周围环境入射至景物表面并 等量地向各个方向反射出去。一般说来,房间里的环 境光成分要多一些,户外的相反要少得多,因为大部 分光按相同的方向照射,而在户外很少有其他物体反 射的光。如户外的探照灯能够包含的环境光成分就比 较少,绝大多数光线沿着一个方向照射,并且很少能 够遇到物体反射进入眼睛。
在进行光照计算时,物体的最终颜色是由其材质属性的 RGB值 和光照属性的RGB值共同决定的。例如,如果当 前的环境光源的RGB值为(0.5,1.0,0.5),而物体的 材质的环境反射成分的RGB值为(0.5,0.5,0.5),那 么物体最终的颜色为: (0.5×0.5,1.0×0.5,0.5×0.5)=(0.25,0.5,0.25) 即将每个环境光源的成分与材质的环境反射率相乘。这样, 物体表面的颜色为三项RGB值的叠加:材质对环境光的反 射率与环境光结合的RGB值;材质对漫反射光的反射率与 漫反射光结合的RGB值;材质对镜面光的反射率与镜面反 射光结合的RGB值。注意,当叠加的RGB中任何一个颜 色分量的值大于1.0,那么就用1.0计算。
注意,在大多数情况下,环境光和漫反射光的成分是相同 的,而一般不需要指定镜面反射指数,除非需要镜面亮斑。
第二种更常用的方法是使用颜色跟踪法。通过颜色跟踪法, 只需要通过调用glColor就可以设置材质属性。要使颜色跟 踪法有效,必须调用带有参数GL_COLOR_MATERIAL的 glEnable函数。然后用glColorMaterial函数指定多边形的哪 一个面使用颜色跟踪法。代码如下:
glLightf(GL_LIGHT0,GL_SPOT_CUTOFF,45.0);
3. 定义聚光方向。
聚光方向决定聚光光锥的轴,它使用齐次坐标定义,缺 省值为(0.0,0.0,-1.0),即指向Z负轴。聚光方向也要进行几 何变换,其结果保存在视点坐标系中。聚光方向是通过函 数glLightfv使用参数GL_SPOT_DIRECTION定义,如下面 一段代码:
在设置了光照模型之后,我们还需要设置绘制物体的材 质属性,使多边形能够反射光,这样就可以看到三棱锥了。 设置材质属性的方法有两种,一种是在绘制每个多边形或 者多边形集和之前利用glMaterial函数。
下面的代码指定了后面绘制的多边形都具有相同的材质属 性:
GLfloat material_ambiemt[]={0.75f, 0.75f, 0.75f, 1.0f};
由于真实感图形是通过景物表面的颜色和明暗色调来表 现景物的几何形状、空间位置以及表面材料的,而一个物体 表面所呈现的颜色是由表面向视线方向辐射的光能决定的。 在计算机图形学中,常采用一个既能表示光能大小又能表示 其颜色组成的物理量即光亮度(luminance)或光强 (intensity of light)来描述物体表面朝某方向辐射光能的颜 色。
采用这个物理量可以正确描述光在物体表面的反射、透 射和吸收现象,因而可以正确计算处物体表面在空间给定方 向上的光能颜色。
物体表面向空间给定方向辐射的光强可应用光照模型 进行计算。简单的光照模型通常假定物体表面是光滑的且 由理想材料构成,因此只考虑光源照射在物体表面产生的 反射光,所生成的图形可以模拟处不透明物体表面的明暗 过渡,具有一定的真实感效果。复杂的光照模型除了考虑 上述因素外,还要考虑周围环境的光对物体表面的影响。 如光亮平滑的物体表面会将环境中其它物体映像在表面上, 而通过透明物体也可看到其后的环境景象。这类光照模型 称为整体光照模型,它能模拟出镜面映像、透明等较精致 的光照效果。
5.2.2 聚光灯
定位光源可以定义成聚光灯形式,即将光的形状限制在一 个圆锥内。OpenGL中聚光的定义包括以下几步: 1. 定义聚光源位置。 因为聚光源也是定向光源,所以他的位置同一般定向光一 样。 2. 定义聚光截止角。 利用函数glLightf使用参数GL_SPOT_CUTOFF定义聚光 光锥的轴与中心线的夹角,也可说成是光锥顶角的一半。 缺省时,这个参数为180.0,即顶角为360度,光向所有的 方向发射,因此聚光关闭。一般在聚光启动情况下,聚光 截止角限制在[0.0,90.0]之间,如下面一行代码设置截止角 为45度:
GLfloat spot_direction[]={-1.0f, -1.0f, 0.0f}; glLightfv(GL_LIGHT0, GL_SPOT_DIRECTION, spot_direction);
4. 定义聚光指数。
参数GL_SPOT_EXPONENT控制光的集中程度,光锥中心 的光强最大,越靠边的光强越小,缺省时为0。如下面的代码:
glMaterialfv函数的第一个参数指定多边形的前面 (GL_FRONT),背面(GL_BACK)或者两面 (GL_FRONT_AND_BACK)具有指定的材质属性。第二 个参数则指定当前设置的是哪一种材质属性,这里我们使 用GL_AMBIENT_AND_DIFFUSE,即设置环境光和漫反射 光的值。最后一个参数是一个数组,它包含了构成属性的 RGBA值。
为了更真实的绘制图形,还要考虑物体表面的细节 纹理,这通常使用一种称为“纹理映射”(texture mapping) 的技术把已有的平面花纹图案映射到物体表面上,并在应 用光照模型时将这些花纹的颜色考虑进去,物体表面细节 的模拟使绘制的图形更接近自然景物。
5.1.1 发射光,环境光,漫反射光和镜面反射光
5.1 真实世界与OPENGL光照
真实感图形绘制是计算机图形学的一个重要组成 部分,它综合利用数学、物理学、计算机科学和其它科 学知识在计算机图形设备上生成象彩色照片那样的具有 真实感的图形。
一般说来,用计算机在图形设备上生成真实感图 形必须完成以下四个步骤:一是用建模,即用一定的数 学方法建立所需三维场景的几何描述,场景的几何描述 直接影响图形的复杂性和图形绘制的计算耗费;二是将 三维几何模型经过一定变换转为二维平面透视投影图; 三是确定场景中所有可见面,运用隐藏面消隐算法将视 域外或被遮挡住的不可见面消去;四是计算场景中可见 面的颜色,即根据基于光学物理的光照模型计算可见面 投射到观察者眼中的光亮度大小和颜色分量,并将它转 换成适合图形设备的颜色值,从而确定投影画面上每一 象素的颜色,最终生成图形。
当光照射到一个物Leabharlann Baidu表面上时,可能会出现如下情形: 首先,光可以通过物体表面向空间反射,产生反射光;其次, 对于透明物体,光可以穿透该物体并从另一端射出,产生透 射光;最后,部分光被物体表面吸收而转换成热。在这些光 中,人眼可以观察到的是反射光和透射光。物体体本身还有 可能发光,比如发光的灯泡。这里我们暂时不考虑透明物体, 这样场景中可能存在以下几种类型的光,即环境光、漫反射 光、镜面光和辐射光。
2.漫反射光(DIFFUSE LIGHT)
漫反射光来自某个方向。它从正面照射物体表面 时比倾斜时更明亮。一旦它照射到物体上,则在各个 方向上均匀地发散出去。因此无论观察点在任何位置, 看到的物体都是一样亮。。来自特定位置和特定方向 的任何光,都可能有散射成分。
3.镜面反射光(SPECULAR LIGHT)
过模型变换等在视点坐标系下保存下来。
真实的光,离光源越远则光强越小。因为定向光源 是无穷远光源,因此距离的变换对光强的影响几乎没有, 所以定向光没有衰减,而定位光有衰减。OpenGL的光 衰减是通过光源的发光量乘以衰减因子计算出来的。其 中缺省状态下,常数衰减因子是1.0,其余两个因子都 是0.0。用户也可以自己定义这些值,如:
4. 发射光
辐射光模拟源自某些物体的光,是最简单的一种 光。在光照模型中,物体表面发射光可增加物体的 亮度,它直接从物体发出并且不受任何光源影响。
在OpenGL中,场景中来自几个不同光源的光可以 单独打开或者关闭。房间内打开一盏电灯时,大多 数光直接来自于这个灯泡,但也有一些光从墙壁反 射过来,这种反射过来的光可称之为环境光,可认 为是均匀散布的,没有特定的方向。场景中也可以 有其他环境光,这些光线经过多次反射,无法确认 来源。当然光源本身还有可能发出发射光。由于我 们知道光是一种波,而颜色仅仅是我们可以看见的 一种光波,所以每种光照成分都是由RGBA值定义的。