블렌딩 안티앨리어싱, 안개효과 그리고 폴리곤 오프셋

Slides:



Advertisements
Similar presentations
1. 도형의 연결 상태 2. 꼭지점과 변으로 이루어진 도형 Ⅷ. 도형의 관찰 도형의 연결상태 연결상태가 같은 도형 단일폐곡선의 성질 연결상태가 같은 입체도형 뫼비우스의 띠.
Advertisements

Term project. Touch-screen 활용 그림판 –Touch-screen 을 입력장치로 하여 LCD 상에 그림을 그리는 프로그램 – 터치 입력을 절대 좌표로 받는 디바이스 /dev/touch 를 만들어 응용 프 로그램에서 수행하도록 함. –User interface.
Chapter 3. 뷰잉(Viewing).
Chapter 4 컬러( COLOR ) 학기 가상현실.
재료수치해석 HW # 박재혁.
CG Programming (Modeling)
CG Programming (Modeling)
Implement of Input and Interaction
OpenGL 실습 12 로봇.
OpenGL Programming (III) 1. Drawing in 3D 2. Manipulating 3D Space
Ch7. 블렌딩 “현재 래스터라이즈 과정에 있는 픽셀과 같은 위치에 있는 이전의 픽셀을 서로 섞는(조합)하는 테크닉!”
2장. 프로그램의 기본 구성. 2장. 프로그램의 기본 구성 2-1"Hello, World!" 들여다 보기 /* Hello.c */ #include int main(void) { printf("Hello, World! \n"); return 0;
OpenGL 실습 1주차.
OpenGL 시작하기.
Lecture #7 제 4 장. 기하학적 객체와 변환 (2).
4장 기하학적 객체와 변환 – OpenGL 변환 학습목표 OpenGL 에서 어떻게 변환을 수행하는지 OpenGL 행렬모드 회전
Chapter 5. 라이팅(Lighting)
7장 디스플레이 리스트.
텍 스 처 매 핑.
Chap 9. 텍스쳐(Texture).
Practice - texture mapping
OpenGL 이란 그래픽스 하드웨어에 대한 소프트웨어 인터페이스 OpenGL의 전신은 실리콘그래픽스사의 IRIS GL
#include <stdio.h> int main(void) { float radius; // 원의 반지름
제 9 장 구조체와 공용체.
수치해석 6장 예제문제 환경공학과 천대길.
컴퓨터 프로그래밍 기초 [Final] 기말고사
선 택 과 피 드 백.
상태 관리 및 기하 오브젝트 그리기.
Sang Il Park Sejong University
OpenGL 프로젝트 < animate the fire >
테 셀 레 이 션 과 이차 곡 면.
11장. 포인터 01_ 포인터의 기본 02_ 포인터와 Const.
SqlParameter 클래스 선문 비트 18기 발표자 : 박성한.
컴퓨터 프로그래밍 기초 #02 : printf(), scanf()
제4장 컬 러(COLOR) 컬러 표현 Direct3D는 RGB 세 성분을 이용해 컬러 표현
임베디드 실습 # LED, 7’Segment 제어
4. OpenGL 상태들과 기본 도형들.
Mobile 3D Graphics (6장 퍼포먼스와 확장성) 교과목명 : 컴퓨터 그래픽스 특론 학 번 :
픽셀, 비트맵, 폰트, 이미지 그리기.
Hanyang University Jungsik Park
11장. 1차원 배열.
3차원 객체 모델링.
OpenGL PROJECT 우광식 성기영 서창수 이인주.
13. 연산자 오버로딩.
프 레 임 버 퍼.
Computer Graphics OpenGL 설치 및 설정
인터넷응용프로그래밍 JavaScript(Intro).
Chapter03 캔버스(1) HTML5 Programming.
박성진 컴퓨터 프로그래밍 기초 [09] 배열 part 1 박성진
핸드폰 시뮬레이션 김 형 도 송 미 경.
광원 제어 하기.
3장 상수 변수 기본 자료형 키워드와 식별자 상수와 변수 기본 자료형 형변환 자료형의 재정의.
Draw the basic Geometry Objects
쉽게 풀어쓴 C언어 Express 제14장 포인터 활용 C Express Slide 1 (of 22)
Chapter6 : JVM과 메모리 6.1 JVM의 구조와 메모리 모델 6.2 프로그램 실행과 메모리 6.3 객체생성과 메모리
연산자 (Operator).
Chapter 4 컬러( COLOR ).
컴퓨터 프로그래밍 기초 - 10th : 포인터 및 구조체 -
OpenGL 프로젝트 김병욱 김상진 김성환.
Window, Viewport Window, Viewport.
4장. 데이터 표현 방식의 이해. 4장. 데이터 표현 방식의 이해 4-1 컴퓨터의 데이터 표현 진법에 대한 이해 n 진수 표현 방식 : n개의 문자를 이용해서 데이터를 표현 그림 4-1.
7주차: Functions and Arrays
1. 정투상법 정투상법 정투상도 (1) 정투상의 원리
9 브라우저 객체 모델.
AdcRead API 함수 분석 마이크로프로세서.
어서와 C언어는 처음이지 제21장.
영역 기반 처리.
버스와 메모리 전송 버스 시스템 레지스터와 레지스터들 사이의 정보 전송을 위한 경로
6 객체.
BoardGame 보드게임 따라가기.
Presentation transcript:

블렌딩 안티앨리어싱, 안개효과 그리고 폴리곤 오프셋 블렌딩 안티앨리어싱, 안개효과 그리고 폴리곤 오프셋

