การเขียนโปรแกรมกราฟิก OPENGL
OPENGL เป็นไลบรารีกราฟิกและโมเดลสามมิติ เนื่องจากประสิทธิภาพที่โดดเด่นในกราฟิกสามมิติ ปัจจุบันภาษาระดับสูงจำนวนมากจึงมีอินเทอร์เฟซสำหรับ OPENGL เช่น: VC, DELPHI, C++ Builder เป็นต้น การใช้ OPENGL สามารถลดความยากสำหรับผู้ใช้ในการพัฒนากราฟิกและรูปภาพได้อย่างมาก ทำให้ผู้ใช้สามารถผลิตโฆษณาเชิงพาณิชย์ระดับสูง, กราฟิก CAD, แอนิเมชั่นสามมิติ, การจำลองกราฟิก และคอลเลกชันภาพยนตร์และโทรทัศน์
1. ฟังก์ชั่นของ OPENGL
เดิมที OPENGL เป็นไลบรารีซอฟต์แวร์กราฟิกบนเวิร์กสเตชัน เนื่องจากมีการใช้งานอย่างกว้างขวางในเชิงพาณิชย์ การทหาร การแพทย์ การบินและอวกาศ และสาขาอื่น ๆ กราฟิกที่ตรงตามความต้องการของผู้ใช้จึงสามารถพัฒนาบนคอมพิวเตอร์ระดับล่างได้ OPENGL ไม่เพียงแต่สามารถวาดภาพพื้นฐานเท่านั้น แต่ยังมีฟังก์ชันและขั้นตอนจำนวนมากสำหรับการประมวลผลภาพกราฟิกอีกด้วย
1. การเปลี่ยนแปลงกราฟิก
มันเป็นพื้นฐานของการแสดงกราฟิกและการผลิต การออกแบบแอนิเมชั่นและการแสดงแอนิเมชั่นแยกกันไม่ออกจากการแปลงกราฟิก ตามคุณสมบัติการแสดงผลของกราฟิก: การแปลงมุมมอง การแปลงโมเดล การแปลงการฉายภาพ การแปลงรูปตัด และการแปลงวิวพอร์ต ฯลฯ
2. เอฟเฟกต์แสง
สีของวัตถุที่ไม่ส่องสว่างนั้นเกิดจากวัตถุที่สะท้อนแสงภายนอกซึ่งเป็นแสงสว่าง ในกราฟิกสามมิติ หากใช้การจัดแสงอย่างไม่เหมาะสม กราฟิกสามมิติจะสูญเสียความรู้สึกสามมิติที่แท้จริงไป OPENGL แบ่งแสงออกเป็น: แสงจากการแผ่รังสี แสงโดยรอบ แสงที่กระจาย แสงสะท้อน ฯลฯ
3. การทำแผนที่พื้นผิว
การทำแผนที่พื้นผิวช่วยให้คุณสามารถเพิ่มพื้นผิวในโลกแห่งความเป็นจริงให้กับพื้นผิวสามมิติได้ ตัวอย่างเช่น: สี่เหลี่ยมผืนผ้าไม่สามารถเป็นตัวแทนของวัตถุในโลกแห่งความเป็นจริงได้ หากเต็มไปด้วยพื้นผิวที่ "จำเป็น" มันก็จะกลายเป็นความสมจริง
4. เทคนิคพิเศษกราฟิก
ฟังก์ชันการผสม ฟังก์ชันป้องกันนามแฝง และฟังก์ชันหมอกสามารถจัดการความโปร่งใสและความโปร่งแสงของกราฟิกสามมิติ ให้วัตถุมีความเรียบเนียน ใช้ส่วนของเส้นเพื่อทำให้เรียบและให้เอฟเฟกต์หมอก
5. เทคนิคพิเศษของภาพ
ฟังก์ชันพื้นฐานสำหรับการประมวลผลบิตแมป: การวาดภาพ การคัดลอกและการจัดเก็บรูปภาพ การทำแผนที่และการถ่ายโอน การปรับขนาดภาพ ฯลฯ ฟังก์ชันการดำเนินการบิตแมปสามารถอธิบายกระบวนการสร้างตัวอักษรจีนในระดับล่างของภาพวาดต้นฉบับได้
2. สร้างแอปพลิเคชัน OPENGL
1. หลักการทั่วไป
A. เพิ่มหน่วยสนับสนุน OPENGL ในการใช้งาน: OpenGL;
B เริ่มต้น OPENGL ในระหว่างเหตุการณ์ OnCreate ของแบบฟอร์ม
C เริ่มต้น OPENGL ระหว่างเหตุการณ์ OnPaing ของหน้าต่าง
D เริ่มต้น OPENGL ระหว่างเหตุการณ์ OnResize ของหน้าต่าง
E เริ่มต้น OPENGL ในระหว่างเหตุการณ์ OnDestroy ของหน้าต่าง
2. ตัวอย่างง่ายๆ
A สร้างโครงการ FILE->แอปพลิเคชันใหม่
B เพิ่มโค้ดในเหตุการณ์ OnCreate:
กระบวนการ TfrmMain.FormCreate (ผู้ส่ง: TObject);
var
pfd:TPixelFormatDescriptor; //ตั้งค่าตารางคำอธิบาย
รูปแบบพิกเซล:จำนวนเต็ม;
เริ่ม
ControlStyle:=ControlStyle+[csOpaque];
FillChar(pfd,ขนาดของ(pfd),0);
ด้วย pfd ทำ
เริ่ม
nSize:=ขนาดของ(TPixelFormatDescriptor);
เวอร์ชัน:=1;
dwFlags:=PFD_DRAW_TO_WINDOW หรือ
PFD_SUPPORT_OPENGL หรือ PFD_DOUBLEBUFFER;
iPixelType:=PFD_TYPE_RGBA;
cColorBits:=24;
cDepthBits:=32;
iLayerType:=PFD_MAIN_PLANE;
จบ;
PixelFormat:=ChoosePixelFormat(Canvas.Handle,@pfd);
SetPixelFormat(Canvas.Handle,PixelFormat,@pfd);
เหล็กแผ่นรีดร้อน:=wglCreateContext(Canvas.Handle);
w:=ClientWidth;
h:=ความสูงของไคลเอ็นต์;
จบ;
รหัส C ในเหตุการณ์ OnDestroy
ขั้นตอน TfrmMain.FormDestroy (ผู้ส่ง: TObject);
เริ่ม
wglDeleteContext (เหล็กแผ่นรีดร้อน);
จบ;
รหัส D ในเหตุการณ์ OnPaint
ขั้นตอน TfrmMain.FormPaint (ผู้ส่ง: TObject);
เริ่ม
wglMakeCurrent (ผ้าใบ. จัดการ, เหล็กแผ่นรีดร้อน);
glClearColor(1,1,1,1);
glColor3f(1,0,0);
glClear(GL_COLOR_BUFFER_BIT หรือ GL_DEPTH_BUFFER_BIT);
มายดราฟ;
glFlush;
SwapBuffers(ผ้าใบ.จัดการ);
จบ;
รหัส E ในเหตุการณ์ OnResize
ขั้นตอน TfrmMain.FormResize (ผู้ส่ง: TObject);
เริ่ม
glMatrixMode(GL_โครงการ);
glLoadIdentity;
glFrustum(-1.0,1.0,-1.0,1.0,3.0,7.0);
glViewPort(0,0,ความกว้างของไคลเอ็นต์,ความสูงของไคลเอ็นต์);
มายดราฟ;
จบ;
รหัส F ในฟังก์ชัน MyDraw (ประกาศโดยผู้ใช้ในคลาสหน้าต่าง)
ขั้นตอน TfrmMain.MyDraw;
เริ่ม
glPushMatrix;
ทรงกลม:=gluNewQuadric;
gluQuadricDrawStyle (ทรงกลม, GLU_LINE);
กลูสเฟียร์(ทรงกลม,0.5,25,25);
glPopMatrix;
SwapBuffers(ผ้าใบ.จัดการ);
gluDeleteQuadric (ทรงกลม);
จบ;
สิ่งที่แนบมาคือรหัสดั้งเดิมของโปรแกรมนี้:
หน่วย MainFrm;
อินเตอร์เฟซ
การใช้งาน
Windows, ข้อความ, SysUtils, ตัวแปร, คลาส, กราฟิก, การควบคุม, แบบฟอร์ม,
กล่องโต้ตอบ OpenGL;
พิมพ์
TfrmMain = คลาส (TForm)
ขั้นตอน FormCreate (ผู้ส่ง: TObject);
ขั้นตอน FormDestroy (ผู้ส่ง: TObject);
ขั้นตอน FormPaint (ผู้ส่ง: TObject);
ขั้นตอน FormResize (ผู้ส่ง: TObject);
ส่วนตัว
{ประกาศส่วนตัว}
เหล็กแผ่นรีดร้อน:HGLRC;
w,h:glFloat;
ทรงกลม:GLUquadricObj;
สาธารณะ
{ประกาศสาธารณะ}
ขั้นตอน MyDraw;
จบ;
var
frmMain: TfrmMain;
การดำเนินการ
{$R *.dfm}
ขั้นตอน TfrmMain.FormCreate (ผู้ส่ง: TObject);
var
pfd:TPixelFormatDescriptor;
รูปแบบพิกเซล:จำนวนเต็ม;
เริ่ม
ControlStyle:=ControlStyle+[csOpaque];
FillChar(pfd,ขนาดของ(pfd),0);
ด้วย pfd ทำ
เริ่ม
nSize:=ขนาดของ(TPixelFormatDescriptor);
เวอร์ชัน:=1;
dwFlags:=PFD_DRAW_TO_WINDOW หรือ
PFD_SUPPORT_OPENGL หรือ PFD_DOUBLEBUFFER;
iPixelType:=PFD_TYPE_RGBA;
cColorBits:=24;
cDepthBits:=32;
iLayerType:=PFD_MAIN_PLANE;
จบ;
PixelFormat:=ChoosePixelFormat(Canvas.Handle,@pfd);
SetPixelFormat(Canvas.Handle,PixelFormat,@pfd);
เหล็กแผ่นรีดร้อน:=wglCreateContext(Canvas.Handle);
w:=ClientWidth;
h:=ความสูงของไคลเอ็นต์;
จบ;
ขั้นตอน TfrmMain.FormDestroy (ผู้ส่ง: TObject);
เริ่ม
wglDeleteContext (เหล็กแผ่นรีดร้อน);
จบ;
ขั้นตอน TfrmMain.FormPaint (ผู้ส่ง: TObject);
เริ่ม
wglMakeCurrent (ผ้าใบ Handle, เหล็กแผ่นรีดร้อน);
glClearColor(1,1,1,1);
glColor3f(1,0,0);
glClear(GL_COLOR_BUFFER_BIT หรือ GL_DEPTH_BUFFER_BIT);
มายดราฟ;
glFlush;
SwapBuffers(ผ้าใบ.จัดการ);
จบ;
ขั้นตอน TfrmMain.MyDraw;
เริ่ม
glPushMatrix;
ทรงกลม:=gluNewQuadric;
gluQuadricDrawStyle (ทรงกลม, GLU_LINE);
กลูสเฟียร์(ทรงกลม,0.5,25,25);
glPopMatrix;
SwapBuffers(ผ้าใบ.จัดการ);
gluDeleteQuadric (ทรงกลม);
จบ;
ขั้นตอน TfrmMain.FormResize (ผู้ส่ง: TObject);
เริ่ม
glMatrixMode(GL_โครงการ);
glLoadIdentity;
glFrustum(-1.0,1.0,-1.0,1.0,3.0,7.0);
glViewPort(0,0,ความกว้างของไคลเอ็นต์,ความสูงของไคลเอ็นต์);
มายดราฟ;
จบ;
จบ.
3. แบบแผนเกี่ยวกับตัวแปรและฟังก์ชัน OPENGL
1. แบบแผนห้องสมุด OPENGL
มีห้องสมุดทั้งหมด 3 แห่ง ได้แก่ ห้องสมุดพื้นฐาน ห้องสมุดเชิงปฏิบัติ และห้องสมุดเสริม ใน DELPHI ไลบรารีพื้นฐานถูกใช้งานโดยหน่วย OpenGL ในสภาพแวดล้อม Windows โดยทั่วไปจะไม่ใช้ไลบรารีเสริม
2. แบบแผนคงที่ของ OPENGL
ค่าคงที่ OPENGL ใช้อักษรตัวใหญ่โดยขึ้นต้นด้วย "GL" และใช้ขีดล่างเพื่อแยกคำ เช่น GL_LINES ซึ่งหมายถึงการใช้ไลบรารีพื้นฐานในการวาดเส้นตรง
3. แบบแผนการตั้งชื่อของฟังก์ชัน OPENGL
A ส่วนแรกเริ่มต้นด้วย gl หรือ wgl เช่น gl ใน glColor3f
B ส่วนที่สองคือฟังก์ชันที่แสดงเป็นภาษาอังกฤษ โดยมีอักษรตัวแรกของคำเป็นตัวพิมพ์ใหญ่
ส่วนที่สามของ C คือตัวเลขซึ่งแสดงถึงพารามิเตอร์ของฟังก์ชัน
ส่วนที่สี่ของ D คือตัวพิมพ์เล็กที่ระบุประเภทของฟังก์ชัน
จำนวนเต็ม b9 บิต
จำนวนเต็ม s16 บิต
จำนวนเต็ม i32 บิต
หมายเลขจุดลอยตัว f32 บิต
หมายเลขจุดลอยตัว d64 บิต
จำนวนเต็มที่ไม่ได้ลงนาม ub9 บิต
ตัวอย่าง: glVertex2f(37,40); {ตัวเลขทศนิยม 32 บิตสองตัวเป็นพารามิเตอร์}
glVertex3d(37,40,5); {ตัวเลขทศนิยม 64 บิตสามตัวเป็นพารามิเตอร์}
p[1..3]:อาร์เรย์ของ glFloat;
glVertes3fv(p); {3f แสดงถึงตัวเลขทศนิยมสามตัว, v แสดงถึงการเรียกอาร์เรย์เป็นอินพุตพิกัดจุดยอด}
4. การเริ่มต้นของ OPENGL
1. โครงสร้าง PIXELFORMATDESCRIPTOR
โดยส่วนใหญ่จะอธิบายคุณสมบัติของพิกเซล เช่น โหมดสีของพิกเซลและองค์ประกอบของสีแดง เขียว และน้ำเงิน
tagPIXELFORMATDESCRIPTOR = บันทึกที่อัดแน่น
nขนาด: Word;
เวอร์ชัน: Word;
dwFlags: DWORD;
iPixelType: ไบต์;
cColorBits: ไบต์;
cRedBits: ไบต์;
cRedShift: ไบต์;
cGreenBits: ไบต์;
cGreenShift: ไบต์;
cBlueBits: ไบต์;
cBlueShift: ไบต์;
cAlphaBits: ไบต์;
cAlphaShift: ไบต์;
cAccumBits: ไบต์;
cAccumRedBits: ไบต์;
cAccumGreenBits: ไบต์;
cAccumBlueBits: ไบต์;
cAccumAlphaBits: ไบต์;
cDepthBits: ไบต์;
cStencilBits: ไบต์;
cAuxBuffers: ไบต์;
iLayerType: ไบต์;
b สงวนไว้: ไบต์;
dwLayerMask: DWORD;
dwVisibleMask: DWORD;
dwDamageMask: DWORD;
จบ;
TPixelFormatDescriptor = tagPIXELFORMATDESCRIPTOR;
dwFlags แสดงถึงคุณลักษณะของรูปแบบจุด:
กราฟิก PFD_DRAW_TO_WINDOW ถูกวาดลงบนหน้าจอหรือพื้นผิวอุปกรณ์
PFD_DRAW_TO_BITMAP ดึงบิตแมปในหน่วยความจำ
PFD_SUPPORT_GDI รองรับการวาดภาพ GDI
PFD_SUPPORT_OPENGL รองรับฟังก์ชัน OPENGL
PFD_DOUBLEBUFFER ใช้การบัฟเฟอร์สองครั้ง
แคชสเตอริโอ PFD_STEREO
PFD_NEED_PALLETTE ใช้จานสี RGBA
PFD_GENERIC_FORMAT เลือกรูปแบบการวาดภาพที่ GDI รองรับ
PFD_NEED_SYSTEM_PALETTE ใช้ชุดฮาร์ดแวร์ที่รองรับ OPENGL
iPixelType ตั้งค่าโหมดสีพิกเซล: PFD_TYPE_RGBA หรือ PFD_TYPE_INDEX..
cColorBits ตั้งค่าบิตสี ถ้าเป็น 9 หมายความว่ามี 256 สีเพื่อแสดงสีของจุด
cRedBits, cGreenBits, cBlueBits เมื่อใช้ RGBA คือจำนวนบิตที่ใช้สำหรับสีหลักสามสี
cRedShitfs, cGreenShifts, cBlueShifts เมื่อใช้ RGBA คือจำนวนหลักที่สามารถปรับสำหรับสีหลักสามสีได้
cAlphaBits, cAlphaShifts เมื่อใช้ RGBA จำนวนบิตที่ใช้โดย Alpha และจำนวนบิตที่ปรับได้
cAccumBits กำหนดจำนวนบิตทั้งหมดในพื้นที่บัฟเฟอร์การสะสม
cAccumRedBits, cAccumGreenBits และ cAccumBlueBits ตั้งค่าจำนวนรวมของระนาบสีหลักสามระนาบในพื้นที่บัฟเฟอร์การสะสม
cAccumAlphaBits กำหนดจำนวนอัลฟ่าบิตทั้งหมดในบัฟเฟอร์การสะสม
cDepthBits กำหนดความลึกของบัฟเฟอร์ความเข้มข้น
cStencilBits กำหนดความลึกของแคชลายฉลุ
cAuxBuffers หมายถึงขนาดของบัฟเฟอร์เสริม
iLayerType ระบุประเภทของเลเยอร์
bReserved ไม่ได้ใช้และต้องเป็นศูนย์
dwLayerMask ระบุมาสก์ของการซ้อนทับ
dwDamageMask ตั้งค่าว่าจะแชร์โหมดพิกเซลเดียวกันในแคชเฟรมเดียวกันหรือไม่
2. ขั้นตอนการเริ่มต้นของ OPENGL
ใช้ Canvas.Handle เพื่อขอรับหมายเลขอ้างอิงหน้าต่าง
B สร้างตัวแปร TPixelFormatDescriptor เพื่อกำหนดรูปแบบพิกเซล
C ใช้ฟังก์ชัน ChoosePixelFormat เพื่อเลือกรูปแบบพิกเซล
D ใช้ฟังก์ชัน SetPixelFormat เพื่อใช้รูปแบบพิกเซลเพื่อให้มีผล
E ใช้ฟังก์ชัน wglCreateContext เพื่อสร้างตารางคำอธิบายการแปล
F ใช้ฟังก์ชัน wglMakeCurrent เพื่อใช้ตารางคำอธิบายการแปลที่สร้างขึ้นเป็นตารางคำอธิบายการแปลปัจจุบัน
3. การเปิดเผยทรัพยากร
ใช้ขั้นตอน wglDeleteContext เพื่อลบตารางบริบทพิกเซล
B ใช้ขั้นตอน ReleaseDC เพื่อปล่อยหน่วยความจำหน้าต่าง
ในเหตุการณ์ OnDestroy ของหน้าต่าง:
เริ่ม
ถ้า hrc<>null แล้ว
wglDeleteCurrent(เหล็กแผ่นรีดร้อน);
ถ้า hdc<>null แล้ว
ReleaseDC (ที่จับ, hdc);
จบ;
5. การเขียนแบบกราฟิกพื้นฐาน OPENGL
1. สีของกราฟิก
ให้ความสนใจกับการตั้งค่าสีพื้นหลัง การตั้งค่าสีมักจะเกี่ยวข้องกับตัวแปรคำอธิบายพิกเซล นั่นคือกับสมาชิก iPixelType ในคำจำกัดความ TPixelFormatDescriptor
iPixelType:=PFD_TYPE_COLORINDEX;
จากนั้นคุณสามารถใช้เฉพาะขั้นตอน glIndexd, glIndexf, glIndexi, glIndexs, glIndexv, glIndexfv, glIndexiv, glIndexsv เพื่อตั้งค่าสีกราฟิก
iPixelType:=PFD_TYPE_RGBA;
จากนั้นคุณสามารถใช้ glColor3b, glColor3f, glColor4b, glColor4f, glColor4fv เพื่อตั้งค่าสีกราฟิกได้เท่านั้น
สีพื้นหลังกราฟิก: สีของหน้าจอและหน้าต่าง ซึ่งก็คือสีของบัฟเฟอร์สี หากต้องการเปลี่ยนสีพื้นหลังของกราฟิก คุณควรใช้ขั้นตอน glClearColor เพื่อตั้งค่าสีพื้นหลังก่อน จากนั้นใช้ขั้นตอน glClear เพื่อรีเฟรชหน้าต่างและหน้าจอด้วยสีพื้นหลังนี้
ขั้นตอน glClearColor (สีแดง: GLClampf, สีเขียว: GLClampf, สีน้ำเงิน: GLClampf, อัลฟา: GLClampf);
ขั้นตอน glClear (มาสก์: GLBitField);
สีแดง, สีเขียว, สีฟ้าและอัลฟ่าเป็นสีพื้นหลังที่จะตั้งค่าและค่าของพวกเขาคือ 0 ถึง 1 มาสก์เป็นวิธีรีเฟรชสีพื้นหลัง
ตัวอย่าง: ตั้งค่าหน้าต่างระบายสีให้เป็นสีเขียว
glClearColor(0,1,0,1);
glClear(GL_COLOR_BUFFER_BIT);
คุณค่าและความหมายของมาส์ก:
GL_COLOR_BUFFER_BIT ตั้งค่าบัฟเฟอร์สีปัจจุบัน
GL_DEPTH_BUFFER_BIT ตั้งค่าบัฟเฟอร์ความลึกปัจจุบัน
GL_ACCUM_BUFFER_BIT ตั้งค่าบัฟเฟอร์การสะสมปัจจุบัน
GL_STENCIL_BUFFER_BIT ตั้งค่าบัฟเฟอร์ STENCIL (เทมเพลต) ปัจจุบัน
หน้าต่างการวาดถูกตั้งค่าเป็นสีเทา
glClearColor(0.3,0.3,0.3,1);
glClear(GL_COLOR_BUFFER_BIT);
สีกราฟิก B
ใช้ glClear3f และ glClear4f เพื่อตั้งค่าสีการวาดของกราฟิก หากใช้พารามิเตอร์สามตัว หมายความว่าการตั้งค่าแสงสีแดง น้ำเงิน และเขียวทั้งสามสีตามลำดับ หากใช้พารามิเตอร์สี่ตัว พารามิเตอร์ตัวที่สี่แทนค่า RGBA
ตัวอย่างการตั้งค่าสีภาพวาดปัจจุบันเป็นสีน้ำเงิน:
glColor3f(0,0,1);
ตั้งค่าสีของพล็อตเป็นสีขาว:
glColor3f(1,1,1);
2. การวาดภาพกราฟิกอย่างง่าย
วาดกราฟิกอย่างง่าย เช่น จุด เส้น รูปหลายเหลี่ยม ฯลฯ ระหว่างขั้นตอน glBegin และ glEnd
glBegin (โหมด: GLenum); {กระบวนการวาด} glEnd;
ค่าของโหมด:
GL_POINTS ดึงหลายจุด
GL_LINES วาดเส้นหลายเส้น โดยวาดเส้นตรงทุกๆ สองจุด
GL_LINE_STRIP วาดเส้นหลายเส้น
GL_LINE_LOOP วาดรูปหลายเหลี่ยมแบบปิดที่เชื่อมต่อกันตั้งแต่ต้นจนจบ
GL_TRIANGLES วาดรูปสามเหลี่ยม
GL_TRIANGLE_STRIP วาดรูปสามเหลี่ยม โดยวาดรูปสามเหลี่ยมทุกๆ สามจุด
GL_TRIANGLE_FAN วาดรูปสามเหลี่ยม
GL_QUADS วาดรูปสี่เหลี่ยม
GL_QUAD_STRIP วาดแถบรูปสี่เหลี่ยมขนมเปียกปูน โดยวาดแถบรูปสี่เหลี่ยมขนมเปียกปูนหนึ่งแถบทุกๆ สี่จุด
GL_POLYGON วาดรูปหลายเหลี่ยม
ตัวอย่างการวาดจุดสามจุด:
เริ่ม
glPushMatrix;
glBegin(GL_POINT);
glVertex2f(0.1,0.1);
glVertex2f(0.5,0.5);
glVertex2f(0.1,0.3);
glend;
SwapBuffers(ผ้าใบ.จัดการ);
จบ;
หากคุณเปลี่ยน GL_POINT เป็น GL_LINES คุณจะวาดเส้น จุดที่สามไม่ถูกต้อง การทำ glColor3f(0,0,1) ก่อน glVertex2f จะเปลี่ยนสีของเส้นเป็นสีเขียว หากคุณเปลี่ยน GL_LINES เป็น GL_LINE_STRIP คุณสามารถวาดได้ สองเส้นตรง
ใช้ขั้นตอน glPointSize เพื่อกำหนดขนาดจุด ใช้ขั้นตอน glLineWidth เพื่อกำหนดความกว้างของเส้น
ใช้ขั้นตอน glLineStipple เพื่อตั้งค่าเทมเพลตสำหรับเส้นประ และใช้ขั้นตอน glEnable(GL_LINE_STIPPLE) และพารามิเตอร์ที่เกี่ยวข้องเพื่อเปิดใช้งานการวาดเพื่อวาดเส้นประ ขั้นตอน glDisable(GL_LINE_STIPPLE) และพารามิเตอร์ที่เกี่ยวข้องจะปิดเส้นประ
ขั้นตอน glLineStipple (ปัจจัย: GLint, รูปแบบ: GLushort);
ตัวประกอบพารามิเตอร์แสดงถึงจำนวนการซ้ำของรูปแบบเทมเพลตเส้นประ ค่าของตัวประกอบคือ 1255 รูปแบบเป็นลำดับไบนารี
glLineStipple(1,0,0x11C);{0x11C แสดงเป็น 10001110, 0 หมายถึงไม่จั่วแต้ม, 1 หมายถึงจั่วแต้ม}
ตัวอย่าง: เริ่มต้น
glColor3f(1,0,0);
glLineWidth(2);
glLineStipple(1,$11C);
glEnable(GL_LINE_STIPPLE);
glBegin(GL_LINES);
glVertex2f(-0.9,0.3);
glVertex2f(0.9,0.3);
glend;
glDisable(GL_LINE_STIPPLE);
glColor3f(1,0,1);
glLineStipple(2,$11C);
glEnable(GL_LINE_STIPPLE);
glBegin(GL_LINES);
glVertex2f(-0.9,0.1);
glVertex2f(0.9,0.1);
glend;
glDisable(GL_LINE_STIPPLE);
SwapBuffers(ผ้าใบ.จัดการ);
จบ;
การวาดรูปหลายเหลี่ยมคล้ายกับการวาดรูปเส้นจุด คุณต้องเปลี่ยนพารามิเตอร์เป็น GL_POLYGON, GL_QUADS, GL_TRAGLES สิ่งที่ควรทราบเมื่อวาด:
ด้านข้างของรูปหลายเหลี่ยมตัดกันที่จุดยอดเท่านั้น
รูปหลายเหลี่ยม B จะต้องเป็นรูปหลายเหลี่ยมนูน หากเป็นรูปหลายเหลี่ยมเว้า ผู้ใช้สามารถพับเป็นรูปหลายเหลี่ยมนูนเท่านั้นเพื่อเร่งความเร็วในการวาด
ตัวอย่าง: glBegin(GL_POLYGON);
glVertex2f(-0.9,0.3);
glVertex2f(0.9,0.3);
glVertex2f(0.9,-0.6);
glVertex2f(0.5,-0.6);
glVertex2f(-0.9,-0.2);
glend;
รูปหลายเหลี่ยมมีด้านหน้าและด้านหลัง และกระบวนการที่เกี่ยวข้องได้แก่:
glPolygonMode ควบคุมโหมดการวาดรูปหลายเหลี่ยมด้านหน้าและด้านหลัง
glFrontface ระบุด้านหน้าของรูปหลายเหลี่ยม
glCullFace แสดงรูปหลายเหลี่ยมที่ตั้งค่าให้กำจัดใบหน้า
glPolygonStripple สร้างสไตล์ของการเติมรูปหลายเหลี่ยม
3. พื้นผิวกำลังสองอย่างง่าย
ทรงกระบอก วงแหวน และทรงกลมล้วนเป็นพื้นผิวกำลังสอง
ทรงกระบอก
gluCylinder(qobj:GLUquadricObj,baseRadius:GLdouble,topRadius:GLdouble,ความสูง:GLdouble,
ชิ้น: GLint, สแต็ค: GLint);
qobj ระบุพื้นผิวกำลังสอง baseRadius คือรัศมีฐานของทรงกระบอก topRadius คือรัศมีด้านบนของทรงกระบอกที่วาด ความสูงคือความสูงของทรงกระบอก ส่วนคือจำนวนเส้นแบ่งรอบแกน Z การแบ่งเส้นตามแนวแกน Z
ถ้า baseRadius และ topRadius ไม่เท่ากัน คุณสามารถวาด frustum และกรวยได้
ขั้นตอน TfrmMain.MyDraw;
var
qObj:GLUQuadricObj;
เริ่ม
glPushMatrix;
glClear(GL_COLOR_BUFFER_BIT หรือ GL_DEPTH_BUFFER_BIT);
glColor3f(1,0,0);
qObj:=gluNewQuadric;
gluQuadricDrawStyle(qObj,GLU_LINE);
กลูซิลินเดอร์(qObj,0.5,0.1,0.2,10,10);
จบ;
นำมา
gluDisk(qobj:GLUquadricObj,รัศมีภายใน:GLdouble,รัศมีด้านนอก:GLdouble,สไลซ์:GLint,
ลูป:GLint);
ขั้นตอน TfrmMain.MyDraw;
var
qObj:GLUQuadricObj;
เริ่ม
glPushMatrix;
glClear(GL_COLOR_BUFFER_BIT หรือ GL_DEPTH_BUFFER_BIT);
glColor3f(1,0,0);
qObj:=gluNewQuadric;
gluQuadricDrawStyle(qObj,GLU_LINE);
กลูดิสก์(qObj,0.2,0.5,10,5);
SwapBuffers(ผ้าใบ.จัดการ);
จบ;
ค. ครึ่งวงกลม
gluPartialDisk(qobj:GLUquadricObj,รัศมีภายใน:GLdouble,รัศมีด้านนอก:GLdouble,สไลซ์:GLint,
ลูป:GLint,startAngle:GLdouble,sweepAngle:GLdouble);
startAngle, SweepAngle คือมุมเริ่มต้นและมุมสิ้นสุดของครึ่งวงกลม
ขั้นตอน TfrmMain.MyDraw;
var
qObj:GLUQuadricObj;
เริ่ม
glPushMatrix;
glClear(GL_COLOR_BUFFER_BIT หรือ GL_DEPTH_BUFFER_BIT);
glColor3f(1,0,0);
qObj:=gluNewQuadric;
gluQuadricDrawStyle(qObj,GLU_LINE);
gluPartialDisk(qObj,0.2,0.5,10,5,90,190);
SwapBuffers(ผ้าใบ.จัดการ);
จบ;
ดีทรงกลม
ฟังก์ชั่น gluSphere (qObj: GLUquadricObj, รัศมี: GLdouble, ชิ้น: GLint, สแต็ค: GLint);
ขั้นตอน TfrmMain.MyDraw;
var
qObj:GLUQuadricObj;
เริ่ม
glPushMatrix;
glClear(GL_COLOR_BUFFER_BIT หรือ GL_DEPTH_BUFFER_BIT);
glColor3f(1,0,0);
qObj:=gluNewQuadric;
gluQuadricDrawStyle(qObj,GLU_LINE);
{ ภาพเงา[ silu(:)5et ]n ภาพเงาโครงร่าง}
กลูสเฟียร์(qObj,0.5,20,20);
SwapBuffers(ผ้าใบ.จัดการ);
จบ;
E เกี่ยวกับกระบวนการของพื้นผิวกำลังสอง
gluNewQuadric สร้างวัตถุพื้นผิวกำลังสองใหม่
gluDeleteQuadric ลบวัตถุพื้นผิวกำลังสอง
gluQuadricDrawStyle ระบุประเภทของพื้นผิวกำลังสองที่จะวาด
gluQuadricNormal ตั้งค่าเวกเตอร์ปกติของพื้นผิวกำลังสอง
gluQuadricOrientation กำหนดว่าพื้นผิวกำลังสองถูกหมุนภายในหรือหมุนภายนอก
gluQuadricTexture กำหนดว่าพื้นผิวกำลังสองใช้พื้นผิวหรือไม่
F ขั้นตอนทั่วไปในการวาดพื้นผิวกำลังสอง
ขั้นแรกให้กำหนดวัตถุ GLUquadricObj
ประการที่สอง สร้างวัตถุพื้นผิว gluNewQuadric
ตั้งค่าคุณสมบัติของพื้นผิวกำลังสองอีกครั้ง (gluQuadricDrawStyle, gluQuadricTexture)
วาดพื้นผิวกำลังสอง (gluCylinder, gluSphere, gluDisk, gluPartialDisk)
6. การเปลี่ยนแปลงใน OPENGL
การแปลงเป็นพื้นฐานของการออกแบบแอนิเมชั่น รวมถึงการแปลกราฟิก การหมุน การปรับขนาด และการดำเนินการอื่นๆ ซึ่งดำเนินการทางคณิตศาสตร์ผ่านเมทริกซ์
1 กระบวนการ glLoadIdentity
สามารถแปลงเมทริกซ์ปัจจุบันเป็นเมทริกซ์เอกลักษณ์ได้
กระบวนการ 2 glLoadMatrix
สามารถกำหนดให้เมทริกซ์ที่ระบุเป็นเมทริกซ์ปัจจุบันได้
ขั้นตอน glLoadmatrixd (m: GLdouble);
ขั้นตอน glLoadmatrixf (m: GLfloat);
m แสดงถึงเมทริกซ์ 4X4 รหัสต่อไปนี้กำหนดและทำให้เป็นเมทริกซ์ปัจจุบัน
M:array[1..4,1..4] ของ GLfloat;
glLoadMatrix(@M);
3 กระบวนการ glMultMatrix
สามารถคูณโมเมนต์ปัจจุบันด้วยเมทริกซ์ที่กำหนดและใช้ผลลัพธ์เป็นโมเมนต์ปัจจุบันได้
ขั้นตอน glMultMatrixd (M: GLdouble);
ขั้นตอน glMultMatrixf (M: GLfloat);
4 glPushMatrix และ glPopmatrix
glPushMatrix สามารถส่งโมเมนต์ปัจจุบันเข้าไปในสแต็กเมทริกซ์ และ glPopMatrix สามารถดึงโมเมนต์ปัจจุบันออกจากสแต็กเมทริกซ์ได้
glPushMatrix สามารถจดจำตำแหน่งปัจจุบันของเมทริกซ์ได้ และ glPopmatrix สามารถส่งคืนตำแหน่งก่อนหน้าได้
หมายเหตุ: ต้องวาง glPushMatrix และ glPopMatrix ภายนอก glBegin และ glEnd
5 การเปลี่ยนแปลงการฉายภาพ
glOrtho สามารถสร้างเมทริกซ์ฉายภาพออร์โธกราฟี คูณโมเมนต์ปัจจุบันด้วยเมทริกซ์ฉายภาพออร์โธกราฟี และใช้ผลลัพธ์เป็นเมทริกซ์ปัจจุบัน
ฟังก์ชัน glOrtho (ซ้าย: GLdouble, ขวา: GLdouble, ล่าง: GLdouble, บน: GLdouble,
ใกล้:GLdouble, ไกล:GLdouble);
ขั้นตอน TfrmMain.FormResize (ผู้ส่ง: TObject);
var
nช่วง: GLfloat;
เริ่ม
nช่วง:=50.0;
w:=clientWidth;
h:=clientHeight;
ถ้า h=0 แล้ว
ชั่วโมง:=1;
glViewPort(0,0,w,h);
ถ้า w<=h แล้ว
glOrtho(-nRange,nRange,-nRange*h/w,nRange*h/w,
-nRange, nRange)
อื่น
glOrtho(-nRange*h/w,nRange*h/w,-nRange,nRange,
-nRange,nRange);
ทาสีใหม่;
จบ;
B glOrtho2D กำหนดเฉพาะด้านหน้า ด้านหลัง ซ้ายและขวาของระดับเสียงการดูแบบออโธกราฟิก
ขั้นตอน glOrtho (ซ้าย: GLdouble, ขวา: GLdouble, ด้านล่าง: GLdouble, บน: GLdouble);
ขั้นตอน C glMatrixMode
ความสามารถในการกำหนดประเภทของเมทริกซ์การดำเนินการปัจจุบัน
ขั้นตอน glMatrixMode (โหมด: GLenum);
ค่าของโหมด:
GL_MODELVIEW ระบุว่าการดำเนินการเมทริกซ์ที่ตามมาคือโมเดลสแต็กเมทริกซ์
GL_PROJECTION ระบุว่าการดำเนินการเมทริกซ์ที่ตามมาเป็นสแต็กเมทริกซ์การฉายภาพ
GL_TEXTURE ระบุว่าการดำเนินการเมทริกซ์ที่ตามมาคือสแต็กเมทริกซ์พื้นผิว
กระบวนการ D glFrustum
สร้างเมทริกซ์การฉายภาพเฉียงเปอร์สเปคทีฟและคูณเมทริกซ์ปัจจุบันด้วยเมทริกซ์ฉายภาพเฉียง ผลลัพธ์คือเมทริกซ์ปัจจุบัน
ขั้นตอน glFrustum (ซ้าย: GLdouble, ขวา: GLdouble, ด้านล่าง: GLdouble, บน: GLdouble,
ถัดไป:GLดับเบิ้ล,ไกล:GLดับเบิ้ล);
พารามิเตอร์เหล่านี้กำหนดระนาบการตัดด้านซ้าย ขวา บน ล่าง ด้านหน้า และด้านหลังของการฉายภาพเฉียง
อี gluPerspective กระบวนการ
สามารถกำหนดปริมาตรการรับชมพีระมิดสี่ด้านโดยมีแกน Z เป็นจุดกึ่งกลางได้
ขั้นตอน gluPerspetive (fovy: GLdouble, อัตราส่วน: GLdouble, zNear: GLdouble, zFar: GLdouble);
fovy กำหนดมุมมองของระนาบ xoz แง่มุม กำหนดอัตราส่วนในทิศทาง x และ y zNear และ zFar กำหนดระยะทางจากมุมมองไปยังระนาบการตัดและระนาบการตัดด้านหลังตามลำดับ
ขั้นตอน TfrmMain.FormResize (ผู้ส่ง: TObject);
var
ด้าน: GLfloat;
เริ่ม
w:=ClientWidth;
h:=ความสูงของไคลเอ็นต์;
ถ้า h=0 แล้ว
ชั่วโมง:=1;
glViewPort(0,0,ไคลเอนต์กว้าง,ไคลเอนต์สูง);
glMatrixMode(GL_โครงการ);
glLoadIdentity;
ด้าน:=w/h;
gluPerspective(30.0,ด้าน,1.0,50.0);
glMatrixMode(GL_MODELVIEW);
glLoadIdentity;
จบ;
6 เมทริกซ์การแปลงทางเรขาคณิต
การเปลี่ยนแปลงท่าทางการเคลื่อนไหวของวัตถุสามมิติหมายถึงการแปล การหมุน และการปรับขนาดของวัตถุ
กระบวนการ glTranslate สามารถย้ายแหล่งกำเนิดพิกัดไปที่ (x, y, z) ซึ่งเป็นไวยากรณ์การประกาศ:
ขั้นตอน glTranslated(x:GLdouble,y:GLdouble,z:GLdouble);
ขั้นตอน glTranslatef (x: GLdouble, y: GLdouble, z: GLdouble);
B glRotate สามารถหมุนวัตถุไปยังมุมที่กำหนดได้ ไวยากรณ์การประกาศของมันคือ:
ขั้นตอน glRotated (มุม: GLdouble, x: GLdouble, y: GLdouble, z: GLdouble);
ขั้นตอน glRotatef (มุม: GLdouble, x: GLdouble, y: GLdouble, z: GLdouble);
ในหมู่พวกเขา มุมคือมุมการหมุน และแกนกลางของการหมุนคือเส้นที่เชื่อมต่อจุดสองจุด (0,0,0) และ (x,y,z)
C glScale สามารถปรับขนาดระบบพิกัดได้ และไวยากรณ์การประกาศของมันคือ:
ขั้นตอน glScaled (x: GLdouble, y: GLdoble, z: GLdouble);
ขั้นตอน glScalef(x:GLdouble,y:GLdoble,z:GLdouble);
ค่า x, y และ z ที่มากกว่า 1 แสดงถึงการขยาย และค่าที่น้อยกว่า 1 แสดงถึงการลดลง
ตัวอย่างรหัสต้นฉบับ:
หน่วย MainFrm;
อินเตอร์เฟซ
การใช้งาน
Windows, ข้อความ, SysUtils, ตัวแปร, คลาส, กราฟิก, การควบคุม, แบบฟอร์ม,
กล่องโต้ตอบ, OpenGL, ExtCtrls;
พิมพ์
TfrmMain = คลาส (TForm)
ตัวจับเวลา 1: TTimer;
ขั้นตอน FormCreate (ผู้ส่ง: TObject);
ขั้นตอน FormDestroy (ผู้ส่ง: TObject);
ขั้นตอน FormPaint (ผู้ส่ง: TObject);
ขั้นตอน FormKeyDown (ผู้ส่ง: TObject; คีย์ var: Word;
กะ: TShiftState);
ขั้นตอน FormResize (ผู้ส่ง: TObject);
ขั้นตอน Timer1Timer (ผู้ส่ง: TObject);
ขั้นตอน FormClose (ผู้ส่ง: TObject; var Action: TCloseAction);
ส่วนตัว
{ประกาศส่วนตัว}
เหล็กแผ่นรีดร้อน:HGLRC;
w,h:จำนวนเต็ม;
ละติจูด ลองจิจูด: GLfloat;
รัศมี: GLdouble;
สาธารณะ
{ประกาศสาธารณะ}
ขั้นตอน MyDraw;
ขั้นตอน InitializeGL (ความกว้าง: GLsizei; ความสูง: GLsizei);
จบ;
var
frmMain: TfrmMain;
การดำเนินการ
{$R *.dfm}
ขั้นตอน TfrmMain.FormCreate (ผู้ส่ง: TObject);
var
pfd:TPixelFormatDescriptor;
รูปแบบพิกเซล:จำนวนเต็ม;
เริ่ม
ControlStyle:=ControlStyle+[csOpaque];
FillChar(pfd,ขนาดของ(pfd),0);
ด้วย pfd ทำ
เริ่ม
nSize:=ขนาดของ(TPixelFormatDescriptor);
เวอร์ชัน:=1;
dwFlags:=PFD_DRAW_TO_WINDOW หรือ
PFD_SUPPORT_OPENGL หรือ PFD_DOUBLEBUFFER;
iPixelType:=PFD_TYPE_RGBA;
cColorBits:=24;
cDepthBits:=32;
iLayerType:=PFD_MAIN_PLANE;
จบ;
PixelFormat:=ChoosePixelFormat(Canvas.Handle,@pfd);
SetPixelFormat(Canvas.Handle,PixelFormat,@pfd);
เหล็กแผ่นรีดร้อน:=wglCreateContext(Canvas.Handle);
w:=ClientRect.Right;
h:=ClientRect.Bottom;
เตรียมใช้งาน GL(w,h);
จบ;
ขั้นตอน TfrmMain.FormDestroy (ผู้ส่ง: TObject);
เริ่ม
wglDeleteContext (เหล็กแผ่นรีดร้อน);
จบ;
ขั้นตอน TfrmMain.FormPaint (ผู้ส่ง: TObject);
เริ่ม
wglMakeCurrent (ผ้าใบ. จัดการ, เหล็กแผ่นรีดร้อน);
glClearColor(1,1,1,1);
glColor3f(1,0,0);
glClear(GL_COLOR_BUFFER_BIT หรือ GL_DEPTH_BUFFER_BIT);
มายดราฟ;
glFlush;
จบ;
ขั้นตอน TfrmMain.MyDraw;
var
qObj:GLUQuadricObj;
เริ่ม
glPushMatrix;
glClear(GL_COLOR_BUFFER_BIT หรือ GL_DEPTH_BUFFER_BIT);
glColor3f(1,0,0);
glRotated(0.5,0.0,1.0,0.0);
glRotated(-ละติจูด,1.0,0.0,0.0);
glrotated(ลองจิจูด,0.0,0.0,1.0);
qObj:=gluNewQuadric;
gluQuadricDrawStyle(qObj,GLU_LINE);
กลูสเฟียร์(qObj,0.5,20,20);
SwapBuffers(ผ้าใบ.จัดการ);
จบ;
{ขั้นตอน TfrmMain.FormResize (ผู้ส่ง: TObject);
var
nช่วง: GLfloat;
เริ่ม
nช่วง:=50.0;
w:=clientWidth;
h:=clientHeight;
ถ้า h=0 แล้ว
ชั่วโมง:=1;
glViewPort(0,0,w,h);
glMatrixMode(GL_โครงการ);
glLoadIdentity;
ถ้า w<=h แล้ว
glOrtho(-nRange,nRange,-nRange*h/w,nRange*h/w,
-nRange, nRange)
อื่น
glOrtho(-nRange*h/w,nRange*h/w,-nRange,nRange,
-nRange,nRange);
glMatrixMode(GL_MODELVIEW);
glLoadidentity;
ทาสีใหม่;
จบ;
-
ขั้นตอน TfrmMain.FormKeyDown (ผู้ส่ง: TObject; คีย์ var: Word;
กะ: TShiftState);
เริ่ม
ถ้า Key=VK_ESCAPE แล้ว
ปิด;
ถ้า Key=VK_UP แล้ว
glRotatef(-5,1.0,0.0,0.0);
ถ้า Key=VK_DOWN แล้ว
glRotatef(5,1.0,0.0,0.0);
ถ้า Key=VK_LEFT แล้ว
glRotatef(-5,0.0,1.0,0.0);
ถ้า Key=VK_RIGHT แล้ว
glRotatef(5.0,0.0,1.0,0.0);
ทาสีใหม่;
จบ;
ขั้นตอน TfrmMain.FormResize (ผู้ส่ง: TObject);
เริ่ม
glMatrixMode(GL_โครงการ);
glLoadIdentity;
glFrustum(-1.0,1.0,-1.0,1.0,3.0,7.0);
glViewPort(0,0,ความกว้างของไคลเอ็นต์,ความสูงของไคลเอ็นต์);
ทาสีใหม่;
ไม่ถูกต้อง;
จบ;
ขั้นตอน TfrmMain.InitializeGL (ความกว้าง var: GLsizei; ความสูง: GLsizei);
var
maxObjectSize, อัตราส่วน: GLfloat;
near_plane:GLดับเบิ้ล;
เริ่ม
glClearindex(0);
glClearDepth(1.0);
glEnable(GL_DEPTH_TEST);
glMatrixMode(GL_โครงการ);
ด้าน:=1.0;
gluPerspective(45.0,ด้าน,3.0,7.0);
glmatrixMode(GL_MODELVIEW);
near_plane:=0.3;
ขนาดวัตถุสูงสุด:=0.3;
รัศมี:=near_plane+maxObjectSize/2.0;
ละติจูด:=0.3;
ลองจิจูด:=0.6;
จบ;
ขั้นตอน TfrmMain.Timer1Timer (ผู้ส่ง: TObject);
เริ่ม
timer1.Enabled:=false;
มายดราฟ;
ผลผลิต;
Timer1.Enabled:=true;
จบ;
ขั้นตอน TfrmMain.FormClose (ผู้ส่ง: TObject; var Action: TCloseAction);
เริ่ม
timer1.Enabled:=false;
ถ้า hrc<>null แล้ว
wglDeleteContext (เหล็กแผ่นรีดร้อน);
จบ;
จบ.
7. แสงและพื้นผิวของ OPENGL
สิ่งเหล่านี้ล้วนหมายถึงการเพิ่มประสิทธิภาพเอฟเฟกต์สามมิติและเอฟเฟกต์สี การจัดแสงสามารถเพิ่มความสว่างและเอฟเฟกต์สามมิติของกราฟิก และพื้นผิวสามารถทำให้กราฟิกสมจริงยิ่งขึ้น การใช้แสงสามารถแสดงลักษณะของวัตถุในลักษณะที่แข็งแกร่งได้ และพื้นผิวสามารถทำให้วัตถุแสดงลักษณะที่หลากหลายได้
1 กระบวนการและการประยุกต์ใช้แสงสว่างและแหล่งกำเนิดแสง
ขั้นตอน glIndex ทำให้สีในตารางดัชนีสีเป็นสีปัจจุบัน
ขั้นตอน glIndexd(c:GLdouble);
ขั้นตอน glIndexf(c:GLdouble);
ขั้นตอน glIndexi (c: GLdouble);
ขั้นตอน glIndexs (c: GLdouble);
พารามิเตอร์ C คือค่าดัชนี ถ้าใช้ขั้นตอน glIndex สมาชิก iPixelType ในโครงสร้าง TPiexlFormatDescriptor จะถูกตั้งค่าเป็น PFD_TYPE_COLORINDEX
ขั้นตอน B glShadeModel
กระบวนการ glShadeModel ตั้งค่าโหมดการเติม ค่า: GL_SMOOTH
ขั้นตอน glShadeModel (โหมด: GLenum);
หมายเหตุ: สองกระบวนการข้างต้นสามารถใช้ได้เฉพาะภายนอก glBegin....glEnd
ขั้นตอน C glLight กำหนดแหล่งกำเนิดแสง
ขั้นตอน glLightf (แสง: GLenum, pname: GLenum, พารามิเตอร์: GLfloat);
ขั้นตอน glLighti (แสง: GLenum, pname: GLenum, พารามิเตอร์: GLfloat);
แสงพารามิเตอร์กำหนดแหล่งกำเนิดแสง ค่าของมันสามารถเป็น: GL_LIGHT0....GL_LIGHTN ค่า N น้อยกว่า GL_MAX_LIGHT
pname พารามิเตอร์ระบุพารามิเตอร์แหล่งกำเนิดแสง:
ความเข้มขององค์ประกอบ GL_AMBIENT ของแสงโดยรอบ
GL_DIFFUSE ความเข้มขององค์ประกอบแสงที่กระเจิง
ความเข้มขององค์ประกอบ GL_SPECULAR ของแสงสะท้อน
GL_POSITION ตำแหน่งแหล่งกำเนิดแสง
GL_SPOT_DIRECTION ทิศทางโฟกัสของแหล่งกำเนิดแสง
GL_SPOT_EXPONENT ดัชนีแหล่งกำเนิดแสง
GL_SPOT_CUTOFF ทิศทางของแหล่งกำเนิดแสง
GL_CONSTANT_ATTENUATION ปัจจัยการสลายตัวคงที่ของแสง
GL_LINEAR_ATTENUATION ปัจจัยการลดทอนแสงทุติยภูมิ
เปิดใช้งานและปิดแหล่งกำเนิดแสงโดยใช้ขั้นตอน glEnable() และ glDisable()
glEnable(GL_LIGHTING); //เปิดใช้งานแหล่งกำเนิดแสง
glDisable(GL_LIGHTING); //ปิดแหล่งกำเนิดแสง
glEnable(GL_LIGHT0); //เปิดใช้งานแหล่งกำเนิดแสงที่ 0
glDisable(GL_LIGHT0); //ปิดแหล่งกำเนิดแสงที่ 0
ตัวอย่างการตั้งค่าแหล่งกำเนิดแสง:
var
ทิศทาง:อาร์เรย์[1..4] ของ GLfloat:={0.0,1.0,0.0,0.0};
glLightfv(GL_LIGHT0,GL_SPOT_CUTOFF,60);
glLightfv(GL_LIGHT0,GL_SPOT_DIRECTION,ทิศทาง);
2 วัสดุและแบบจำลองแสง
ขั้นตอน glMaterial ตั้งค่าพารามิเตอร์วัสดุ
ขั้นตอน glMaterialf (ใบหน้า: GLenum, pname: GLenum, พารามิเตอร์: GLfloat);
ขั้นตอน glMaterali (ใบหน้า: GLenum, pname: GLenum, พารามิเตอร์: GLfloat);
ขั้นตอน glMaterialfv (ใบหน้า: GLenum, pname: GLenum, พารามิเตอร์: GLfloat);
ขั้นตอน glMaterialiv (ใบหน้า: GLenum, pname: GLenum, พารามิเตอร์: GLfloat);
ใบหน้าพารามิเตอร์ระบุพื้นผิวของวัตถุและค่าของมันคือ: GL_FRONT, GL_BACK, GL_FRONT_BACK
pname,param ไม่ได้ถูกนำมาใช้ในเอกสารนี้
กระบวนการ B glLightModel
ขั้นตอน glLightModelf (pname: GLenum, พารามิเตอร์: GLfloat);
pname พารามิเตอร์คือพารามิเตอร์โมเดลแหล่งกำเนิดแสง ซึ่งสามารถรับค่า GL_LIGHT_MODEL_AMBIENT
GL_LIGHT_MODEL_LOCAL_VIEWER,GL_LIGHT_MODEL_TWO_SIDE
รหัสตัวอย่าง:
ขั้นตอน TfrmMain.SetLighting;
var
MaterialAmbient: อาร์เรย์ [1..4] ของ GLfloat;
MaterialDiffuse:Array[1..4] ของ GLfloat;
MaterialSpecular:อาร์เรย์[1..4] ของ GLfloat;
AmbientLightPosition:อาร์เรย์[1..4] ของ GLfloat;
LightAmbient: อาร์เรย์ [1..4] ของ GLfloat;
วัสดุความมันเงา:GLfloat;
เริ่ม
วัสดุโดยรอบ[1]:=0.5;
วัสดุโดยรอบ[2]:=0.8;
วัสดุโดยรอบ[1]:=0.2;
วัสดุโดยรอบ[1]:=1.0;
วัสดุกระจาย[1]:=0.4;
วัสดุกระจาย[2]:=0.8;
วัสดุกระจาย[3]:=0.1;
วัสดุกระจาย[4]:=1.0;
วัสดุเฉพาะ[1]:=1.0;
วัสดุสเปค[2]:=0.5;
วัสดุสเปค[3]:=0.1;
วัสดุเฉพาะ[4]:=1.0;
วัสดุความเงา:=50.0;
ตำแหน่งแสงโดยรอบ[1]:=0.5;
ตำแหน่งแสงโดยรอบ[2]:=1.0;
ตำแหน่งแสงโดยรอบ[3]:=1.0;
ตำแหน่งแสงโดยรอบ[4]:=0.0;
แสงโดยรอบ[1]:=0.5;
แสงโดยรอบ[2]:=0.2;
แสงโดยรอบ[3]:=0.8;
แสงโดยรอบ[4]:=1.0;
glMaterialfv(GL_FRONT,GL_AMBIENT,@MaterialAmbient);
glMaterialfv(GL_FRONT,GL_DIFFUSE,@MaterialDiffuse);
glMaterialfv(GL_FRONT,GL_SPECULAR,@วัสดุสเปค);
glMaterialfv(GL_FRONT,GL_SHIINESS,@วัสดุความเงางาม);
glLightfv(GL_LIGHT0,GL_POSITION,@AmbientLightPosition);
glLightModelfv(GL_LIGHT_MODEL_AMBIENT,@LightAmbient);
glEnable(GL_LIGHTING);
glเปิดใช้งาน(GL_LIGHT0);
GLShadeModel(GL_SMOOTH);
จบ;
3 การใช้พื้นผิว
glTexImage1D กำหนดการแมปพื้นผิวหนึ่งมิติ
ขั้นตอน glTexImage1D (เป้าหมาย: GLenum, ระดับ: GLint, ส่วนประกอบ: GLint, ความกว้าง: GLsizei,
เส้นขอบ:GLint,รูปแบบ:GLenum,ประเภท:GLenum,พิกเซล:GLvoid);
ค่าตัวกำหนดเป้าหมายพารามิเตอร์คือ GL_TEXTURE_1D ซึ่งหมายถึงการแมปพื้นผิว ระดับคือระดับของภาพพื้นผิวที่มีความละเอียดหลายระดับ ความกว้างคือความกว้างของพื้นผิว ค่าคือ 2n และค่าของ n คือ 32, 64, 129 ฯลฯ Border คือขอบเขตของพื้นผิว และค่าของมันคือ 0 หรือ 1 Pixel คือตำแหน่งของพื้นผิวในหน่วยความจำ Component ระบุการผสมและการปรับ RGBA:
1เลือกส่วนผสม B
2เลือกส่วนผสม B และ A
3เลือกส่วนผสม R, G, B
4เลือกส่วนผสม R,G,B,A
B glTexImage2D กำหนดการแมปพื้นผิวสองมิติ
ขั้นตอน glTexImage2D (เป้าหมาย: GLenum, ระดับ: GLint, ส่วนประกอบ: GLint, ความกว้าง: GLsizei,
เส้นขอบ:GLint,รูปแบบ:GLenum,ประเภท:GLenum,พิกเซล:GLvoid);
หากเป้าหมายพารามิเตอร์คือ GL_TEXTURE_2D ความหมายคือการแมปพื้นผิวสองมิติ ความสูงคือความสูงของพื้นผิว และพารามิเตอร์อื่นๆ ในฟังก์ชันจะเหมือนกับ glTexImage1D ค่าของพารามิเตอร์ส่วนประกอบจะเหมือนกับด้านบน
รหัสตัวอย่าง:
ขั้นตอน TfrmMain.SetTextures;
var
บิต: อาร์เรย์ [1..64,1..64,1..64] ของ GLubyte;
bmp:TBitmap;
i,j:จำนวนเต็ม;
เริ่ม
bmp:=TBitmap.สร้าง;
bmp.LoadFromFile('d:/dsoft/1119/01/logon.bmp');
สำหรับ i:=1 ถึง 64 ทำ
สำหรับ j:=1 ถึง 64 ทำ
เริ่ม
บิต[i,j,1]:=GLbyte(GetRValue(bmp.Canvas.Pixels[i,j]));
บิต[i,j,2]:=GLbyte(GetRValue(bmp.Canvas.Pixels[i,j]));
บิต[i,j,3]:=GLbyte(GetRValue(bmp.Canvas.Pixels[i,j]));
บิต[i,j,4]:=255;
จบ;
{0 หมายถึงระดับการแรเงาสีเดียว GL_RGBA หมายถึงค่าผสม
64X64 หมายถึงความสูงและความกว้างของพื้นผิว 0 หมายถึงไม่มีเส้นขอบ
gl_rgba หมายถึงประเภทพื้นผิว gl_unsigned_type แสดงถึงประเภทข้อมูลที่อยู่วัตถุ @generation}
glteximage2d (gl_texture_2d, 0, gl_rgba, 64,64,0, gl_rgba,
gl_unsigned_byte,@bits);
glenable (gl_texture_2d);
จบ;
C โพรซีเดอร์ C GLTEXPARAMETER ตั้งค่าพารามิเตอร์พื้นผิว
ขั้นตอน gltexparameterf (เป้าหมาย: glenum, pname: glenum, param: glfloat);
ขั้นตอน gltexparameteri (เป้าหมาย: glenum, pname: glenum, param: glfloat);
เป้าหมายพารามิเตอร์แสดงถึง gl_texture_1d หรือ gl_texture_2d และพารามิเตอร์คือค่าพื้นผิว
ฟังก์ชัน d gltexenv ตั้งค่าพารามิเตอร์สภาพแวดล้อมของพื้นผิว
ฟังก์ชั่น gltexenvf (เป้าหมาย: glenum, pname: glenum, param: glfloat);
ฟังก์ชั่น gltexenvi (เป้าหมาย: glenum, pname: glenum, param: glfloat);
เป้าหมายพารามิเตอร์คือ gl_texture_env
พารามิเตอร์ pname คือค่าพารามิเตอร์พื้นผิวและค่าคือ gl_texture_env_mode
พารามิเตอร์พารามิเตอร์คือค่าสภาพแวดล้อมและค่าของมันคือ gl_modulate, gl_decal และ gl_blend
รหัสตัวอย่างสำหรับโปรแกรมนี้:
หน่วย mainfrm;
อินเตอร์เฟซ
การใช้งาน
Windows, ข้อความ, SysUtils, ตัวแปร, คลาส, กราฟิก, การควบคุม, แบบฟอร์ม,
กล่องโต้ตอบ, opengl, extctrls;
พิมพ์
TfrmMain = คลาส (TForm)
ตัวจับเวลา 1: TTimer;
ขั้นตอน FormCreate (ผู้ส่ง: TObject);
ขั้นตอน FormDestroy (ผู้ส่ง: TObject);
รูปแบบขั้นตอน (ผู้ส่ง: tobject);
procedure formkeydown (ผู้ส่ง: tobject; var key: word;
กะ: TShiftState);
ขั้นตอนการกำหนดรูปแบบ (ผู้ส่ง: tobject);
ขั้นตอน Timer1Timer (ผู้ส่ง: TObject);
ขั้นตอน FormClose (ผู้ส่ง: TObject; var Action: TCloseAction);
ส่วนตัว
{ประกาศส่วนตัว}
HRC: HGLRC;
W, H: จำนวนเต็ม;
ละติจูดลองจิจูด: glfloat;
รัศมี: gldouble;
สาธารณะ
{ประกาศสาธารณะ}
ขั้นตอนการกำหนดค่า;
ขั้นตอนการตั้งค่า;
ขั้นตอน myDraw;
โพรซีเดอร์ Initializegl (ความกว้าง var: glsizei; ความสูง: glsizei);
จบ;
var
frmmain: tfrmmain;
การดำเนินการ
{$R *.dfm}
ขั้นตอน tfrmmain.formcreate (ผู้ส่ง: tobject);
var
PFD: tpixelformatdescriptor;
Pixelformat: จำนวนเต็ม;
เริ่ม
Controlstyle: = controlstyle+[csopaque];
Fillchar (pfd, sizeof (pfd), 0);
ด้วย PFD DO
เริ่ม
nsize: = sizeof (tpixelformatdescriptor);
nversion: = 1;
dwflags: = pfd_draw_to_window หรือ
pfd_support_opengl หรือ pfd_doublebuffer;
ipixeltype: = pfd_type_rgba;
ccolorbits: = 24;
CdEpthbits: = 32;
ilayerType: = pfd_main_plane;
จบ;
PixelFormat: = ChoosePixelFormat (canvas.handle,@pfd);
setPixElformat (canvas.handle, pixelformat,@pfd);
HRC: = wglCreateContext (canvas.handle);
w: = clientRect.right;
H: = clientRect.bottom;
Initializegl (W, H);
จบ;
ขั้นตอน tfrmmain.formdestroy (ผู้ส่ง: tobject);
เริ่ม
WGLDELETECONTEXT (HRC);
จบ;
ขั้นตอน tfrmmain.formpaint (ผู้ส่ง: tobject);
เริ่ม
wglMakecurrent (canvas.handle, hrc);
Glclearcolor (1,1,1,1);
glcolor3f (1,0,0);
glclear (gl_color_buffer_bit หรือ gl_depth_buffer_bit);
setTextures;
MyDraw;
setlighting;
glflush;
จบ;
ขั้นตอน tfrmmain.mydraw;
var
qobj: gluquadricobj;
เริ่ม
glpushmatrix;
glclear (gl_color_buffer_bit หรือ gl_depth_buffer_bit);
glcolor3f (1,0,0);
glrotated (0.5,0.0,1.0,0.0);
glrotated (-latitude, 1.0,0.0,0.0);
glrotated (ลองจิจูด, 0.0,0.0,1.0);
qobj: = glunewquadric;
gluquadricdrawstyle (qobj, glu_line);
Glusphere (QOBJ, 0.5,20,20);
swapbuffers (canvas.handle);
setlighting;
setTextures;
จบ;
{ขั้นตอน tfrmmain.formResize (ผู้ส่ง: tobject);
var
NRANGE: GLFLOAT;
เริ่ม
NRANGE: = 50.0;
w: = clientWidth;
H: = clientHeight;
ถ้า h = 0 แล้ว
H: = 1;
Glviewport (0,0, W, H);
glmatrixmode (gl_projection);
Glloadidentity;
ถ้า w <= h แล้ว
Glortho (-nrange, NRANGE, -NRANGE*H/W, NRANGE*H/W,
-Nrange, nrange)
อื่น
Glortho (-NRANGE*H/W, NRANGE*H/W, -NRANGE, NRANGE,
-nrange, nrange);
glmatrixmode (gl_modelview);
Glloadidentity;
ทาสีใหม่;
จบ;
-
โพรซีเดอร์ tfrmmain.formkeydown (ผู้ส่ง: tobject; var key: word;
กะ: TShiftState);
เริ่ม
ถ้า key = vk_escape แล้ว
ปิด;
ถ้า key = vk_up แล้ว
glrotatef (-5,1.0,0.0.0,0.0);
ถ้า key = vk_down แล้ว
glrotatef (5,1.0,0.0.0,0.0);
ถ้า key = vk_left แล้ว
glrotatef (-5,0.0,1.0,0.0);
ถ้า key = vk_right แล้ว
glrotatef (5.0,0.0,1.0,0.0);
ทาสีใหม่;
จบ;
ขั้นตอน tfrmmain.formresize (ผู้ส่ง: tobject);
เริ่ม
glmatrixmode (gl_projection);
Glloadidentity;
glfrustum (-1.0,1.0, -1.0,1.0,3.0,7.0);
glviewport (0,0, clientWidth, clientHeight);
ทาสีใหม่;
ไม่ถูกต้อง;
จบ;
ขั้นตอน tfrmmain.initializegl (ความกว้าง var: glsizei; ความสูง: glsizei);
var
MaxObjectSize, แง่มุม: glfloat;
ใกล้ _plane: gldouble;
เริ่ม
Glclearindex (0);
Glcleardepth (1.0);
glenable (gl_depth_test);
glmatrixmode (gl_projection);
แง่มุม: = 1.0;
gluperspective (45.0, แง่มุม, 3.0,7.0);
glmatrixmode (gl_modelview);
ใกล้ _plane: = 0.3;
MaxObjectSize: = 0.3;
รัศมี: = ใกล้ _plane+maxobjectsize/2.0;
ละติจูด: = 0.3;
ลองจิจูด: = 0.6;
จบ;
ขั้นตอน tfrmmain.timer1timer (ผู้ส่ง: tobject);
เริ่ม
timer1.Enabled:=false;
MyDraw;
ผลผลิต;
timer1.enabled: = true;
จบ;
โพรซีเดอร์ tfrmmain.formclose (ผู้ส่ง: tobject; การกระทำ var: tcloseaction);
เริ่ม
timer1.Enabled:=false;
ถ้า hrc <> null แล้ว
WGLDELETECONTEXT (HRC);
จบ;
ขั้นตอน tfrmmain.setlighting;
var
Materialambient: Array [1..4] ของ Glfloat;
Materialdiffuse: Array [1..4] ของ Glfloat;
MaterialSpecular: อาร์เรย์ [1..4] ของ glfloat;
AmbientlightPosition: Array [1..4] ของ Glfloat;
Lightambient: Array [1..4] ของ Glfloat;
MaterialShininess: glfloat;
เริ่ม
materialambient [1]: = 0.5;
materialambient [2]: = 0.8;
materialambient [1]: = 0.2;
materialambient [1]: = 1.0;
Materialdiffuse [1]: = 0.4;
Materialdiffuse [2]: = 0.8;
Materialdiffuse [3]: = 0.1;
Materialdiffuse [4]: = 1.0;
MaterialSpecular [1]: = 1.0;
MaterialSpecular [2]: = 0.5;
MaterialSpecular [3]: = 0.1;
MaterialSpecular [4]: = 1.0;
MaterialShininess: = 50.0;
AmbientLightPosition [1]: = 0.5;
AmbientLightPosition [2]: = 1.0;
AmbientLightPosition [3]: = 1.0;
AmbientLightPosition [4]: = 0.0;
Lightambient [1]: = 0.5;
Lightambient [2]: = 0.2;
Lightambient [3]: = 0.8;
Lightambient [4]: = 1.0;
glmaterialfv (gl_front, gl_ambient,@materialambient);
glmaterialfv (gl_front, gl_diffuse,@materialdiffuse);
glmaterialfv (gl_front, gl_specular,@materialspecular);
glmaterialfv (gl_front, gl_shininess,@materialshininess);
gllightfv (gl_light0, gl_position,@ambientlightposition);
gllightmodelfv (gl_light_model_ambient,@lightambient);
glenable (gl_lighting);
glenable (gl_light0);
glshademodel (gl_smooth);
จบ;
ขั้นตอน tfrmmain.settextures;
var
บิต: อาร์เรย์ [1..64,1..64,1..64] ของ glubyte;
BMP: TBITMAP;
ฉัน, J: จำนวนเต็ม;
เริ่ม
bmp: = tbitmap.create;
bmp.loadfromfile ('d: /dsoft/1119/02/logon.bmp');
สำหรับ i: = 1 ถึง 64 ทำ
สำหรับ j: = 1 ถึง 64 ทำ
เริ่ม
บิต [i, j, 1]: = glbyte (getrvalue (bmp.canvas.pixels [i, j]));
บิต [i, j, 2]: = glbyte (getrvalue (bmp.canvas.pixels [i, j]));
บิต [i, j, 3]: = glbyte (getrvalue (bmp.canvas.pixels [i, j]));
บิต [i, j, 4]: = 255;
จบ;
glpixelstorei (gl_unpack_alignment, 4);
gltexparameteri (gl_texture_2d, gl_texture_wrap_s, gl_clamp);
gltexparameteri (gl_texture_2d, gl_texture_mag_filter, gl_nearest);
gltexparameteri (gl_texture_2d, gl_texture_min_filter, gl_nearest);
{0 แสดงถึงระดับการแรเงาสีเดียว gl_rgba แสดงถึงค่าผสม
64x64 แสดงถึงความสูงและความกว้างของพื้นผิว 0 หมายถึงไม่มีเส้นขอบ
gl_rgba หมายถึงประเภทพื้นผิว gl_unsigned_type แสดงถึงประเภทข้อมูลที่อยู่วัตถุ @generation}
glteximage2d (gl_texture_2d, 0, gl_rgba, 64,64,0, gl_rgba,
gl_unsigned_byte,@bits);
glenable (gl_texture_2d);
gltexenvf (gl_texture_env, gl_texture_env_mode, gl_decal);
จบ;
จบ.