Chapter 5. 라이팅(Lighting) 2012-2학기 가상현실
라이팅(Lighting) 은면 제거 실세계와 OpenGL 라이팅 빛이 비춰진 구를 그리는 간단한 예제 광원 생성하기 라이팅 모델 선택하기 재질 속성 정의하기 라이팅에 관련된 수학 컬러 인덱스 모드의 라이팅 2012-2학기 가상현실
은면 제거(hidden-surface removal) 다른 오브젝트에 의해 가려진 솔리드 오브젝트의 일부분을 제거하는 것 은면을 제거하는 가장 쉬운 방법 깊이 버퍼(z-buffer라고도 함)을 사용 하는 것 깊이 버퍼를 사용하기 위해서는 깊이 버퍼링을 활성화 glutInitDisplayMode(GLUT_DEPTH | …); glEnable(GL_DEPTH_TEST); glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT) 2012-2학기 가상현실
은면제거 예제 glutInitDisplayMode(GLUT_DEPTH | …); glEnable(GL_DEPTH_TEST); while (1) { glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); get_viewing_point_from_mouse_position(); draw_3d_object_A(); draw_3d_object_B(); } 2012-2학기 가상현실
실세계와 OpenGL 라이팅 OpenGL에서는 빛을 빨간색, 초록색, 파란색의 성분으로 이루어진것으로 간주. 라이팅 모델에서, 장면의 빛은 여러 개의 광원으로 부터 나오며, 각각의 광원을 끄거나 켤 수 있음. 광원은 빛을 흡수하고 반사할 수 있는 표면에만 영향을 미침. 각 표면은 다양한 속성을 지닌 재질(material)로 이루어졌다고 가정. 재질은 스스로 빛을 낼 수도 있고 거울처럼 입사광의 일부를 모든 방향으로 산란시키거나 광택이 있는 표면처럼 일정한 방향으로 반사시키기도 함. 라이팅 모델에서 조명(lighting)이 ambient, diffuse, specular, emissive와 같은 4가지의 독립적인 성분으로 구성. 2012-2학기 가상현실
Ambient, diffuse, specular, emissive 라이트 Ambient light(주변광) 주변환경에 의해 심하게 산란, 원래 방향을 알 수 없게 된 빛 모든 방향으로부터 오는 것처럼 보임 거실의 배경 조명은 ambient 성분이 많음 Ambient 라이트가 표면에 도달하면 모든 방향으로 골고루 흩어짐 Diffuse light(확산광) 한 방향으로 비추는 빛 정면으로 비출 때가 비스듬히 비출 때 보다 밝게 나타남 표면에 도달하면 모든 방향으로 골고루 산란되기 때문에 보는 방향에 관계 없이 밝기가 일정하다. 특정한 위치나 방향에서 비추는 빛은 대개가 diffuse 라이트이다. 2012-2학기 가상현실
특정한 방향에서 비추고, 특정한 방향으로 반사되는 경향 레이저빔이 고품질의 거울에 부딪히면 100% 정반사된다. Specular light(반사광) 특정한 방향에서 비추고, 특정한 방향으로 반사되는 경향 레이저빔이 고품질의 거울에 부딪히면 100% 정반사된다. 빛나는 금속이나 플라스틱은 specular 성분이 많고 분필이나 카페트와 같은 물체는 specular 성분이 거의 없다. Emissive light 오브젝트 스스로 빛을 내는 것 처럼 보여주는 컬러 오브젝트의 컬러 강도를 높이지만 광원의 영향은 받지 않는다. Emissive 컬러는 전체 장면에 어떤 빛도 추가하지 않는다. 2012-2학기 가상현실
재질 컬러 OpenGL 라이팅 모델에서는 비춰진 빨간색, 초록색, 파란색 빛에 대한 반사율에 따라 재질의 컬러를 계산 빛과 마찬가지로, 재질도 다양한 ambient, diffuse, specular 컬러를 가짐 이들은 각각 재질의 ambient, diffuse, specular 반사율을 결정 Ambient 및 diffuse 반사율은 재질의 전반적인 색을 정의하며, 일반적으로 서로 같은 값을 갖거나 거의 비슷하다. Specular 반사율은 보통 백색이나 회색이므로, specular 하이라이트는 광원의 specular 세기와 동일한 컬러를 가짐 2012-2학기 가상현실
빛과 재질 속성을 위한 RGB값 빛을 지정하기 위한 컬러 성분은 재질의 컬러 성분과는 다른 의미 빛의 경우, 컬러 성분의 값은 각 컬러에 대한 최대 세기 비율 빛의 R, G, B 값이 모두 1.0 이면 가장 밝은 흰색으로 표현됨 0.5이면 컬러는 흰색이나 세기가 절반으로 줄었으므로 회색으로 보인다. 재질의 경우, 각 컬러 성분의 값은 해당 컬러에 대한 반사율 재질에 대해 R=1, G=0.5, B=0이면, 재질은 빨간색 입사광선은 모두 반사하고, 초록색 입사광선은 절반만 반사하며, 파란색 입사광선은 전혀 반사하지 않는다. OpenGL에서 빛은 (LR, LG, LB) 성분을 가지며, 재질은 이 성분에 대한 (MR, MG, MB) 성분을 가지며, 모든 반사 효과를 무시할 경우에 눈에 도달하는 빛은 (LR ∙ MR, LG ∙ MG, LB ∙ MB) 이다. 2012-2학기 가상현실
(R1, G1, B1) 과 (R2, G2, B2) 의 색을 내는 두 개의 빛이 있다면 OpenGL 에서는 (R1+R2, G1+G2, B1+B2)를 생성한다. 2012-2학기 가상현실
빛이 비춰진 구를 그리는 간단한 예제 장면에 조명을 추가하기 위해서는 다음과 같은 단계를 거침 모든 오브젝트의 각 정점마다 법선 벡터를 계산 이러한 법선들은 광원에 대한 오브젝트의 방향을 결정 여러 개의 광원을 만들고, 선택해서 배치 라이팅 연산의 수행을 위해 전역적 ambient 라이트(global ambient light)의 단계와 시점의 유효범위를 정의하는 라이팅 모델을 만들고, 선택 오브젝트에 대한 재질 속성을 정의 2012-2학기 가상현실
빛이 비춰진 구 그리기: light.c #include <GL/glut.h> #include <stdlib.h> void init(void) { GLfloat mat_specular[] = { 1.0, 1.0, 1.0, 1.0 }; GLfloat mat_shininess[] = { 50.0 }; GLfloat light_position[] = { 1.0, 1.0, 1.0, 0.0 }; glClearColor (0.0, 0.0, 0.0, 0.0); glShadeModel (GL_SMOOTH); glMaterialfv(GL_FRONT, GL_SPECULAR, mat_specular); // 추가하기 glMaterialfv(GL_FRONT, GL_SHININESS, mat_shininess); // 추가하기 glLightfv(GL_LIGHT0, GL_POSITION, light_position); // 추가하기 2012-2학기 가상현실
glEnable(GL_LIGHTING); glEnable(GL_LIGHT0); glEnable(GL_DEPTH_TEST); } void display(void) { glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glutSolidSphere (1.0, 20, 16); glFlush (); 2012-2학기 가상현실
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); } 2012-2학기 가상현실
void keyboard(unsigned char key, int x, int y) { switch (key) { case 27: exit(0); break; } 2012-2학기 가상현실
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); glutKeyboardFunc(keyboard); glutMainLoop(); return 0; } 2012-2학기 가상현실
실행 결과 2012-2학기 가상현실
컬러인덱스 모드에서는 라이팅 기능이 다소 제한적이므로 라이팅을 수행할 때는 RGBA 모드를 사용한다. 오브젝트를 구성하는 모든 정점에 대한 법선 벡터 정의하기 법선은 광원에 대한 오브젝트의 방향을 결정 OpenGL에서는 정점마다 할당된 법선을 이용하여 각 정점에 비추는 빛의 양을 계산 앞의 예제인 구에서는 glutSolidSphere() 루틴 안에 구에 대한 법선이 설정됨 라이팅 연산이 제대로 수행되려면 표면 법선을 단위 길이로 지정해야 함 법선의 단위 길이를 갖도록 보장해주려면 glEnable()에 GL_NORMALIZE 나 GL_RESCALE_NORMAL 을 인자로 주고 호출해야 함. 2012-2학기 가상현실
한 개 이상의 광원을 생성하고, 배치하고, 활성화 하기 5-1은 흰색 광원 한 개 사용, 광원의 위치는 glLightfv()로 지정 OpenGL 에서는 최소 8개의 광원을 사용할 수 있고 다양한 컬러를 지정 가능 광원의 속성 정의한 후에 glEnable() 커맨드로 활성화 시켜야 함 glEnable(GL_NIGHTING)을 호출, 라이팅 연산을 수행할 준비를 해야 함 2012-2학기 가상현실
glLightModel*() 커맨드는 라이팅 모델 매개변수들을 설정 라이팅 모델 전역적 ambient 라이트 명시 라이팅 모델 선택하기 glLightModel*() 커맨드는 라이팅 모델 매개변수들을 설정 라이팅 모델 전역적 ambient 라이트 명시 시점을 무한히 먼 곳에 놓을지, 장면 안에 놓을지를 지정 라이팅 연산이 오브젝트 표면의 앞면과 뒷면이 서로 다르게 수행될지 여부를 결정 Specular 컬러를 ambient 및 diffuse 컬러와 별도로 계산할지 여부를 결정 2012-2학기 가상현실
오브젝트의 재질 속성은 빛을 반사하는 방식을 정의, 특정한 재질로 구성된 것처럼 보이게 함 오브젝트의 재질 속성 정의하기 오브젝트의 재질 속성은 빛을 반사하는 방식을 정의, 특정한 재질로 구성된 것처럼 보이게 함 위의 예제에서는 glMaterialfv()를 사용, 재질의 specular 컬러와 shininess만 명시적으로 설정 2012-2학기 가상현실
광원 생성하기 광원은 컬러, 위치, 방향 등과 같은 여러 가지 속성을 지님 빛에 관련된 모든 속성은 glLight*() 커맨드로 지정 속성을 지정할 조명, 지정할 속성, 속성에 대한 속성값을 인자로 받는다. void glLight{if}(GLenum light, GLenum pname, TYPE param); void glLight{if}v(Glenum light, GLenum pname, TYPE *param); 식별자가 light인 조명을 생성 GL_LIGHT0, GL_LIGHT1 ~7 까지 사용 pname 은 지정할 속성을 정의 2012-2학기 가상현실
조명의 속성 glLight*() 의 pname 매개변수에 대한 기본 값 매개변수 이름 기본값 설명 GL_AMBIENT (0.0, 0.0, 0.0, 1.0) Ambient 라이트의 세기 GL_DIFFUSE (1.0, 1.0, 1.0, 1.0), (0.0, 0.0, 0.0, 1.0) Diffuse 라이트의 세기 GL_SPECULAR (1.0, 1.0, 1.0, 1.0), Specular 라이트의 세기 GL_POSITION (0.0, 0.0, 1.0, 0.0) 조명의(x, y, z, w) 위치 GL_SPOT_DIRECTION (0.0, 0.0, -1.0) 조명의(x, y, z) 방향 GL_SPOT_EXPONENT 0.0 스포트라이트 지수 GL_SPOT_CUTOFF 180.0 스포트라이트 절단각 GL_CONSTANT_ATTENUATION 1.0 감쇠율 상수 GL_LINEAR_ATTENUATION 선형 감쇠율 GL_QUADRATIC_ATTENUATION 2차 감쇠율 2012-2학기 가상현실
GL_AMBIENT : ambient 라이트의 세기를 지정 컬러 각각의 조명을 세 가지 컬러 관련 매개변수(GL_AMBIENT, GL_DIFFUSE, GL_SPECULAR) 중 하나로 설정 가능 GL_AMBIENT : ambient 라이트의 세기를 지정 GL_DIFFUSE : 사람들이 일반적으로 생각하는 “빛의 컬러” 의미 GL_SPECULAR : 오브젝트의 specular highlight 의 컬러에 영향 2012-2학기 가상현실
배치와 감쇠 광원이 장면에서 무한히 먼 위치에 있을지, 장면의 바로 근처에 있을지를 선택할 수 있음. 무한히 먼 위치에 있는 경우: 방향(directional) 광원 오브젝트에 도달한 때는 평행한 상태가 됨 예) 태양 장면의 바로 근처에 있는 경우: 위치(positional) 광원 광원의 위치와 빛을 비추는 방향이 장면에 영향을 미친다. 예) 책상 위에 놓인 스탠드 예제 5-1 에서 GLfloat light_position={1.0, 1.0, 1.0, 0.0}; glLightfv(GL_LIGHT0, GL_POSITION, light_position); GL_POSITION 의 4개 값은 x, y, z, w 의미 w 가 0이면 방향 광원을 나타내고 광원의 방향은 (x, y, z) 기본값은 (0, 0, 1, 0) w가 0이 아니면 동차 오브젝트 좌표계(homogeneous object coordinates)에서 (x, y, z) 위치에 놓여진 위치 광원을 의미 2012-2학기 가상현실
방향 광원은 무한히 먼 곳에 있으므로 거리에 따라 빛의 세기가 약해지지 않는다. 위치 광원으로부터 나오는 빛은 감쇠시켜야 한다. 감쇠인자 = d: 광원의 위치와 정점 사이의 거리 kc = GL_CONSTANT_ATTENUATION, 기본값은 1 kl = GL_LINEAR_ATTENUATION, 기본값은 0 kq = GL_QUADRATIC_ATTENUATION, 기본값은 0 1 kc + kld + kqd2 2012-2학기 가상현실
빛을 원뿔 모양으로 방출하도록 설정함으로써 위치 광원으로 스포트라이트(spotlights)를 표현할 수 있음. 스포트라이트를 만들려면 원뿔의 펼쳐질 정도를 정해야 함 위치광원이기 때문에 위치도 반드시 정해주어야 함 GL_SPOT_CUTTOFF 매개변수를 사용, 원뿔의 중심 축과 모서리가 이루는 각을 지정 glLightf(GL_LIGHT0, GL_SPOT_CUTOFF, 45.0); GL_SPOT_CUTOFF 매개변수의 기본값이 180.0이기 때문에 스포트라이트 기능은 기본적으로 비활성화 2012-2학기 가상현실
GLfloat spot_direction[] = {-1.0, -1.0, 0.0}; 스포트라이트 방향 지정 GLfloat spot_direction[] = {-1.0, -1.0, 0.0}; glLightfv (GL_LIGHT0, GL_SPOT_DIRECTION, spot_direction); 원뿔축의 방향을 결정 방향은 오브젝트 좌표로 지정 기본적인 방향은 (0.0, 0.0, -1.0)이며 이것은 음의 z축 방향을 비추게 된다. 스포트라이트의 원뿔 내 빛의 세기 조절 감쇠 인자를 설정하여 빛의 세기에 곱하거나, GL_SPOT_EXPONENT 매개변수를 설정하여 빛이 집중되는 정도를 지정 기본 값은 0이며 빛의 세기는 원뿔의 중심에서 가장 세고 원뿔의 모서리로 갈수록 감쇠되며 감쇠 비율은 원뿔의 중심과 빛이 진행하는 방향이 이루는 각에 대한 cos 값으로 결정 2012-2학기 가상현실
그림5-2 GL_SPOT_CUTOFF 매개변수 2012-2학기 가상현실
다중 조명 한 장면에 최소한 8개의 조명을 사용할 수 있다. 광원의 수가 늘어날수록 수행 속도가 느려짐 8개의 조명을 식별하는데 사용되는 상수 GL_LIGHT0, GL_LIGHT1, GL_LIGHT2, GL_LIGHT3 등 예제 5-3 두 번째 광원 GLfloat Light1_ambient[] = {0.2, 0.2, 0.2, 1.0}; GLfloat Light1_diffuse[] = {1.0, 1.0, 1.0, 1.0}; GLfloat Light1_specular[] = {1.0, 1.0, 1.0, 1.0}; GLfloat Light1_position[] = {-2.0, 2.0, 1.0, 1.0}; GLfloat Light1_direction[] = {-1.0, -1.0, 0.0}; 2012-2학기 가상현실
glLightfv(GL_LIGHT1, GL_AMBIENT, Light1_ambient); glLightfv(GL_LIGHT1, GL_DIFFUSE, Light1_diffuse); glLightfv(GL_LIGHT1, GL_SPECULAR, Light1_specular); glLightfv(GL_LIGHT1, GL_POSITION, Light1_position); glLightfv(GL_LIGHT1, GL_CONSTANT_ATTENUATION, 1.5); glLightfv(GL_LIGHT1, GL_LINEAR_ATTENUATION, 0.5); glLightfv(GL_LIGHT1, GL_QUADRATIC_ATTENUATION, 0.2); glLightfv(GL_LIGHT1, GL_SPOT_CUTOFF, 45.0); glLightfv(GL_LIGHT1, GL_SPOT_DIRECTION, spot_direction); glLightfv(GL_LIGHT1, GL_SPOT_EXPONENT, 2.0); glEnable(GL_LIGHT1); 2012-2학기 가상현실
광원의 위치와 방향 제어하기 OpenGL에서는 광원의 위치와 방향을 기하 프리미티브의 위치와 같은 방식으로 처리 glLight*()를 통해 지정된 광원의 위치나 방향을 현재의 모델뷰 행렬에 의해 변환되어 눈 좌표계에 놓여짐. 즉, 모델뷰 행렬의 내용을 변경시켜서 광원의 위치와 방향을 조절할 수 있다. 살펴볼 내용 움직이지 않는 조명 정지된 오브젝트 주위를 회전하는 조명 시점을 따라 움직이는 조명 2012-2학기 가상현실
조명 고정하기 조명을 고정하려면 뷰잉 변환이나 모델링 변환을 모두 수행 후에 조명의 위치 설정 예제 5-4 고정된 광원 glViewport(0, 0, (Glsizei) w, (Glsizei) h); glMatrixMode(GL_PROJECTION); glLoadIdentity(); if (w <= h) glOrtho(-1.5, 1.5, -1.5*h/w, 1.5*h/w, -10.0, 10.0); else glOrtho(-1.5*h/w, 1.5*h/w, -1.5, 1.5, -10.0, 10.0); glMatrixMode(GL_MODELVIEW); /* 아래부분은 init()에 설정할 내용 */ GLfloat light_position[] = { 1.0, 1.0, 1.0, 1.0, }; glLIghtfv(GL_LIGHT0, GL_POSITION, position); 뷰포트와 투영행렬을 먼저 초기화, 다음 모델뷰 행렬에 단위 행렬을 로드하고, 조명의 위치 설정 2012-2학기 가상현실
조명 이동하기 조명의 위치에 대해 회전 변환이나 이동 변환을 적용, 오브젝트를 중심으로 움직이기 위해서는 모델변환 수행 후, 조명의 위치 지정하는 방법 사용 예제 5-5 독립적으로 이동하는 광원 static GLdouble spin; void display(void){ GLfloat light_position[] = { 0.0, 0.0, 1.5, 1.0}; glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glPushMatrix(); gluLookAt(0.0, 0.0, 5.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0); glPushMarix(); glRotated(spin, 1.0, 0.0, 0.0); glLightfv(GL_LIGHT0, GL_POSITION, light_position); glPopMatrix(); glutSolidTorus(0.275, 0.85, 8, 15); glFlush() } 2012-2학기 가상현실
전역 변수 spin은 입력 장치를 통해 제어된다. display()를 호출하면 조명이 고정된 토러스(Torus) 주변을 spin으로 지정된 만큼 회전한 장면을 그림 뷰잉 변환과 모델링 변환을 분리할 때 사용하는 glPushMatrix(), glPopMatrix()는 모두 모델뷰스택을 사용 2012-2학기 가상현실
모델링 변환으로 조명 움직이기 [예제 5 – 6] #include <GL/glut.h> #include <stdlib.h> static int spin = 0; /* 모델변환을 호출한 뒤 조명의 위치 리셋, 조명을 워드 좌표계상의 *새로운 위치에 놓는다 육면체는 조명의 위치 */ void init(void) { glClearColor (0.0, 0.0, 0.0, 0.0); glShadeModel (GL_SMOOTH); glEnable(GL_LIGHTING); glEnable(GL_LIGHT0); glEnable(GL_DEPTH_TEST); } 2012-2학기 가상현실
GLfloat position[] = { 0.0, 0.0, 1.5, 1.0 }; void display(void) { GLfloat position[] = { 0.0, 0.0, 1.5, 1.0 }; glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glPushMatrix (); gluLookAt (0.0, 0.0, 5.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0); glRotated ((GLdouble) spin, 1.0, 0.0, 0.0); glLightfv (GL_LIGHT0, GL_POSITION, position); 2012-2학기 가상현실
glDisable (GL_LIGHTING); glColor3f (0.0, 1.0, 1.0); glTranslated (0.0, 0.0, 1.5); glDisable (GL_LIGHTING); glColor3f (0.0, 1.0, 1.0); glutWireCube (0.1); glEnable (GL_LIGHTING); glPopMatrix (); glutSolidTorus (0.275, 0.85, 8, 15); glFlush (); } 2012-2학기 가상현실
void reshape (int w, int h) { glViewport (0, 0, (GLsizei) w, (GLsizei) h); glMatrixMode (GL_PROJECTION); glLoadIdentity(); gluPerspective(40.0, (GLfloat) w/(GLfloat) h, 1.0, 20.0); glMatrixMode(GL_MODELVIEW); } void mouse(int button, int state, int x, int y){ switch (button) { case GLUT_LEFT_BUTTON: 2012-2학기 가상현실
if (state == GLUT_DOWN) { spin = (spin + 30) % 360; glutPostRedisplay(); } break; default: break; } void keyboard(unsigned char key, int x, int y){ switch (key) { case 27: exit(0); 2012-2학기 가상현실
void keyboard(unsigned char key, int x, int y) { switch (key) { case 27: exit(0); break; } 2012-2학기 가상현실
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); glutMouseFunc(mouse); glutKeyboardFunc(keyboard); glutMainLoop(); return 0; } 2012-2학기 가상현실
2012-2학기 가상현실
2012-2학기 가상현실
시점에 따라 광원 움직이기 시점에 따라 조명을 움직이게 하려면 뷰잉 변환 이전에 조명의 위치를 지정해야 함 그러면 뷰잉 변환을 빛과 시점에 동시에 적용 여기서 조명이 눈 좌표계에 저장된다. 예제5-7 시점에 따라 이동하는 광원 GLfloat light_position[] = {0.0, 0.0, 0.0, 1.0}; glViewport(0,0, (GLint) w, (GLint) h); glMatrixMode(GL_PROJECTION); glLoadIdentity(); gluPerspective(40.0, (GLfloat) w / (GLfloat) h, 1.0, 100.0); glMatrixMode (GL_MODELVIEW); glLightfv(GL_LIGHT0, GL_POSITION, light_position); 2012-2학기 가상현실
static GLdouble ex, ey, ez, upx, upy, upz; void display (void) { glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glPushMatrix(); gluLookAt(ex, ey, ez, 0.0, 0.0, 0.0, upx, upy, upz); glutSolidTorus(0.275, 0.85, 8, 15); glPopMatrix(); glFlush(); } 2012-2학기 가상현실
lightposition 튜토리얼 조명의 위치 및 모델뷰 행렬의 효과 2012-2학기 가상현실
라이팅 모델 선택하기 OpenGL 라이팅 모델은 다음과 같은 네 가지 요소로 구성되어 있음 전역적 ambient 라이트의 세기 시점의 위치가 장면에 지역적으로 존재하는지, 무한히 멀리 떨어져 있다고 가정하는지 여부 오브젝트의 앞면 뒷면에 대한 라이팅 연산을 서로 다른 방식으로 수행할지 여부 specular 컬러를, ambient, diffuse 컬러와 분리하여 텍스처 연산 후에 적용할지 여부 2012-2학기 가상현실
라이팅 모델에 대한 속성은 glLightModel*()로 설정 void glLightModel{if}(GLenum pname, TYPE param); void glLIghtModel{if}(GLenum pname, TYPE *param); param은 pname에 해당하는 속성에 지정할 값을 가리킴 벡터 형태가 아닐 경우에는 하나의 값으로 된 라이팅 모델 속성만 지정할 수 있으며, GL_LIGHT_MODEL_AMBIENT에 대해서는 설정못함 2012-2학기 가상현실
glLightModel*()의 pname 매개변수 값 매개변수 이름 기본값 설명 GL_LIGHT_MODEL_ AMBIENT (0.2, 0.2, 0.2, 1.0) 전체 장면의 ambient RGBA 세기 GL_LIGHT_MODDEL_ LOCAL_VIEWER 0.0 또는 GL_FALSE Specular 반사 각도를 계산하는 방법 TWO_SIDE 단면 라이팅과 양면 라이팅 중에서 하나 선택 GL_LIGHT_MOD DEL_COLOR_CONTROL GL_SINGLE_COLOR Specular 컬러를 ambient 및 diffuse 컬러와 별도로 계산할지 여부 2012-2학기 가상현실
각각의 광원으로 부터 장면에 ambient 라이트를 형성할 수 있다. 전역적 ambient 라이트에 대한 RGBA 세기를 지정하려면 GL_LIGHT_MODEL_AMBIENT 매개변수를 사용 glfloat lmodel_ambient[] = { 0.2, 0.2, 0.2, 1.0 }; glLightModelfv(GL_LIGHT_MODEL_AMBIENT, lmodel_ambient); 2012-2학기 가상현실
시점의 위치는 specular 반사로부터 생성된 하이라이트르 계산하는데 영향을 미침. 특정한 정점에 대한 하이라이트의 세기 로컬 시점과 무한 시점 시점의 위치는 specular 반사로부터 생성된 하이라이트르 계산하는데 영향을 미침. 특정한 정점에 대한 하이라이트의 세기 그 정점에 대한 법선과 정점으로 부터 광원에 대한 방향, 정점으로 부터 시점에 대한 방향에 따라 달라짐 무한시점 사용하면 시점, 장면의 정점간의 방향이 일정하게 유지 디폴트는 무한 시점이며, 로컬 시점 변경은 다음과 같다: glLightModeli(GL_LIGHT_MODEL_LOCAL_VIEWER, GL_TRUE); 2012-2학기 가상현실
오브젝트 일부분을 잘라내어 내부표면을 보여주어야 하는 경우 양면 라이팅 라이팅 연산은 모든 폴리곤에 대해 수행 보통은 폴리곤의 앞면에 대해 라이팅 조건 설정 오브젝트 일부분을 잘라내어 내부표면을 보여주어야 하는 경우 내부 표면에 대해서도 지정한 라이팅 조건에 따라 라이팅 효과를 주어야 함. 양면 라이팅 기능을 활성화 시키려면 다음과 같이 호출 glLightModeli(GL_LIGHT_MODEL_TWO_SIDE, GL_TRUE); 뒷면 폴리곤에 대해서는 표면의 법선의 방향을 반대로 바꾼다. 양면 라이팅 기능 비활성화 GL_TRUE -> GL_FALSE 로 바꾼다. 2012-2학기 가상현실
다음과 같이 호출하면 specular 컬러를 계산하는 것과 적용하는 것을 서로 분리 일반적인 라이팅 연산은 ambient light, diffuse light, specular light, emissive light 등을 계산한 후에 더함 기본적으로, 라이팅 뒤에 텍스처 매핑을 적용하기 때문에 specular 하이라이트 들이 사라지거나 텍스처 효과가 제대로 나타나지 않게 됨 다음과 같이 호출하면 specular 컬러를 계산하는 것과 적용하는 것을 서로 분리 glLightModeli(GL_LIGHT_MODEL_COLOR_CONTROL, GL_SEPARATE_SPECULAR_COLOR); 두 개의 컬러가 생성 1차 컬러: specular light 를 제외한 나머지 빛을 나타냄 2차 컬러: 모든 specular light 를 합한 값 2012-2학기 가상현실
텍스처매핑을 처리하는 동안에는 1차 컬러만 텍스처 컬러와 합한다. 텍스처 연산이 끝난 뒤에 1차 컬러와 텍스처 컬러를 합한 결과에 2차 컬러를 추가한다. 이렇게 컬러를 분리하여 적용한 오브젝트는 좀더 선명하게 나타남 디폴트 설정으로 돌아갈 때에는 glLightModel(GL_LIGHT_MODEL_COLOR_CONTROL, GL_SINGLE_COLOR); 2012-2학기 가상현실
OpenGL에서는 라이팅을 명시적으로 활성해 주어야 함 glEnable(GL_LIGHTING); 활성화 라이팅 활성화 하기 OpenGL에서는 라이팅을 명시적으로 활성해 주어야 함 glEnable(GL_LIGHTING); 활성화 glDisable(GL_LIGHTING); 비활성화 광원에 대한 매개변수를 지정한 후에는 정의한 광원을 명시적으로 활성화시켜야 함 glEnable(GL_LIGHT0); 2012-2학기 가상현실
재질 속성 정의하기 재질 속성들은 광원을 생성시 사용한 속성들과 개념상 비슷 오브젝트에 대한 재질 속성(ambient, diffuse, specular 컬러와 shiness) 정의 방법 설정하는 방법 glMaterial*() 커맨드를 이용 void glMaterial{if}(Glenum face, Glenum pname, TYPE param); void glMaterial{if}v(Glenum face, Glenum pname, TYPE *param); 라이팅 연산에서 사용할 현재 재질 속성을 지정 face 인자 : GL_FRONT, GL_BACK, GL_FRONT_AND_BACK 등을 사용 pname: 재질 속성의 종류 param: 속성에 대한 값 2012-2학기 가상현실
pname 매개변수에 대한 기본값 매개변수 이름(pname) 기본값 설명 GL_AMBIENT (0.2, 0.2, 0.2, 1.0) 재질의 ambient 컬러 GL_DIFFUSE (0.8, 0.8, 0.8, 1.0) 재질의 diffuse 컬러 GLAMBIENT_AND_DIFFUSE 재질의 ambient & diffuse 컬러 GL_SPECULAR (0.0, 0.0, 0.0, 1.0) 재질의 specular 지수 GL_SHININESS 0.0 Specular 지수 GL_EMISSION 재질의 emissive 컬러 GL_COLOR_INDEX (0, 1, 1) ambient, diffuse, specular 컬러 인덱스 2012-2학기 가상현실
Diffuse 반사율은 물체의 컬러를 인지하는데 매우 중요한 역할 diffuse 반사와 ambient 반사 GL_DIFFUSE 나 GL_AMBIENT 매개변수는 오브젝트에 반사된 diffuse라이트 및 ambient 라이트의 컬러에 영향을 미침 Diffuse 반사율은 물체의 컬러를 인지하는데 매우 중요한 역할 Diffuse 라이트의 컬러와 법선 방향에 대한 빛의 입사 각도는 오브젝트 컬러 인식에 영향을 미침 Ambient 반사율은 오브젝트의 전역적인 컬러에 영향을 미침 실세계 오브젝트의 경우, diffuse 반사율과 ambient 반사율은 일반적으로 같은 컬러를 갖는다. OpenGL 에서 glMaterial*()를 통해 두 반사율을 동시에 설정하는 기능 제공 GLfloat mat_amb_diff[] = {0.1, 0.5, 0.8, 1.0}; glMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE, mat_amb_diff); 2012-2학기 가상현실
오브젝트에 대한 specular 반사는 하이라이트를 생성 Specular 반사량은 시점의 위치에 영향을 받는다. 반사각이 수직일 때 가장 밝게 나타남 반사된 빛에 대해 나타나는 재질의 효과를 GL_SPECULAR로 지정 가능 GL_SHININESS를 통해 하이라이트의 크기와 밝기도 조절 Emission GL_EMISSION에 대해 RGBA 컬러를 설정: 오브젝트에서 컬러의 빛이 뿜어져 나오는 것처럼 표현 주로 램프와 같은 광원을 표현할 때 사용 GLfloat mat_emission[] = {0.3, 0.2, 0.2, 0.0}; glMaterialfv(GL_FRONT, GL_EMISSION, mat_emission); 2012-2학기 가상현실
예제 5-8 다양한 재질 속성: material.c #include <stdlib.h> #include <GL/glut.h> void init(void) { GLfloat ambient[] = { 0.0, 0.0, 0.0, 1.0 }; GLfloat diffuse[] = { 1.0, 1.0, 1.0, 1.0 }; GLfloat specular[] = { 1.0, 1.0, 1.0, 1.0 }; GLfloat position[] = { 0.0, 3.0, 2.0, 0.0 }; GLfloat lmodel_ambient[] = { 0.4, 0.4, 0.4, 1.0 }; GLfloat local_view[] = { 0.0 }; 2012-2학기 가상현실
glEnable(GL_DEPTH_TEST); glShadeModel(GL_SMOOTH); glClearColor(0.0, 0.1, 0.1, 0.0); glEnable(GL_DEPTH_TEST); glShadeModel(GL_SMOOTH); glLightfv(GL_LIGHT0, GL_AMBIENT, ambient); glLightfv(GL_LIGHT0, GL_DIFFUSE, diffuse); glLightfv(GL_LIGHT0, GL_POSITION, position); glLightModelfv(GL_LIGHT_MODEL_AMBIENT, lmodel_ambient); glLightModelfv(GL_LIGHT_MODEL_LOCAL_VIEWER, local_view); glEnable(GL_LIGHTING); glEnable(GL_LIGHT0); } 2012-2학기 가상현실
GLfloat mat_ambient[] = { 0.7, 0.7, 0.7, 1.0 }; void display(void) { GLfloat no_mat[] = { 0.0, 0.0, 0.0, 1.0 }; GLfloat mat_ambient[] = { 0.7, 0.7, 0.7, 1.0 }; GLfloat mat_ambient_color[] = { 0.8, 0.8, 0.2, 1.0 }; GLfloat mat_diffuse[] = { 0.1, 0.5, 0.8, 1.0 }; GLfloat mat_specular[] = { 1.0, 1.0, 1.0, 1.0 }; GLfloat no_shininess[] = { 0.0 }; GLfloat low_shininess[] = { 5.0 }; GLfloat high_shininess[] = { 100.0 }; GLfloat mat_emission[] = {0.3, 0.2, 0.2, 0.0}; glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); 2012-2학기 가상현실
glMaterialfv(GL_FRONT, GL_AMBIENT, no_mat); glPushMatrix(); glTranslatef (-3.75, 3.0, 0.0); glMaterialfv(GL_FRONT, GL_AMBIENT, no_mat); glMaterialfv(GL_FRONT, GL_DIFFUSE, mat_diffuse); glMaterialfv(GL_FRONT, GL_SPECULAR, no_mat); glMaterialfv(GL_FRONT, GL_SHININESS, no_shininess); glMaterialfv(GL_FRONT, GL_EMISSION, no_mat); glutSolidSphere(1.0, 16, 16); glPopMatrix(); 2012-2학기 가상현실
glMaterialfv(GL_FRONT, GL_AMBIENT, no_mat); glPushMatrix(); glTranslatef (-1.25, 3.0, 0.0); glMaterialfv(GL_FRONT, GL_AMBIENT, no_mat); glMaterialfv(GL_FRONT, GL_DIFFUSE, mat_diffuse); glMaterialfv(GL_FRONT, GL_SPECULAR, mat_specular); glMaterialfv(GL_FRONT, GL_SHININESS, low_shininess); glMaterialfv(GL_FRONT, GL_EMISSION, no_mat); glutSolidSphere(1.0, 16, 16); glPopMatrix(); 2012-2학기 가상현실
glMaterialfv(GL_FRONT, GL_AMBIENT, no_mat); glPushMatrix(); glTranslatef (3.75, 3.0, 0.0); glMaterialfv(GL_FRONT, GL_AMBIENT, no_mat); glMaterialfv(GL_FRONT, GL_DIFFUSE, mat_diffuse); glMaterialfv(GL_FRONT, GL_SPECULAR, no_mat); glMaterialfv(GL_FRONT, GL_SHININESS, no_shininess); glMaterialfv(GL_FRONT, GL_EMISSION, mat_emission); glutSolidSphere(1.0, 16, 16); glPopMatrix(); 2012-2학기 가상현실
glMaterialfv(GL_FRONT, GL_AMBIENT, mat_ambient); glPushMatrix(); glTranslatef (-3.75, 0.0, 0.0); glMaterialfv(GL_FRONT, GL_AMBIENT, mat_ambient); glMaterialfv(GL_FRONT, GL_DIFFUSE, mat_diffuse); glMaterialfv(GL_FRONT, GL_SPECULAR, no_mat); glMaterialfv(GL_FRONT, GL_SHININESS, no_shininess); glMaterialfv(GL_FRONT, GL_EMISSION, no_mat); glutSolidSphere(1.0, 16, 16); glPopMatrix(); 2012-2학기 가상현실
glMaterialfv(GL_FRONT, GL_AMBIENT, mat_ambient); glPushMatrix(); glTranslatef (-1.25, 0.0, 0.0); 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, low_shininess); glMaterialfv(GL_FRONT, GL_EMISSION, no_mat); glutSolidSphere(1.0, 16, 16); glPopMatrix(); 2012-2학기 가상현실
glMaterialfv(GL_FRONT, GL_AMBIENT, mat_ambient); glPushMatrix(); glTranslatef (1.25, 0.0, 0.0); 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, high_shininess); glMaterialfv(GL_FRONT, GL_EMISSION, no_mat); glutSolidSphere(1.0, 16, 16); glPopMatrix(); 2012-2학기 가상현실
glMaterialfv(GL_FRONT, GL_AMBIENT, mat_ambient); glPushMatrix(); glTranslatef (3.75, 0.0, 0.0); glMaterialfv(GL_FRONT, GL_AMBIENT, mat_ambient); glMaterialfv(GL_FRONT, GL_DIFFUSE, mat_diffuse); glMaterialfv(GL_FRONT, GL_SPECULAR, no_mat); glMaterialfv(GL_FRONT, GL_SHININESS, no_shininess); glMaterialfv(GL_FRONT, GL_EMISSION, mat_emission); glutSolidSphere(1.0, 16, 16); glPopMatrix(); 2012-2학기 가상현실
glMaterialfv(GL_FRONT, GL_AMBIENT, mat_ambient_color); glPushMatrix(); glTranslatef (-3.75, -3.0, 0.0); glMaterialfv(GL_FRONT, GL_AMBIENT, mat_ambient_color); glMaterialfv(GL_FRONT, GL_DIFFUSE, mat_diffuse); glMaterialfv(GL_FRONT, GL_SPECULAR, no_mat); glMaterialfv(GL_FRONT, GL_SHININESS, no_shininess); glMaterialfv(GL_FRONT, GL_EMISSION, no_mat); glutSolidSphere(1.0, 16, 16); glPopMatrix(); 2012-2학기 가상현실
glMaterialfv(GL_FRONT, GL_AMBIENT, mat_ambient_color); glPushMatrix(); glTranslatef (-1.25, -3.0, 0.0); glMaterialfv(GL_FRONT, GL_AMBIENT, mat_ambient_color); glMaterialfv(GL_FRONT, GL_DIFFUSE, mat_diffuse); glMaterialfv(GL_FRONT, GL_SPECULAR, mat_specular); glMaterialfv(GL_FRONT, GL_SHININESS, low_shininess); glMaterialfv(GL_FRONT, GL_EMISSION, no_mat); glutSolidSphere(1.0, 16, 16); glPopMatrix(); 2012-2학기 가상현실
glMaterialfv(GL_FRONT, GL_AMBIENT, mat_ambient_color); glPushMatrix(); glTranslatef (1.25, -3.0, 0.0); glMaterialfv(GL_FRONT, GL_AMBIENT, mat_ambient_color); glMaterialfv(GL_FRONT, GL_DIFFUSE, mat_diffuse); glMaterialfv(GL_FRONT, GL_SPECULAR, mat_specular); glMaterialfv(GL_FRONT, GL_SHININESS, high_shininess); glMaterialfv(GL_FRONT, GL_EMISSION, no_mat); glutSolidSphere(1.0, 16, 16); glPopMatrix(); 2012-2학기 가상현실
glMaterialfv(GL_FRONT, GL_AMBIENT, mat_ambient_color); glPushMatrix(); glTranslatef (3.75, -3.0, 0.0); glMaterialfv(GL_FRONT, GL_AMBIENT, mat_ambient_color); glMaterialfv(GL_FRONT, GL_DIFFUSE, mat_diffuse); glMaterialfv(GL_FRONT, GL_SPECULAR, no_mat); glMaterialfv(GL_FRONT, GL_SHININESS, no_shininess); glMaterialfv(GL_FRONT, GL_EMISSION, mat_emission); glutSolidSphere(1.0, 16, 16); glPopMatrix(); glFlush(); } 2012-2학기 가상현실
void reshape(int w, int h) { glViewport(0, 0, w, h); glMatrixMode(GL_PROJECTION); glLoadIdentity(); if (w <= (h * 2)) glOrtho (-6.0, 6.0, -3.0*((GLfloat)h*2)/(GLfloat)w, 3.0*((GLfloat)h*2)/(GLfloat)w, -10.0, 10.0); else glOrtho (-6.0*(GLfloat)w/((GLfloat)h*2), 6.0*(GLfloat)w/((GLfloat)h*2), -3.0, 3.0, -10.0, 10.0); glMatrixMode(GL_MODELVIEW); } 2012-2학기 가상현실
void keyboard(unsigned char key, int x, int y) { switch (key) { case 27: exit(0); break; } 2012-2학기 가상현실
int main(int argc, char** argv) { glutInit(&argc, argv); glutInitDisplayMode (GLUT_SINGLE | GLUT_RGB | GLUT_DEPTH); glutInitWindowSize (600, 450); glutCreateWindow(argv[0]); init(); glutReshapeFunc(reshape); glutDisplayFunc(display); glutKeyboardFunc (keyboard); glutMainLoop(); return 0; } 2012-2학기 가상현실
glMaterialfv()를 여러 번 호출하여 각 구에 대한 재질 속성을 설정 2012-2학기 가상현실
Lightmaterial 튜토리얼 2012-2학기 가상현실
재질의 변화에 따른 성능 저하를 최소화 하기 위한 또 다른 방법으로, glColorMaterial() 이용 컬러 재질 모드 재질의 변화에 따른 성능 저하를 최소화 하기 위한 또 다른 방법으로, glColorMaterial() 이용 void glColorMaterial(GLenum face, GLenum mode); face 에 의해 지정된 면의 mode 에 해당하는 재질 속성이 현재 컬러 이용 face : GL_FRONT, GL_BACK, GL_FRONT_AND_BACK mode : GL_AMBIENT, GL_DIFFUSE, GL_SPECULAR, GL_AMBIENT_AND_DIFFUSE, GL_EMISSION 등이 있음 glColorMaterial()은 두 개의 독립적인 값을 지정함. 첫 번째 값 : 변경될 면을 지정 두 번째 값 : 변경될 재질 속성을 지정 2012-2학기 가상현실
glColorMaterial()을 호출한 뒤에는 GL_COLOR_MATERIAL을 인자로 하는 glEnable() 호출 그러면, 장면을 그릴 때마다 glColor*()를 사용하여 현재 컬러를 변경하거나, glMaterial*()로 재질을 변경할 수 있다. 정점들의 재질 속성을 하나씩 변경하려면 glColorMaterial()을 사용해야 한다 glEnable(GL_COLOR_MATERIAL); glColorMaterial(GL_FRONT, GL_DIFFUSE); glColor3f(0.2, 0.5, 0.8); // diffuse 반사 변경 .. // 오브젝트를 그림 glColorMaterial(GL_FRONT, GL_SPECULAR); glColor3f(0.9, 0.0, 0.2): // specular 반사 변경 .. // 다른 오브젝트를 그림 glDisable(GL_COLOR_MATERIAL); 2012-2학기 가상현실
정점들의 재질 속성을 하나씩 변경하려면 glColorMaterial() 사용 여러 개의 재질 속성을 변경하려면 glMaterial*() 사용 2012-2학기 가상현실
예제 5-9 glColorMaterial() 사용하기: colormat.c #include <GL/glut.h> #include <stdlib.h> GLfloat diffuseMaterial[4] = { 0.5, 0.5, 0.5, 1.0 }; void init(void) { GLfloat mat_specular[] = { 1.0, 1.0, 1.0, 1.0 }; GLfloat light_position[] = { 1.0, 1.0, 1.0, 0.0 }; glClearColor (0.0, 0.0, 0.0, 0.0); glShadeModel (GL_SMOOTH); glEnable(GL_DEPTH_TEST); 2012-2학기 가상현실
glMaterialfv(GL_FRONT, GL_DIFFUSE, diffuseMaterial); glMaterialfv(GL_FRONT, GL_SPECULAR, mat_specular); glMaterialf(GL_FRONT, GL_SHININESS, 25.0); glLightfv(GL_LIGHT0, GL_POSITION, light_position); glEnable(GL_LIGHTING); glEnable(GL_LIGHT0); glColorMaterial(GL_FRONT, GL_DIFFUSE); glEnable(GL_COLOR_MATERIAL); } 2012-2학기 가상현실
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); void display(void) { glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glutSolidSphere(1.0, 20, 16); glFlush (); } void reshape (int w, int h) glViewport (0, 0, (GLsizei) w, (GLsizei) h); glMatrixMode (GL_PROJECTION); glLoadIdentity(); 2012-2학기 가상현실
glOrtho (-1.5, 1.5, -1.5*(GLfloat)h/(GLfloat)w, 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(); } 2012-2학기 가상현실
void mouse(int button, int state, int x, int y) { switch (button) { case GLUT_LEFT_BUTTON: if (state == GLUT_DOWN) { diffuseMaterial[0] += 0.1; if (diffuseMaterial[0] > 1.0) diffuseMaterial[0] = 0.0; glColor4fv(diffuseMaterial); glutPostRedisplay(); } 2012-2학기 가상현실
case GLUT_MIDDLE_BUTTON: if (state == GLUT_DOWN) { diffuseMaterial[1] += 0.1; if (diffuseMaterial[1] > 1.0) diffuseMaterial[1] = 0.0; glColor4fv(diffuseMaterial); glutPostRedisplay(); } break; 2012-2학기 가상현실
case GLUT_RIGHT_BUTTON: if (state == GLUT_DOWN) { diffuseMaterial[2] += 0.1; if (diffuseMaterial[2] > 1.0) diffuseMaterial[2] = 0.0; glColor4fv(diffuseMaterial); glutPostRedisplay(); } break; default: 2012-2학기 가상현실
void keyboard(unsigned char key, int x, int y) { switch (key) { case 27: exit(0); break; } 2012-2학기 가상현실
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); glutMouseFunc(mouse); glutKeyboardFunc(keyboard); glutMainLoop(); return 0; } 2012-2학기 가상현실
실행결과 2012-2학기 가상현실
컬러 인덱스 모드의 라이팅 컬러 인덱스 모드에서 RGBA값과 같은 매개변수는 의미가 없음 별도의 공식을 사용해야 함 컬러 인덱스 모드에서 재질색을 지정하기 위해서는 다음과 같이 glMaterial*() 함수에 GL_COLOR_INDEXES 값을 지정 GLfloat mat_colormap[] = {16.0, 47.0, 79.0}; glMaterialfv (GL_FRONT, GL_COLOR_INDEXES, mat_colormap); 세 값은 각각 ambient, diffuse, specular 재질 컬러에 대한 컬러 인덱스 2012-2학기 가상현실