내용 블렌딩 물체를 반투명하게 나타내는 기법 안티앨리어싱 가장자리를 부드럽게 처리 안개 효과 화면을 사실적으로 나타내는 기법 폴리곤 오프셋 교차되는 도형을 깔끔하게 나타냄 2009-2 학기 가상현실

블렌딩 블렌딩이 활성화 되어 있을 경우 알파값은 프레임 버퍼에 저장되어 있는 픽셀의 컬러와 프레그먼트의 픽셀의 컬러값을 결합하는데 사용 블렌딩 연산은 장면이 레스터화되고, 프레그먼트로 전환된 후 프레임버퍼의 마지막 픽셀이 그려지기 전에 수행 블렌딩을 하지 않으면 새로운 프레그먼트들은 프레임버퍼에 있는 기존의 컬러값을 덮어쓰게 됨 프레그먼트의 RGB 성분은 컬러를 나타내고, 알파 성분은 투명도를 나타낸다고 생각 2009-2 학기 가상현실

블렌딩을 하는 동안 프레그먼트의 컬러값과 현재 저장된 픽셀의 컬러값은 2단계의 과정을 거쳐 결합 입력값 요소와 기존값 요소 블렌딩을 하는 동안 프레그먼트의 컬러값과 현재 저장된 픽셀의 컬러값은 2단계의 과정을 거쳐 결합 입력값(source) 요소와 기존값(destination) 요소의 계산 방식을 설정하고 입력값과 기존값을 서로 대응되는 요소들끼리 곱해줌 입력값과 기존값에 있는 RGBA값들을 더한다. (RsSr+RdDr, GsSg+GdDg, BsSb+BdDb, AsSa+AdDa) 2009-2 학기 가상현실

입력값 블렌딩 요소와 기존값 블렌딩 요소가 만들어지는 방법 두 개의 상수를 만들기 위해 glBlendFunc() 사용 두 가지 상수 중 하나는 입력값 요소가 계산되는 방법 결정 다른 하나는 기존값 요소가 계산되는 방법 결정 glEnable(GL_BLEND)로 활성화 기본값: GL_ONE(입력값), GL_ZERO(기존값) => 블렌딩 비활성화 void glBlendFunc(GLenum sfactor, GLenum dfacor); 프레그먼트에 있는 컬러값(입력값)과 프레임 버퍼에 있는 컬러값(기존값)이 결합되는 방식을 설정 sfactor : 입력값의 블렌딩 요소를 계산하는 방법 dfactor : 기존 값의 블렌딩 요소가 계산되는 방법 각 요소들은 [0,1] 사이의 값을 가짐 결합된 입력값과 기존값의 컬러값도 [0, 1] 구간으로 클램프됨 2009-2 학기 가상현실

블 렌 딩 입력값 블렌딩 요소와 기존값 블렌딩 요소들 상수 관련 요소 계산된 블렌딩 요소 GL_ZERO 입력값, 기존값 블 렌 딩 입력값 블렌딩 요소와 기존값 블렌딩 요소들 상수 관련 요소 계산된 블렌딩 요소 GL_ZERO 입력값, 기존값 (0, 0, 0, 0) GL_ONE (1, 1, 1, 1) GL_DST_COLOR 입력값 (Rd, Gd, Bd, Ad) GL_SRC_COLOR 기존값 (Rs, Gs, Bs, As) GL_ONE_MINUS_DST_COLOR (1,1,1,1)-(Rd,Gd,Bd,Ad) GL_ONE_MINUS_SRC_COLOR (1,1,1,1)-(Rs,Gs,Bs,As) GL_SRC_ALPHA 입력값. 기존값 (As, As, As, As) 2009-2 학기 가상현실

블 렌 딩 GL_ONE_MINUS_SRC_ALPHA 입력값, 기존값 (1,1,1,1)- (As, As, As, As) 블 렌 딩 GL_ONE_MINUS_SRC_ALPHA 입력값, 기존값 (1,1,1,1)- (As, As, As, As) GL_DST_ALPHA (Ad, Ad, Ad, Ad) GL_ONE_MINUS_DST_ALPHA (1,1,1,1)- (Ad, Ad, Ad, Ad) GL_SRC_ALPHA_SATURATE 입력값 (f, f, f, 1); f=min(As,1-Ad) GL_CONSTANT_COLOR (Rc, Gc, Bc, Ac) GL_ONE_MINUS_CONSTANT_COLOR (1,1,1,1)-(Rc,Gc,Bc,Ac) GL_CONSTANT_ALPHA (Ac, Ac,Ac,Ac) GL_ONE_MINUS_CONSTANT_ALPHA (1,1,1,1)-(Ac,Ac,Ac,Ac) 2009-2 학기 가상현실

블 렌 딩 블렌딩을 사용한 샘플들 입력값 요소와 기존값 요소의 모든 조합을 사용할 수 있는 건 아님 블 렌 딩 블렌딩을 사용한 샘플들 입력값 요소와 기존값 요소의 모든 조합을 사용할 수 있는 건 아님 대부분 응용 프로그램에서는 몇 가지 조합만 사용 하나의 이미지와 또 다른 이미지를 절반씩 그릴 때(두 이미지를 동등한 비율로 혼합하여 그릴 때) 입력값 요소를 GL_ONE으로, 기존값 요소를 GL_ZERO로 놓고 첫번째 그림을 그린 후, 입력값 요소를 GL_SRC_ALPHA로 설정, 기존값 요소를 GL_ONE_MINUS_SRC_ALPHA로 설정, 알파값을 0.5로 놓고 두 번째 그림을 그림 첫 번째 그림을 0.75, 두 번째 그림을 0.25 정도의 비율로 섞고 싶을 경우에는, 첫 번째 그림은 위와 동일하게, 두 번째 그림은 알파값을 0.25로 설정하여 그림 2009-2 학기 가상현실

