1 / 31

Draw the basic Geometry Objects

Draw the basic Geometry Objects. Hanyang University Jungsik Park. VERTEX ATTRIBUTE AND GEOMETRIC PRIMITIVES. Vertex. Vertex 3D 공간상의 점 , 또는 기본 도형 ( 삼각형 , 폴리곤 등 ) 의 꼭지점 Vertex attributes Vertex coordinate Composition of primitives Vertex color Normal vector Texture coordinate.

karlf
Télécharger la présentation

Draw the basic Geometry Objects

An Image/Link below is provided (as is) to download presentation Download Policy: Content on the Website is provided to you AS IS for your information and personal use and may not be sold / licensed / shared on other websites without getting consent from its author. Content is provided to you AS IS for your information and personal use only. Download presentation by click this link. While downloading, if for some reason you are not able to download a presentation, the publisher may have deleted the file from their server. During download, if you can't get a presentation, the file might be deleted by the publisher.

E N D

Presentation Transcript


  1. Draw the basic Geometry Objects Hanyang University Jungsik Park

  2. VERTEX ATTRIBUTE AND GEOMETRIC PRIMITIVES

  3. Vertex • Vertex • 3D 공간상의 점, 또는 기본 도형(삼각형, 폴리곤 등)의 꼭지점 • Vertex attributes • Vertex coordinate • Composition of primitives • Vertex color • Normal vector • Texture coordinate

  4. Vertex coordinate • glVertex*() • vertex의 3D/2D 좌표를 지정. • vertex 속성 중 가장 중요한 속성으로 glBegin() ~ glEnd() 사이에 위치시킴으로써 frame buffer에 도형을 그리게 된다. • 그 외의 속성은 지정하지 않아도 도형을 그릴 수 있으나 vertex 좌표를 지정하지 않으면 도형을 그릴 수 없다. • glFlush()를 호출함으로써 frame buffer의 내용을 화면에 출력한다.

  5. Vertex coordinate • OpenGL coordinate system • 3D cartesian coordinate system • x, y, z 축 각각 [-1.0, 1.0]의 범위를 갖는정규화된 직육면체의 view volume 내의 물체를 그린다. • 일반적으로 더 큰 view volume, 혹은원근감을 표현할 수 있는 frustum view volume 내의 물체를 그리기 위해 view volume 변환을 먼저 수행한다. • 2D의 경우 z=0인 평면상의 물체를 그린다.

  6. Primitives • Geometric primitives • vertex들로 구성되며, vertex의 좌표는 glVertex*()로 지정 • 면을 가지는 도형의 경우 vertex들이 반시계방향의 순서를 가지도록 지정되어야 한다.

  7. 폴리곤 구성의 규칙 폴리곤을 구성하는 모든 vertex는 한 평면상에 위치해야 한다. 폴리곤을 이루는 선들은 서로 교차해서는 안 되면, 폴리곤의 전체적인 모양은 볼록해야 한다. 위의 규칙을 항상 만족하는 삼각형을 많이 사용 Polygon construction rules

  8. Polygon construction rules • 다음 도형을 하나의 폴리곤으로 그리는 경우 • 잘못된 결과가 나타난다. glBegin(GL_QUADS); glVertex2f(-0.5, -0.5); glVertex2f(0.5, 0.5); glVertex2f(-0.5, 0.5); glVertex2f(0.5, -0.5); glEnd();

  9. Example code #include <GL/glut.h> int primitive[] = {GL_POINTS, GL_LINES, GL_LINE_STRIP, GL_LINE_LOOP , GL_POLYGON, GL_QUADS, GL_TRIANGLES}; int index; void mydisplay(){ glClear(GL_COLOR_BUFFER_BIT); glBegin(primitive[index]); glVertex2f(-0.5, 0.0); glVertex2f(-0.3536, 0.3536); glVertex2f(0.0, 0.5); glVertex2f(0.3536, 0.3536); glVertex2f(0.5, 0.0); glVertex2f(0.3536, -0.3536); glVertex2f(0.0, -0.5); glVertex2f(-0.3536, -0.3536); glEnd(); glFlush(); } void mykeyboard(unsigned char key, int x, int y) { if (key == 'n' || key == 'N') index++; else if (key == 'p' || key == 'P') index--; if (index < 0) index = 6; if (index > 6) index = 0; glutPostRedisplay(); } int main(int argc, char** argv){ glutCreateWindow(“primitives"); glutDisplayFunc(mydisplay); glutKeyboardFunc(mykeyboard); glutMainLoop(); }

  10. Drawing with fewer vertices • GL_TRIANGLE_STRIP, GL_QUAD_STRIP • GL_TRIANGLE_FAN • Advantages to using fewer vertices • 메모리 공간 절약 • 연산수 감소 및 그래픽 카드로의 데이터 전송 대역폭 절약 P2 P3 P0 P1 P4 P6 P5

  11. Example code - GL_TRIANGLE_STRIP • GL_TRIANGLES 사용 void mydisplay(){ glClear(GL_COLOR_BUFFER_BIT); glBegin(GL_TRIANGLES); glVertex2f(-0.6, -0.2); // P0 glVertex2f(-0.5, 0.2); // P1 glVertex2f(-0.3, -0.2); // P2 glVertex2f(-0.3, -0.2); // P2 glVertex2f(-0.5, 0.2); // P1 glVertex2f(-0.2, 0.2); // P3 glVertex2f(-0.3, -0.2); // P2 glVertex2f(-0.2, 0.2); // P3 glVertex2f(0.0, -0.2); // P4 glVertex2f(0.0, -0.2); // P4 glVertex2f(-0.2, 0.2); // P3 glVertex2f(0.1, 0.2); // P5 glVertex2f(0.0, -0.2); // P4 glVertex2f(0.1, 0.2); // P5 glVertex2f(0.3, -0.2); // P6 glVertex2f(0.3, -0.2); // P6 glVertex2f(0.1, 0.2); // P5 glVertex2f(0.4, 0.2); // P7 glEnd(); glFlush(); } • GL_TRIANGLE_STRIP 사용 void mydisplay(){ glClear(GL_COLOR_BUFFER_BIT); glBegin(GL_TRIANGLE_STRIP); glVertex2f(-0.6, -0.2); // P0 glVertex2f(-0.5, 0.2); // P1 glVertex2f(-0.3, -0.2); // P2 glVertex2f(-0.2, 0.2); // P3 glVertex2f(0.0, -0.2); // P4 glVertex2f(0.1, 0.2); // P5 glVertex2f(0.3, -0.2); // P6 glVertex2f(0.4, 0.2); // P7 glEnd(); glFlush(); }

  12. Example code – GL_TRIANGLE_FAN #include <math.h> #include <GL/glut.h> #define PI 3.141592 void mydisplay(){ GLfloat x, y, angle; glClear(GL_COLOR_BUFFER_BIT); glBegin(GL_TRIANGLE_FAN); glVertex2f(0.0f, 0.0f); for(angle = 0.0f; angle < (2.0f*PI); angle += (PI/8.0f)) { x = 0.5f*sin(angle); y = 0.5f*cos(angle); glVertex2f(x, y); } glEnd(); glFlush(); } int main(int argc, char** argv){ glutCreateWindow("simple"); glutDisplayFunc(mydisplay); glutMainLoop(); }

  13. Draw 3D object • glVertex3*()로 3차원 좌표 지정(z축 추가) • 아래 그림은 cube를 그린 예제 • 입체감을 표현하기 위해선 다음의 요소가 필요 • perspective projection • lighting & shading

  14. Example code - Draw 3D object void mydisplay(){ glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT); glPushMatrix(); glRotatef(xRot, 1.0f, 0.0f, 0.0f); glRotatef(yRot, 0.0f, 1.0f, 0.0f); glBegin(GL_QUADS); glVertex3f(0.3,0.3,0.3); glVertex3f(0.3,-0.3,0.3); glVertex3f(-0.3,-0.3,0.3); glVertex3f(-0.3,0.3,0.3); glVertex3f(0.3,0.3,-0.3); glVertex3f(0.3,-0.3,-0.3); glVertex3f(-0.3,-0.3,-0.3); glVertex3f(-0.3,0.3,-0.3); glVertex3f(0.3,0.3,-0.3); glVertex3f(0.3,0.3,0.3); glVertex3f(-0.3,0.3,0.3); glVertex3f(-0.3,0.3,-0.3); glVertex3f(0.3,-0.3,-0.3); glVertex3f(0.3,-0.3,0.3); glVertex3f(-0.3,-0.3,0.3); glVertex3f(-0.3,-0.3,-0.3); glVertex3f(0.3,0.3,0.3); glVertex3f(0.3,0.3,-0.3); glVertex3f(0.3,-0.3,-0.3); glVertex3f(0.3,-0.3,0.3); glVertex3f(-0.3,0.3,0.3); glVertex3f(-0.3,0.3,-0.3); glVertex3f(-0.3,-0.3,-0.3); glVertex3f(-0.3,-0.3,0.3); glEnd(); glPopMatrix(); glFlush(); } void specialkeys(int key, int x, int y) { if(key == GLUT_KEY_UP) xRot-= 5.0f; if(key == GLUT_KEY_DOWN) xRot += 5.0f; if(key == GLUT_KEY_LEFT) yRot -= 5.0f; if(key == GLUT_KEY_RIGHT) yRot += 5.0f; if(key > 356.0f) xRot = 0.0f; if(key < -1.0f) xRot = 355.0f; if(key > 356.0f) yRot = 0.0f; if(key < -1.0f) yRot = 355.0f; // Refresh the Window glutPostRedisplay(); } int main(int argc, char** argv){ glutCreateWindow("simple"); glutDisplayFunc(mydisplay); glutSpecialFunc(specialkeys); glutMainLoop(); }

  15. Vertex color • OpenGL에서는 vertex 단위로 색상을 할당. • 선, 면의 색상은 구성하는 vertex들의 색을 interpolation하여 결정 • glColor*() • 색상은 인자의 수에 따라 RGBA, RGB로 지정 • void glColor4f (GLfloat red, GLfloat green, GLfloat blue, GLfloat alpha); • void glColor3f (GLfloat red, GLfloat green, GLfloat blue); • 각 채널의 값의 범위 • 인자가 실수인 경우 [0.0, 1.0] • 인자가 정수인 경우 [0, 255]

  16. Example code – vertex color #include <GL/glut.h> int primitive[] = {GL_POINTS, GL_LINES, GL_LINE_STRIP, GL_LINE_LOOP , GL_POLYGON, GL_QUADS, GL_TRIANGLES}; int index; void mydisplay(){ glClear(GL_COLOR_BUFFER_BIT); glBegin(primitive[index]); glColor3f(1.0, 0.0, 0.0); // red glVertex2f(-0.5, 0.0); glColor3f(0.0, 1.0, 0.0); // green glVertex2f(-0.3536, 0.3536); glColor3f(0.0, 0.0, 1.0); // blue glVertex2f(0.0, 0.5); glColor3f(0.5, 0.5, 0.5); // gray glVertex2f(0.3536, 0.3536); glColor3f(1.0, 1.0, 0.0); // yellow glVertex2f(0.5, 0.0); glColor3f(1.0, 0.0, 1.0); // magenta glVertex2f(0.3536, -0.3536); glColor3f(0.0, 1.0, 1.0); // cyan glVertex2f(0.0, -0.5); glColor3f(1.0, 1.0, 1.0); // white glVertex2f(-0.3536, -0.3536); glEnd(); glFlush(); } void mykeyboard(unsigned char key, int x, int y) { if (key == 'n' || key == 'N') index++; else if (key == 'p' || key == 'P') index--; if (index < 0) index = 6; if (index > 6) index = 0; glutPostRedisplay(); } int main(int argc, char** argv){ glutCreateWindow(“primitives"); glutDisplayFunc(mydisplay); glutKeyboardFunc(mykeyboard); glutMainLoop(); }

  17. Other attributes • Normal vector • 폴리곤 앞면의 법선 벡터. 폴리곤 단위가 아닌 vertex 단위로 지정. • glNormal*() • lighting, backface culling 등에 사용됨 • Texture coordinate • 폴리곤에 텍스쳐를 매핑할 때 폴리곤의 각 지점과 영상의 픽셀을 대응시키기 위한 좌표 • glTexcoord*()

  18. MANIPULATION OF THE OPENGL STATES

  19. States • Point size & line width • Winding • Backface culling • Depth test • Polygon mode • Fill face • Wireframe • Point • Shade model

  20. States • State를 변화시키는 방법 • on/off 로 사용되는 state variable • glEnable() / glDisable() • depth test, lighting, texture mapping 등 • 그 외의 값을 가지는 state variable을 변화시키는 경우 • glFrontFace(), glLineWidth() 등 해당 state variable 전용 함수

  21. Point size & line width • Point size • 점의 크기를 지정 • void glPointSize(GLfloat size); • 기본값은 1이고, 사용할 수 있는 값의 범위는 플랫폼에 따라 다르다. • Point size로 사용할 수 있는 값의 범위를 알아내는 법 • Line width • 선의 두께를 지정 • void glLineWidth (GLfloat width); • 기본값은 1이고, 사용할 수 있는 값의 범위는 플랫폼에 따라 다르다. • Line width로 사용할 수 있는 값의 범위를 알아내는 법 • GLfloat sizes[2]; • GLfloat step; • glGetFloatv(GL_POINT_SIZE_RANGE,sizes); • glGetFloatv(GL_POINT_SIZE_GRANULARITY,&step); • GLfloat sizes[2]; • GLfloat step; • glGetFloatv(GL_LINE_WIDTH_RANGE,sizes); • glGetFloatv(GL_LINE_WIDTH_GRANULARITY,&step);

  22. Example – line width void mydisplay(){ glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT); GLfloat y; GLfloat fSizes[2]; GLfloat fCurrSize; glGetFloatv(GL_LINE_WIDTH_RANGE,fSizes); fCurrSize = fSizes[0]; for(y = -0.9f; y < 0.9f; y += 0.2f) { glLineWidth(fCurrSize); glBegin(GL_LINES); glVertex2f(-0.8f, y); glVertex2f(0.8f, y); glEnd(); fCurrSize += 1.0f; } glFlush(); }

  23. Winding • 폴리곤을 구성하는 vertex들의 순서를 지정 • 폴리곤의 앞면과 뒷면을 결정하기 위한 방법 • glFrontFace(GL_CCW); • 반시계 방향으로 vertex 지정(디폴트) • glFrontFace(GL_CW); • 시계 방향으로 vertex 지정 • 앞면과 뒷면을 결정함으로써 보이지 않는 부분을 그리지 않거나, 앞면과 뒷면에 각각 다른 색상,재질을 지정할 수 있다.

  24. Backface culling • 폴리곤의 보이지 않는 면(뒷면)을 제거하는 옵션 • glEnable(GL_CULL_FACE); • glDisable(GL_CULL_FACE); • 불필요한 면을 그리지 않음으로써 성능상의 이득을 얻을 수 있다. • 종이 같은 얇은 평면, 유리와 같은 투명한 물체는 뒷면도 그려져야 하므로 backface culling을 사용하지 않는다.

  25. Depth test • 어떤 물체가 다른 물체의 앞에 있는 경우, 뒤의 물체가 그려지지 않도록 한다. • glEnable(GL_DEPTH_TEST); • depth buffer를 이용하여 픽셀을 그릴 때마다 z값을 비교하여 높은 z값을 갖는 픽셀로 갱신함으로써 뒤의 물체가 보이지 않도록 한다. • glDisable(GL_DEPTH_TEST); • z값과 관계없이 나중에 그려지는 물체를 그린다. • backface culling과 달리 z값을 비교하여 그려지는지 여부를 결정하기 때문에 depth test로 인한 성능 이득은 없지만 사실적인 표현을 위해 필요한 요소. • backface culling : 아예 그리지 않음 • depth test : 그렸지만 보이지 않음

  26. Polygon mode • 폴리곤을 색칠된 면으로 그리거나, wireframe으로 그리는 옵션 • void glPolygonMode (GLenum face, GLenum mode); • face : GL_FRONT, GL_BACK, GL_FRONT_AND_BACK • mode : GL_FILL, GL_LINE, GL_POINT • 예 : 물체의 앞면을 wireframe으로 그릴 경우 • glPolygonMode(GL_FRONT, GL_LINE);

  27. Shade model • 폴리곤의 면을 색칠하는 방법 지정 • glShadeModel(GL_SMOOTH); • vertex 색상을 interpolation하여 면의 각 부분을 색칠 • glShadeModel(GL_FLAT); • 폴리곤을 구성하는 vertex 중 마지막 vertex의 색상으로 면을 색칠

  28. Example code #include <stdio.h> #include <GL/glut.h> bool bBackfaceCull = false; bool bDepthTest = false; bool bWindCCW = false; bool bShadeSmooth = false; bool bWireFrame = false; static GLfloat xRot = 0.0f; static GLfloat yRot = 0.0f; void mydisplay(){ glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT); if (bBackfaceCull) glEnable(GL_CULL_FACE); else glDisable(GL_CULL_FACE); if (bDepthTest) glEnable(GL_DEPTH_TEST); else glDisable(GL_DEPTH_TEST); if (bWindCCW) glFrontFace(GL_CCW); else glFrontFace(GL_CW); if (bShadeSmooth) glShadeModel(GL_SMOOTH); else glShadeModel(GL_FLAT); if (bWireFrame) glPolygonMode(GL_FRONT, GL_LINE); else glPolygonMode(GL_FRONT, GL_FILL); glPushMatrix(); glRotatef(xRot, 1.0f, 0.0f, 0.0f); glRotatef(yRot, 0.0f, 1.0f, 0.0f);

  29. Example code(cont’d) glBegin(GL_QUADS); // Front Face glColor3f(1.0f, 1.0f, 1.0f); glVertex3f(0.3,0.3,0.3); // White glColor3f(1.0f, 1.0f, 0.0f); glVertex3f(0.3,-0.3,0.3); // Yellow glColor3f(1.0f, 0.0f, 0.0f); glVertex3f(-0.3,-0.3,0.3); // Red glColor3f(1.0f, 0.0f, 1.0f); glVertex3f(-0.3,0.3,0.3); // Magenta // Back Face glColor3f(0.0f, 1.0f, 1.0f); glVertex3f(0.3,0.3,-0.3); // Cyan glColor3f(0.0f, 1.0f, 0.0f); glVertex3f(0.3,-0.3,-0.3); // Green glColor3f(0.0f, 0.0f, 0.0f); glVertex3f(-0.3,-0.3,-0.3); // Black glColor3f(0.0f, 0.0f, 1.0f); glVertex3f(-0.3,0.3,-0.3); // Blue // Top Face glColor3f(0.0f, 1.0f, 1.0f); glVertex3f(0.3,0.3,-0.3); // Cyan glColor3f(1.0f, 1.0f, 1.0f); glVertex3f(0.3,0.3,0.3); // White glColor3f(1.0f, 0.0f, 1.0f); glVertex3f(-0.3,0.3,0.3); // Magenta glColor3f(0.0f, 0.0f, 1.0f); glVertex3f(-0.3,0.3,-0.3); // Blue // Bottom Face glColor3f(0.0f, 1.0f, 0.0f); glVertex3f(0.3,-0.3,-0.3); // Green glColor3f(1.0f, 1.0f, 0.0f); glVertex3f(0.3,-0.3,0.3); // Yellow glColor3f(1.0f, 0.0f, 0.0f); glVertex3f(-0.3,-0.3,0.3); // Red glColor3f(0.0f, 0.0f, 0.0f); glVertex3f(-0.3,-0.3,-0.3); // Black

  30. Example code(cont’d) // Left face glColor3f(1.0f, 1.0f, 1.0f); glVertex3f(0.3,0.3,0.3); // White glColor3f(0.0f, 1.0f, 1.0f); glVertex3f(0.3,0.3,-0.3); // Cyan glColor3f(0.0f, 1.0f, 0.0f); glVertex3f(0.3,-0.3,-0.3); // Green glColor3f(1.0f, 1.0f, 0.0f); glVertex3f(0.3,-0.3,0.3); // Yellow // Right face glColor3f(1.0f, 0.0f, 1.0f); glVertex3f(-0.3,0.3,0.3); // Magenta glColor3f(0.0f, 0.0f, 1.0f); glVertex3f(-0.3,0.3,-0.3); // Blue glColor3f(0.0f, 0.0f, 0.0f); glVertex3f(-0.3,-0.3,-0.3); // Black glColor3f(1.0f, 0.0f, 0.0f); glVertex3f(-0.3,-0.3,0.3); // Red glEnd(); glPopMatrix(); // Show the graphics glFlush(); } void specialkeys(int key, int x, int y) { if(key == GLUT_KEY_UP) xRot-= 5.0f; if(key == GLUT_KEY_DOWN) xRot += 5.0f; if(key == GLUT_KEY_LEFT) yRot -= 5.0f; if(key == GLUT_KEY_RIGHT) yRot += 5.0f; if(key > 356.0f) xRot = 0.0f; if(key < -1.0f) xRot = 355.0f; if(key > 356.0f) yRot = 0.0f; if(key < -1.0f) yRot = 355.0f; glutPostRedisplay(); }

  31. Example code(cont’d) void mykeyboard(unsigned char key, int x, int y) { switch (key) { case 'b': case 'B': bBackfaceCull = !bBackfaceCull; if (bBackfaceCull) printf("backface culling : on\n"); else printf("backface culling : off\n"); break; case 'd': case 'D': bDepthTest = !bDepthTest; if (bDepthTest) printf("depth test : on\n"); else printf("depth test : off\n"); break; case 'w': case 'W': bWireFrame = !bWireFrame; if (bWireFrame) printf("draw wireframe\n"); else printf("fill face\n"); break; case 's': case 'S': bShadeSmooth = !bShadeSmooth; if (bShadeSmooth) printf("smooth shading\n"); else printf("flat shading\n"); break; case 'c': case 'C': bWindCCW = !bWindCCW; if (bWindCCW) printf("wind counter-clockwise\n"); else printf("wind clockwise\n"); break; } glutPostRedisplay(); } int main(int argc, char** argv){ glutCreateWindow("simple"); glutDisplayFunc(mydisplay); glutKeyboardFunc(mykeyboard); glutSpecialFunc(specialkeys); glutMainLoop(); }

More Related