현재 이미지에 관계 없이 브러쉬로 칠할 때 마다 색이 덧입혀지도록 만들고 싶은 경우 3개의 서로 다른 그림을 균일하게 섞고 싶은 경우 기존값 요소를 GL_ONE으로 설정, 입력값 요소를 GL_SRC_ALPHA로 설정 후 그림의 알파값을 0.3333333으로 똑같이 놓고 그림 현재 이미지에 관계 없이 브러쉬로 칠할 때 마다 색이 덧입혀지도록 만들고 싶은 경우 10%의 알파값과 GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA 이용, 브러쉬 이미지를 표현 블렌딩 함수의 입력값 요소로 GL_DST_COLOR 또는 GL_ONE_MINUS_DST_COLOR를 사용, 기존값 요소로 GL_SRC_COLOR 또는 GL_ONE_MINUS_SRC_COLOR를 사용 하면 각 컬러 요소들을 개별적으로 조절 가능 2009-2 학기 가상현실

가장 멀리 있는 면은 배경 컬러의 80%, 그 다음이 40%, 가장 가까운 면이 90% 컬러를 전달하려면 3개의 반투명한 면으로 구성된 그림을 그릴 때 몇몇 오브젝트들이 다른 오브젝트들을 가리고 있고, 모든 오브젝트들이 솔리드 배경 위에 놓여 있는 경우 가장 멀리 있는 면은 배경 컬러의 80%, 그 다음이 40%, 가장 가까운 면이 90% 컬러를 전달하려면 입력값 요소와 기존값 요소를 기본값으로 설정 블렌딩 요소의 입력값은 GL_SRC_ALPHA, 기존값은 GL_ONE_MINUS_SRC_ALPHA로 바꿈 알파값은 차례로 0.2, 0.6, 0.1로 설정 투명하게 처리해서 보이지 않게 만들려는 프레그먼트에 대해서는 알파값을 0으로주고, 불투명한 프레그먼트에 대해서는 알파값을 1.0으로 준다. 이런 식으로 이미지에 있는 개별적인 프레그먼트에 서로 다른 알파값을 할당하면 직사각형이 아닌 래스터 이미지 효과를 낼 수 있다. 2009-2 학기 가상현실

예제 6-1 블렌딩 예제 : alpha.c 서로 겹쳐진 두 개의 컬러 삼각형 include <GL/glut.h> #include <stdlib.h> static int leftFirst = GL_TRUE; /* 알파 블렌딩 함수 초기화 */ static void init(void) { glEnable (GL_BLEND); glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); glShadeModel (GL_FLAT); glClearColor (0.0, 0.0, 0.0, 0.0); } 2009-2 학기 가상현실

static void drawLeftTriangle(void){ // draw a yellow triangle glBegin (GL_TRIANGLES); glColor4f(1.0, 1.0, 0.0, 0.75); glVertex3f(0.1, 0.9, 0.0); glVertex3f(0.1, 0.1, 0.0); glVertex3f(0.7, 0.5, 0.0); glEnd(); } static void drawRightTriangle(void){ // draw a cyan triangle glColor4f(0.0, 1.0, 1.0, 0.75); glVertex3f(0.9, 0.9, 0.0); glVertex3f(0.3, 0.5, 0.0); glVertex3f(0.9, 0.1, 0.0); 2009-2 학기 가상현실

glClear(GL_COLOR_BUFFER_BIT); if (leftFirst) { drawLeftTriangle(); void display(void) { glClear(GL_COLOR_BUFFER_BIT); if (leftFirst) { drawLeftTriangle(); drawRightTriangle(); } else { glFlush(); 2009-2 학기 가상현실

void reshape(int w, int h) { glViewport(0, 0, (GLsizei) w, (GLsizei) h); glMatrixMode(GL_PROJECTION); glLoadIdentity(); if (w <= h) gluOrtho2D (0.0, 1.0, 0.0, 1.0*(GLfloat)h/(GLfloat)w); else gluOrtho2D (0.0, 1.0*(GLfloat)w/(GLfloat)h, 0.0, 1.0); } 2009-2 학기 가상현실

void keyboard(unsigned char key, int x, int y){ switch (key) { case 't': case 'T': leftFirst = !leftFirst; glutPostRedisplay(); break; case 27: /* Escape key */ exit(0); default: } 2009-2 학기 가상현실

int main(int argc, char** argv) { glutInit(&argc, argv); glutInitDisplayMode (GLUT_SINGLE | GLUT_RGB); glutInitWindowSize (200, 200); glutCreateWindow (argv[0]); init(); glutReshapeFunc (reshape); glutKeyboardFunc (keyboard); glutDisplayFunc (display); glutMainLoop(); return 0; } 2009-2 학기 가상현실

2009-2 학기 가상현실

폴리곤이 그려지는 순서는 블렌딩의 결과에 많은 영향을 미침 깊이 버퍼를 이용한 3차원 블렌딩 폴리곤이 그려지는 순서는 블렌딩의 결과에 많은 영향을 미침 3차원의 반투명한 물체를 그릴 때는 앞에서부터 뒤로 그릴 것인지, 뒤에서부터 앞으로 그릴 것인지에 따라 다른 결과를 얻을 수 있음. 깊이버퍼에는 스크린의 윈도우상의 물체 중에서 주어진 픽셀이 차지하고 있는 부분과 시점 사이의 거리가 기록 한 화면에 불투명 오브젝트와 반투명 오브젝트 모두를 그릴 때는 불투명한 오브젝트의 뒤에 가려진 부분이 그려지지 않도록 깊이버퍼를 사용 2009-2 학기 가상현실

반투명한 오브젝트가 가까이 있는 경우에는 불투명한 오브젝트의 컬러와 블렌딩한다. 반투명한 오브젝트를 그리는 동안 깊이 버퍼를 활성화시키되 읽기 전용 상태로 둔다. glDepthMask() 함수 이용 인자로 GL_FALSE를 주면 버퍼는 읽기 전용, GL_TRUE면 쓰기 가능 그리는 방법 먼저 깊이 버퍼를 사용하여 불투명한 오브젝트를 그린 후 깊이 버퍼를 읽기 전용 상태로 만들고, 반투명한 물체를 그리면서 불투명한 오브젝트의 깊이버퍼값과 비교함. 2009-2 학기 가상현실

예제 6-2 3차원 블렌딩: alpha3D.c #include <GL/glut.h> #include <stdlib.h> #include <stdio.h> #define MAXZ 8.0 #define MINZ -8.0 #define ZINC 0.4 static float solidZ = MAXZ; static float transparentZ = MINZ; static GLuint sphereList, cubeList; static void init(void) { GLfloat mat_specular[] = { 1.0, 1.0, 1.0, 0.15 }; GLfloat mat_shininess[] = { 100.0 }; GLfloat position[] = { 0.5, 0.5, 1.0, 0.0 }; 2009-2 학기 가상현실

glMaterialfv(GL_FRONT, GL_SPECULAR, mat_specular); glMaterialfv(GL_FRONT, GL_SHININESS, mat_shininess); glLightfv(GL_LIGHT0, GL_POSITION, position); glEnable(GL_LIGHTING); glEnable(GL_LIGHT0); glEnable(GL_DEPTH_TEST); sphereList = glGenLists(1); glNewList(sphereList, GL_COMPILE); glutSolidSphere (0.4, 16, 16); glEndList(); cubeList = glGenLists(1); glNewList(cubeList, GL_COMPILE); glutSolidCube (0.6); } 2009-2 학기 가상현실

GLfloat mat_solid[] = { 0.75, 0.75, 0.0, 1.0 }; void display(void) { GLfloat mat_solid[] = { 0.75, 0.75, 0.0, 1.0 }; GLfloat mat_zero[] = { 0.0, 0.0, 0.0, 1.0 }; GLfloat mat_transparent[] = { 0.0, 0.8, 0.8, 0.6 }; GLfloat mat_emission[] = { 0.0, 0.3, 0.3, 0.6 }; glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glPushMatrix (); glTranslatef (-0.15, -0.15, solidZ); glMaterialfv(GL_FRONT, GL_EMISSION, mat_zero); glMaterialfv(GL_FRONT, GL_DIFFUSE, mat_solid); glCallList (sphereList); glPopMatrix (); 2009-2 학기 가상현실

glTranslatef (0.15, 0.15, transparentZ); glPushMatrix (); glTranslatef (0.15, 0.15, transparentZ); glRotatef (15.0, 1.0, 1.0, 0.0); glRotatef (30.0, 0.0, 1.0, 0.0); glMaterialfv(GL_FRONT, GL_EMISSION, mat_emission); glMaterialfv(GL_FRONT, GL_DIFFUSE, mat_transparent); glEnable (GL_BLEND); glDepthMask (GL_FALSE); // Depth 버퍼가 읽기전용 상태로 됨 glBlendFunc (GL_SRC_ALPHA, GL_ONE); glCallList (cubeList); glDepthMask (GL_TRUE); // Depth 버퍼가 쓰기전용 상태로 됨 glDisable (GL_BLEND); glPopMatrix (); glutSwapBuffers(); } 2009-2 학기 가상현실

void reshape(int w, int h) { glViewport(0, 0, (GLint) w, (GLint) 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); } 2009-2 학기 가상현실

if (solidZ <= MINZ || transparentZ >= MAXZ) glutIdleFunc(NULL); void animate(void) { if (solidZ <= MINZ || transparentZ >= MAXZ) glutIdleFunc(NULL); else { solidZ -= ZINC; transparentZ += ZINC; glutPostRedisplay(); } 2009-2 학기 가상현실

void keyboard(unsigned char key, int x, int y){ switch (key) { case 'a': case 'A': solidZ = MAXZ; transparentZ = MINZ; glutIdleFunc(animate); break; case 'r': case 'R': glutPostRedisplay(); case 27: exit(0); } } 2009-2 학기 가상현실

int main(int argc, char** argv) { glutInit(&argc, argv); glutInitDisplayMode (GLUT_SINGLE | GLUT_RGB |GLUT_DEPTH); glutInitWindowSize(500, 500); glutCreateWindow(argv[0]); init(); glutReshapeFunc(reshape); glutKeyboardFunc(keyboard); glutDisplayFunc(display); glutMainLoop(); return 0; } 2009-2 학기 가상현실

실행결과 2009-2 학기 가상현실

안티앨리어싱 수평이나 수직에 가까운 선들이 울퉁불퉁하게 보이는 것을 앨리어싱이라 함 안티앨리어싱: 앨리어싱을 줄이는 방법 그림의 조각이 덮고 있는 픽셀 조각에 기초하여 각 프레그먼트에 대한 적용범위(Coverage)를 계산한다. RGBA 모드에서는 프레그먼트의 알파값과 적용범위값을 곱한다. 컬러인덱스모드에서는 프레그먼트 적용범위에 기초해서 컬러 인덱스의 하위 4비트를 설정한다. 0000: 적용범위 없음 1111: 적용범위가 전체 2009-2 학기 가상현실

void glHint(GLenum target, GLenum hint) 이 함수는 OpenGL의 특정한 동작을 제어 적용범위의 계산은 복잡하고 OpenGL 구현마다 달라질 수 있으므로 glHint()를 사용하여 제어 target : 제어할 동작을 나타냄 hint : 효율적으로 동작하도록 설정할 때 GL_FASTEST 지정 최고의 품질로 이미지 생성 때 GL_NICEST를 지정 별도로 지정하고 싶지 않을 때 GL_DONT_CARE 선택 2009-2 학기 가상현실

glHint()에서 사용하는 값들: target 인자값 매개변수 설명 GL_POINT_SMOOTH_HINT, GL_LINE_SMOOTH_HINT, GL_POLYGON_SMOOTH_HINT 안티앨리어싱 작업에서 점이나 선, 또는 다각형의 샘플링 품질을 설정 GL__FOG_HINT 안개 효과 계산이 픽셀마다 이루어지는지(GL_NICEST),정점마다 이루어지는지(GL_FASTEST) 여부를 설정 GL_PERSPECTIVE_CORRECTION_HINT 컬러와 텍스처 좌표 보간의 품질을 설정 2009-2 학기 가상현실

점이나 선을 안티앨리어싱 하려면 먼저 glEnable() 함수로 안티앨리어싱 모드를 활성화 점과 선에 대한 안티앨리어싱 점이나 선을 안티앨리어싱 하려면 먼저 glEnable() 함수로 안티앨리어싱 모드를 활성화 GL_POINT_SMOOTH 나 GL_LINE_SMOOTH 의 값을 선택함 glHInt()를 이용하여, 품질에 대한 힌트를 줄 수 있음 점의 크기나 선의 너비, 선의 모양 등 결정 RGBA 모드에서의 안티앨리어싱 RGBA모드에서는 블렌딩을 활성화 시켜야 함 입력값에 GL_SRC_ALPHA를 기존값에 GL_ONE_MUNUS_SRC_ALPHA를 사용. 선분이 조금 밝아지는 효과를 주기 위해서 기존값을 GL_ONE으로 설정 가능 2009-2 학기 가상현실

예제 6-3 안티앨리어싱 선분: aargb.c 안티앨리어싱 된 선분 [ 6 – 3 ] #include <GL/glut.h> #include <stdlib.h> #include <stdio.h> static float rotAngle = 0.; /* 알파 블렌딩, 힌트, 선분의 너비를 포함, RGBA 모드를 위한 * 안티앨리어싱 초기화, 선분의 너비입상(line width granularity)과 * 너비에 관해서 OpenGL의 구현에 따라 달라지는 내용 출력 */ void init(void) { GLfloat values[2]; glGetFloatv (GL_LINE_WIDTH_GRANULARITY, values); printf ("GL_LINE_WIDTH_GRANULARITY value is %3.1f\n", values[0]); 2009-2 학기 가상현실

glGetFloatv (GL_LINE_WIDTH_RANGE, values); printf ("GL_LINE_WIDTH_RANGE values are %3.1f %3.1f\n", values[0], values[1]); glEnable (GL_LINE_SMOOTH); glEnable (GL_BLEND); glBlendFunc (GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); glHint (GL_LINE_SMOOTH_HINT, GL_DONT_CARE); glLineWidth (1.5); glClearColor(0.0, 0.0, 0.0, 0.0); } 2009-2 학기 가상현실

glClear(GL_COLOR_BUFFER_BIT); glColor3f (0.0, 1.0, 0.0); void display(void) { glClear(GL_COLOR_BUFFER_BIT); glColor3f (0.0, 1.0, 0.0); glPushMatrix(); glRotatef(-rotAngle, 0.0, 0.0, 0.1); glBegin (GL_LINES); glVertex2f (-0.5, 0.5); glVertex2f (0.5, -0.5); glEnd (); glPopMatrix(); 2009-2 학기 가상현실

glRotatef(rotAngle, 0.0, 0.0, 0.1); glBegin (GL_LINES); glColor3f (0.0, 0.0, 1.0); glPushMatrix(); glRotatef(rotAngle, 0.0, 0.0, 0.1); glBegin (GL_LINES); glVertex2f (0.5, 0.5); glVertex2f (-0.5, -0.5); glEnd (); glPopMatrix(); glFlush(); } 2009-2 학기 가상현실

void reshape(int w, int h) { glViewport(0, 0, w, h); glMatrixMode(GL_PROJECTION); glLoadIdentity(); if (w <= h) gluOrtho2D (-1.0, 1.0, -1.0*(GLfloat)h/(GLfloat)w, 1.0*(GLfloat)h/(GLfloat)w); else gluOrtho2D (-1.0*(GLfloat)w/(GLfloat)h, 1.0*(GLfloat)w/(GLfloat)h, -1.0, 1.0); glMatrixMode(GL_MODELVIEW); } 2009-2 학기 가상현실

void keyboard(unsigned char key, int x, int y) { switch (key) { case 'r': case 'R': rotAngle += 20.; if (rotAngle >= 360.) rotAngle = 0.; glutPostRedisplay(); break; case 27: /* Escape Key */ exit(0); default: } 2009-2 학기 가상현실

int main(int argc, char** argv) { glutInit(&argc, argv); glutInitDisplayMode (GLUT_SINGLE | GLUT_RGB); glutInitWindowSize (200, 200); glutCreateWindow (argv[0]); init(); glutReshapeFunc (reshape); glutKeyboardFunc (keyboard); glutDisplayFunc (display); glutMainLoop(); return 0; } 2009-2 학기 가상현실

2009-2 학기 가상현실

컬러 인덱스 모드에서 안티 앨리어싱을 적용할 때 가장 까다로운 부분은 컬러 맵을 읽어오고 사용하는 부분 컬러 인덱스 모드에서의 안티앨리어싱 컬러 인덱스 모드에서 안티 앨리어싱을 적용할 때 가장 까다로운 부분은 컬러 맵을 읽어오고 사용하는 부분 컬러 인덱스의 마지막 4비트가 적용 범위값을 나타내기 때문에 배경 컬러에서 오브젝트 컬러까지 16개의 인덱스를 컬러 램프에 읽어 와야 함 램프에 있는 처음 16컬러로 컬러 버퍼를 초기화 한 다음, 이 램프에 있는 컬러를 사용하여 점과 선을 그림 2009-2 학기 가상현실

내부가 채워진 폴리곤을 안티앨리어싱 하는 원리는 점이나 선을 안티앨리어싱 하는 것과 비슷 안티앨리어싱을 적용한 폴리곤 내부가 채워진 폴리곤을 안티앨리어싱 하는 원리는 점이나 선을 안티앨리어싱 하는 것과 비슷 폴리곤들 모서리가 서로 중첩될 때는 컬러 값을 적절하게 블렌딩 RGBA 모드에서 안티앨리어싱을 하기 위해서는 폴리곤 가장자리의 적용 범위값을 알파값으로 사용. 폴리곤에 대해 안티앨리어싱을 적용하려면 glEnable()의 인자로 GL_POLYGON_SMOOTH를 넘겨줌 2009-2 학기 가상현실

안 개 효 과 이미지가 너무 날카롭거나 부자연스럽게 보이는 경우를 보완 안티앨리어싱으로 오브젝트의 모서리를 부드럽게 다듬어 오브젝트가 좀더 사실적으로 보이도록 만들기 가능 안개 효과 함께 이용, 전반적인 이미지를 더욱 자연스럽게 표현 안개효과가 활성화 되면 시점으로부터 멀리 떨어져 있는 물체는 안개효과 컬러로 서서히 흐려짐 안개 효과는 행렬변환, 라이팅, 텍스처매핑이 끝난 뒤에 적용됨 점과 선을 포함한 모든 종류의 기하 프리미티브에 적용될 수 있다. 점과 선에 안개효과를 적용한 것을 Depth-cuing 이라고 부름 2009-2 학기 가상현실

glEnable() 인자로 GL_FOG 넘겨줌 glFog()를 이용, 안개의 컬러와 밀도를 결정할 방정식을 선택 예) 안개 효과 사용하기 glEnable() 인자로 GL_FOG 넘겨줌 glFog()를 이용, 안개의 컬러와 밀도를 결정할 방정식을 선택 예) glFogi(GL_FOG_MODE, GL_LINEAR); 필요에 따라 glHint()로 GL_FOG_HINT의 값을 설정할 수도 있다. 2009-2 학기 가상현실

예제 6-5 RGBA 에서 안개 효과를 적용하여 그린 다섯 개의 구: fog.c #include <GL/glut.h> #include <math.h> #include <stdlib.h> #include <stdio.h> static GLint fogMode; static void init(void) { GLfloat position[] = { 0.5, 0.5, 3.0, 0.0 }; glEnable(GL_DEPTH_TEST); glLightfv(GL_LIGHT0, GL_POSITION, position); glEnable(GL_LIGHTING); 2009-2 학기 가상현실

glMaterialfv (GL_FRONT, GL_AMBIENT, mat); glEnable(GL_LIGHT0); { GLfloat mat[3] = {0.1745, 0.01175, 0.01175}; glMaterialfv (GL_FRONT, GL_AMBIENT, mat); mat[0] = 0.61424; mat[1] = 0.04136; mat[2] = 0.04136; glMaterialfv (GL_FRONT, GL_DIFFUSE, mat); mat[0] = 0.727811; mat[1] = 0.626959; mat[2] = 0.626959; glMaterialfv (GL_FRONT, GL_SPECULAR, mat); glMaterialf (GL_FRONT, GL_SHININESS, 0.6*128.0); } 2009-2 학기 가상현실

GLfloat fogColor[4] = {0.5, 0.5, 0.5, 1.0}; fogMode = GL_EXP; glEnable(GL_FOG); { GLfloat fogColor[4] = {0.5, 0.5, 0.5, 1.0}; fogMode = GL_EXP; glFogi (GL_FOG_MODE, fogMode); glFogfv (GL_FOG_COLOR, fogColor); glFogf (GL_FOG_DENSITY, 0.35); glHint (GL_FOG_HINT, GL_DONT_CARE); glFogf (GL_FOG_START, 1.0); glFogf (GL_FOG_END, 5.0); } glClearColor(0.5, 0.5, 0.5, 1.0); /* fog color */ 2009-2 학기 가상현실

static void renderSphere (GLfloat x, GLfloat y, GLfloat z){ glPushMatrix(); glTranslatef (x, y, z); glutSolidSphere(0.4, 16, 16); glPopMatrix(); } void display(void){ glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); renderSphere (-2., -0.5, -1.0); renderSphere (-1., -0.5, -2.0); renderSphere (0., -0.5, -3.0); renderSphere (1., -0.5, -4.0); renderSphere (2., -0.5, -5.0); glFlush(); 2009-2 학기 가상현실

void reshape(int w, int h) { glViewport(0, 0, (GLsizei) w, (GLsizei) h); glMatrixMode(GL_PROJECTION); glLoadIdentity(); if (w <= h) glOrtho (-2.5, 2.5, -2.5*(GLfloat)h/(GLfloat)w, 2.5*(GLfloat)h/(GLfloat)w, -10.0, 10.0); else glOrtho (-2.5*(GLfloat)w/(GLfloat)h, 2.5*(GLfloat)w/(GLfloat)h, -2.5, 2.5, -10.0, 10.0); glMatrixMode(GL_MODELVIEW); glLoadIdentity (); } 2009-2 학기 가상현실

void keyboard(unsigned char key, int x, int y) { switch (key) { case 'f': case 'F': if (fogMode == GL_EXP) { fogMode = GL_EXP2; printf ("Fog mode is GL_EXP2\n"); } else if (fogMode == GL_EXP2) { fogMode = GL_LINEAR; printf ("Fog mode is GL_LINEAR\n"); 2009-2 학기 가상현실

else if (fogMode == GL_LINEAR) { fogMode = GL_EXP; printf ("Fog mode is GL_EXP\n"); } glFogi (GL_FOG_MODE, fogMode); glutPostRedisplay(); break; case 27: exit(0); default: 2009-2 학기 가상현실

int main(int argc, char** argv) { glutInit(&argc, argv); glutInitDisplayMode (GLUT_SINGLE | GLUT_RGB|GLUT_DEPTH); glutInitWindowSize(500, 500); glutCreateWindow(argv[0]); init(); glutReshapeFunc (reshape); glutKeyboardFunc (keyboard); glutDisplayFunc (display); glutMainLoop(); return 0; } 2009-2 학기 가상현실

실행결과 2009-2 학기 가상현실

void glFog{if}(Glenum pname, TYPE param); 안개 효과 방정식 void glFog{if}(Glenum pname, TYPE param); void glFog{if}v(Glenum pname, TYPE *params); 이 함수들은 안개 효과를 계산하기 위한 매개변수 방정식 설정 pname 을 GL_FOG_MODE로 설정할 경우 param은 GL_EXP, GL_EXP2, GL_LINEAR 중에서 설정 2009-2 학기 가상현실

RGBA 모드에서는 안개 효과 요소 f를 다음과 같이 최종적인 안개 효과의 컬러를 결정하는 데 사용 C = fCi + (1 – f)Cf f: 안개효과 요소 Ci : 입력된 프레그먼트의 RGBA 값을 나타냄 Cf : GL_FOG_COLOR로 설정된 안개 효과 컬러값을 나타냄 2009-2 학기 가상현실

컬러 인덱스 모드에서의 최종적인 안개 효과는 컬러는 다음과 같은 공식으로 계산 컬러 인덱스 모드에서의 안개 효과 컬러 인덱스 모드에서의 최종적인 안개 효과는 컬러는 다음과 같은 공식으로 계산 I = Ii + (1 – f) If Ii : 는 입력된 프레그먼트의 컬러 인덱스를 나타냄 If : GL_FOG_INDEX 설정된 안개 효과의 컬러 인덱스를 나타냄 컬러 인덱스 모드에서 안개 효과를 사용하려면 컬러 램프에 적절한 값을 넣어야 한다. 2009-2 학기 가상현실

폴리곤 오프셋 솔리드 오브젝트의 모서리를 하이라이트 처리하려면 오브젝트를 GL_FILL 모드로 그린 후 다른 컬러로 GL_LINE 모드에서 다시 한 번 그려주어야 함 선분과 폴리곤은 정확히 동일한 방식으로 래스터화 되지 않음. 그래서 선분의 깊이값과 폴리곤 모서리 깊이값이 서로 다름 이 때문에 선분이 도형의 위에서 사라졌다 나타났다 하는 현상이 발생(스티칭 현상) 이러한 어색한 효과를 없애주기 위해서 폴리곤 오프셋 이용 모서리를 하이라이트 선분과 깨끗하게 분리 2009-2 학기 가상현실

오프셋은 폴리곤을 래스터하는 3가지 방법에 따라 활성화 GL_FILL, GL_LINE, GL_POINT glEnableI()의 인자로 GL_POLYGON_OFFSET_FILL, GL_POLYGON_OFFSET, GL_POLYGON_OFFSET_POINT 으로 모드를 활성화 void glPolygonOffset(GLfloat factor, GLfoat units); 폴리곤 오프셋이 활성화되어 있을 때 각각 프레그먼트의 깊이값을 계산된 오프셋값에 더한다. 2009-2 학기 가상현실

m: 다각형의 최대 깊이 경사값(maximum depth slope) r: OpenGL 구현에 따라 다름 깊이경사값 계산된 오프셋값 o = m*factor + r*units m: 다각형의 최대 깊이 경사값(maximum depth slope) r: OpenGL 구현에 따라 다름 깊이경사값 폴리곤을 가로지르는 선분의 z값의 변화량을 x와 y값의 변화량으로 나눈 값을 말한다. 깊이값은 윈도우 좌표계의 값으로 계산되고 [0, 1] 구간으로 클램프된다. near 클리핑 평면과 far 클리핑 평면에 평행한 폴리곤은 깊이 경사가 0이된다. 깊이 경사가 0에 가까운 폴리곤들은 작은 상수 오프셋으로 충분하며, glPolygonOffset()의 인자로 factor=0.0, unit=1.0으로 전달 클리핑 평면에 대해 큰 각도를 갖는 도형(깊이 경사값이 0보다 큰 도형)은 큰 오프셋이 필요 0이 아닌 작은 값, 즉 0.75나 1.0 같은 값들을 이용 2009-2 학기 가상현실

glEnable(GL_LIGHTING); glEnable(GL_LIGHT0); 예제: glEnable(GL_LIGHTING); glEnable(GL_LIGHT0); glEnable(GL_POLYGON_OFFSET_FILL); glPolygonOffset(1.0, 1.0); glCallList(list); glDisable(GL_POLYGON_OFFSET_FILL); glDisable(GL_LIGHTING); glDisable(GL_LIGHT0); glColor3f(1.0, 1.0, 1.0); glPolygonMode(GL_FRONT_AND_BACK, GL_LINE); glPolygonMode(GL_FRONT_AND_BACK, GL_FILL); 2009-2 학기 가상현실

예제 6-7 눈에 띄는 결함을 없애는 다각형 오프셋: polyoff.c #include <GL/glut.h> #include <stdio.h> #include <stdlib.h> #ifdef GL_VERSION_1_1 GLuint list; GLint spinx = 0; GLint spiny = 0; GLfloat tdist = 0.0; GLfloat polyfactor = 1.0; GLfloat polyunits = 1.0; 2009-2 학기 가상현실

GLfloat mat_ambient[] = { 0.8, 0.8, 0.8, 1.0 }; void display (void) { GLfloat mat_ambient[] = { 0.8, 0.8, 0.8, 1.0 }; GLfloat mat_diffuse[] = { 1.0, 0.0, 0.5, 1.0 }; GLfloat mat_specular[] = { 1.0, 1.0, 1.0, 1.0 }; GLfloat gray[] = { 0.8, 0.8, 0.8, 1.0 }; GLfloat black[] = { 0.0, 0.0, 0.0, 1.0 }; glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); glPushMatrix (); glTranslatef (0.0, 0.0, tdist); glRotatef ((GLfloat) spinx, 1.0, 0.0, 0.0); glRotatef ((GLfloat) spiny, 0.0, 1.0, 0.0); 2009-2 학기 가상현실

glMaterialfv(GL_FRONT, GL_AMBIENT_AND_DIFFUSE, gray); glMaterialfv(GL_FRONT, GL_SPECULAR, black); glMaterialf(GL_FRONT, GL_SHININESS, 0.0); glEnable(GL_LIGHTING); glEnable(GL_LIGHT0); glEnable(GL_POLYGON_OFFSET_FILL); glPolygonOffset(polyfactor, polyunits); glCallList (list); glDisable(GL_POLYGON_OFFSET_FILL); 2009-2 학기 가상현실

glDisable(GL_LIGHTING); glDisable(GL_LIGHT0); glColor3f (1.0, 1.0, 1.0); glPolygonMode(GL_FRONT_AND_BACK, GL_LINE); glCallList (list); glPolygonMode(GL_FRONT_AND_BACK, GL_FILL); glPopMatrix (); glFlush (); } 2009-2 학기 가상현실

GLfloat light_ambient[] = { 0.0, 0.0, 0.0, 1.0 }; void gfxinit (void) { GLfloat light_ambient[] = { 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 light_position[] = { 1.0, 1.0, 1.0, 0.0 }; GLfloat global_ambient[] = { 0.2, 0.2, 0.2, 1.0 }; glClearColor (0.0, 0.0, 0.0, 1.0); list = glGenLists(1); glNewList (list, GL_COMPILE); glutSolidSphere(1.0, 20, 12); glEndList (); 2009-2 학기 가상현실

glEnable(GL_DEPTH_TEST); 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); glLightModelfv (GL_LIGHT_MODEL_AMBIENT, global_ambient); } 2009-2 학기 가상현실

void reshape(int width, int height) { glViewport (0, 0, width, height); glMatrixMode (GL_PROJECTION); glLoadIdentity (); gluPerspective(45.0, (GLdouble)width/(GLdouble)height, 1.0, 10.0); glMatrixMode (GL_MODELVIEW); gluLookAt (0.0, 0.0, 5.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0); } 2009-2 학기 가상현실

void mouse(int button, int state, int x, int y) { switch (button) { case GLUT_LEFT_BUTTON: switch (state) { case GLUT_DOWN: spinx = (spinx + 5) % 360; glutPostRedisplay(); break; default: } 2009-2 학기 가상현실

case GLUT_MIDDLE_BUTTON: switch (state) { case GLUT_DOWN: spiny = (spiny + 5) % 360; glutPostRedisplay(); break; default: } 2009-2 학기 가상현실

case GLUT_RIGHT_BUTTON: switch (state) { case GLUT_UP: exit(0); break; default: } 2009-2 학기 가상현실

void keyboard (unsigned char key, int x, int y) { switch (key) { case 't': if (tdist < 4.0) { tdist = (tdist + 0.5); glutPostRedisplay(); } break; case 'T': if (tdist > -5.0) { tdist = (tdist - 0.5); 2009-2 학기 가상현실

polyfactor = polyfactor + 0.1; case 'F': polyfactor = polyfactor + 0.1; printf ("polyfactor is %f\n", polyfactor); glutPostRedisplay(); break; case 'f': polyfactor = polyfactor - 0.1; 2009-2 학기 가상현실

polyunits = polyunits + 1.0; printf ("polyunits is %f\n", polyunits); case 'U': polyunits = polyunits + 1.0; printf ("polyunits is %f\n", polyunits); glutPostRedisplay(); break; case 'u': polyunits = polyunits - 1.0; default: } 2009-2 학기 가상현실

int main(int argc, char** argv) { glutInit(&argc, argv); glutInitDisplayMode(GLUT_SINGLE | GLUT_RGB | GLUT_DEPTH); glutCreateWindow(argv[0]); glutReshapeFunc(reshape); glutDisplayFunc(display); glutMouseFunc(mouse); glutKeyboardFunc(keyboard); gfxinit(); glutMainLoop(); return 0; } 2009-2 학기 가상현실

int main(int argc, char** argv) { #else int main(int argc, char** argv) { fprintf (stderr, "This program demonstrates a feature which is not in OpenGL Version 1.0.\n"); fprintf (stderr, "If your implementation of OpenGL Version 1.0 has the right extensions,\n"); fprintf (stderr, "you may be able to modify this program to make it run.\n"); return 0; } #endif 2009-2 학기 가상현실

실행 결과 2009-2 학기 가상현실