Tải bản đầy đủ (.pdf) (45 trang)

Các vấn đề hiện đại CNPM – OpenGL ES 2.0

Bạn đang xem bản rút gọn của tài liệu. Xem và tải ngay bản đầy đủ của tài liệu tại đây (3.46 MB, 45 trang )

ĐẠI HỌC QUỐC GIA HÀ NỘI
TRƯỜNG ĐẠI HỌC CÔNG NGHỆ


BÁO CÁO

MÔN: CÁC VẤN ĐỀ HIỆN ĐẠI
CÔNG NGHỆ PHẦN MỀM

NGÀNH: CÔNG NGHỆ THÔNG TIN


ĐỀ TÀI: TÌM HIỂU OPENGL ES 2.0



GV đánh giá: TS.Võ Đình
Hiếu

Sinh viên: Lê Thái Hòa

Nhóm:


Hà Nội, tháng 12 năm 2013
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
1


Mục Lục
I. GIỚI THIỆU ĐỀ TÀI 3


1. Nội dung đề tài 3
2. Lý do chọn đề tài 3
II.PHÂN TÍCH ĐỀ TÀI 5
Phần 1 - Các khái niệm cơ bản của thế giới 3D và OpenGL 5
1. Đối thủ lớn nhất của OpenGL 6
2. OpenGL làm việc như thế nào? 6
3. Logic của OpenGL 7
3.1 Primitives 7
3.2 Bộ đệm (Buffers) 8
3.3 Rasterize 8
4. Đường ống dẫn của OpenGL 9
4.1 Vertex Shader 9
4.2 Fragment Shader 9
Phần 2: Đi xâu vào OpenGL ES 2.0 10
1. Các kiểu dữ liệu OpenGL và đường ống dẫn lập trình 10
2. Primitives 12
3. Bộ đệm (Buffers) 14
3.1 Khung đệm (Frame Buffers) 14
3.2 Làm đệm (Render Buffers) 15
4. Kết cấu (Texture) 19
5. Rasterize 24
6. Shaders 28
7. Rendering 38
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
2

7.1. Pre-Render 38
7.2. Bản vẽ (Drawing) 39
7.3. Render 41
Phần 3: Đồ họa 2D với OpenGL ES 2.0 41

TÀI LIỆU THAM KHẢO 43
Books 43






Các vấn đề hiện đại CNPM – OpenGL ES 2.0
3

I. GIỚI THIỆU ĐỀ TÀI
1. Nội dung đề tài
Tên đề tài: Nghiên cứu về OpenGL ES 2.
Đề tài được triển khai qua 3 phần
 Phần 1: Các khái niệm cơ bản của thế giới 3D và OpenGL
 Phần 2: Đi xâu vào OpenGL ES 2.0
 Phần 3: Đồ họa 2D với OpenGL ES 2.0
2. Lý do chọn đề tài
Game là một lĩnh vực giải trí hiện đang được coi là HOT cho tất cả các nền
tảng hiện nay, đặc biệt nói đến là smartphone. Khi nói tới giải trí, chúng ta thường
nghĩ tới game. Đôi khi game cũng được sử dụng như một công cụ giáo dục. Game
được phát triển cho nhiều thiết bị như PC, smartphone, các thiết bị cầm tay hoặc
chạy ngay trên chính trình duyệt web. Các nền tảng cho phép phát triển game có
thể kể đến là các hệ điều hành cho máy tính: Windows, Linux, Mac, ,hệ điều
hành smartphone: iOS, Android, WindowsPhone, Symbian, Bada, Game được
phát triển bởi hầu hết các ngôn ngữ lập trình tùy thuộc độ mềm dẻo và yêu cầu của
game. Ngoài ra trong cuộc sống cần sử dụng tới rất nhiều ứng dụng như CAD,
thực tế ảo, mô phỏng khoa học, mô phỏng thông tin
Khi nhắc tới game và các ứng dụng kể trên chúng ta nghĩ ngay tới đồ họa của

nó như thế nào? Vậy tại sao lại cần đồ họa và cái gì làm nên đồ họa? OpenGL sẽ
trả lời câu hỏi này cho chúng ta. OpenGL (tên tiếng anh Open Graphics Library) là
một tiêu chuẩn kỹ thuật đồ họa có mục đích định ra một giao diện lập trình ứng
dụng(tiếng anh: API) đồ họa 3 chiều hoặc 2 chiều. OpenGL còn có đối thủ cạnh
tranh là DirectX của Microsoft.
OpenGL ES là một sản phẩm miễn phí bao gồm các hàm API cho phép tạo
các ứng dụng 2D, 3D trên các ứng dụng nhúng – bao gồm các thiết bị cầm tay. Nó
được định nghĩa như là một tập con của OpenGL, tạo ra tính linh hoạt, mạnh mẽ
trên giao diện cấp thấp giữa phần mềm và đồ họa. OpenGL ES được phát triển
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
4

nhằm mục đích tạo đồ họa cho nền tảng smartphone vì một số hàm trong OpenGL
gốc không còn thích hợp với cấu hình phần cứng của các dòng smartphone.
OpenGL ES2.0 là phiên bản 2.0 của OpenGL ES. Được cải tiến so hơn so với
phiên bản trước là OpenGL ES1.0 và OpenGL ES1.1.
Smartphone hiện đang là xu thế công nghệ hiện nay về tính tiện dụng. Vì vậy
việc phát triển đồ họa trên smartphone là rất cần thiết. Nói tới đây chúng ta cũng
dễ hiểu được tầm quan trọng của OpenGL ES trong công nghiệp đồ họa hiện nay.
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
5


II.PHÂN TÍCH ĐỀ TÀI
Phần 1 - Các khái niệm cơ bản của thế giới 3D và OpenGL
OpenGL có nghĩa là mở cửa thư viện đồ họa và nó được sử dụng rất nhiều hiện
nay trong ngôn ngữ máy tính. OpenGL là điểm gần nhất giữa CPU (mà các nhà
phát triển chạy các ứng dụng dựa trên một ngôn ngữ) và GPU (bộ xử lý đồ họa của
tồn tại trong tất cả các card đồ họa). Vì vậy, OpenGL cần phải được hỗ trợ bởi các
nhà cung cấp của card đồ họa (như NVIDIA) và được thực hiện bởi các nhà cung

cấp của hệ điều hành (như Apple trong hệ điều hành MacOS và iOS) và cuối cùng
là cung cấp cho OpenGL, các nhà phát triển, một API thống nhất để làm việc. API
này là "ngôn ngữ miễn phí" (hoặc gần như miễn phí). Điều này là tuyệt vời, bởi vì
nếu bạn sử dụng C, C++, hoặc Objective-C, hoặc Perl, hoặc C #, hoặc JavaScript,
bất cứ nơi nào sử dụng, API sẽ luôn luôn được hỗ trợ tương đương, sẽ trình bày
các hành vi tương tự, các chức năng tương tự, với cùng lệnh! Để đối phó với API
OpenGL của các nhà phát triển.
Trước khi bắt đầu nói về OpenGL API tôi xin trình bày một chút kiến thức về
thế giới 3D, lịch sử 3D.



Khoảng 20 năm trước có 1 người tên là Silicon Graphics (SGI) đã làm 1 loạt
các thiết bị. Các thiết bị đó có thể thể hiện 1 ảnh ảo của thực tế trong thế giới hình
ảnh 2D. Thiết bị này còn thể hiện hình ảnh 3D, mô phỏng các nhìn và chiều sâu
của mắt người. Thiết bị này gọi là IrisGL (Có lẽ thiết bị này bởi vì nó sẽ cố gắng
để mô phỏng mống mắt của mắt).
Vâng thiết bị trên là thư viện đồ họa vĩ đại đầu tiên. Nhưng nó biến mất rất
nhanh, bởi vì để thực hiện những gì mà nó làm thì cần phải điều khiển nhiều thứ
trong CPU như card đồ họa, hệ thống Windows, ngôn ngữ Nó là quá nhiều để 1
công ty quản lý. Vì vậy SGI để lại một số thứ như "Tạo ra card đồ họa", "Quản lý
windows." cho các công ty khác và SGI tập chung vào phần quan trọng nhất của
thư viện đồ họa. Trong năm 1992 khởi chạy lần đầu tiên.
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
6

Trong năm 1995 Microsoft phát hành Direct3D, đối thủ cạnh tranh của
OpenGL. Và năm 1997 Opengl 1.1 ra đời. Nhưng thực sự thú vì là năm 2004 với
sự ra đời của OpengL 2.0 với nhiều thay đổi lớn, Shaders, Programable Pipeline.
Vào năm 2007 chúng ta gặp được Opengl es2.0 nó mang đến cho chúng ta

sức mạnh thực sự của Shaders, Programable pipeline và hệ thống nhúng
(Embedded Systems).
Chúng ta có thể nhìn thấy logo của OpenGL (hoặc OpenGL ES) trong nhiều
trò chơi, các ứng dụng 3D, các ứng dụng 2D và rất nhiều phần mềm đồ họa (đặc
biệt trong các phần mềm 3D). OpenGL ES được sử dụng bởi PlayStation,
Android, Nintendo 3DS, Nokia, Samsung, Symbian và dĩ nhiên bởi Apple với hệ
điều hành MacOS và iOS.
1. Đối thủ lớn nhất của OpenGL
Opengl ra đời 1992, tại thời điểm đó Microsoft (MS) có window 3.1. MS tin
rằng không có gì được tạo ra, mọi thứ được sao chép. MS cố gắng sao chép tất cả
của Opengl và họ có Direct3D và giới thiệt nó vào năm 1995 trên Windows 95.
Một năm sau đó 1996. MS giới thiệu Direct3D là 1 bản sao đen của Opengl,
ưu điểm lại là MS thống trị thị trường thông tin trong nhiều năm liền, và Direct3D
đã có được lợi thế và nó lây lan như là bệnh dịch của máy tính. và sau đố MS cung
cấp các hệ điều hành cho Mobile và các trò chơi, tất nhiên là đi cùng với
Direct3D.
Ngày nay Direct3D tương tự như Opengl. Có HLSL, cũng có programable
pipeline, và fixed pipeline, và thậm chí các tên Hàm cũng tương tự. Nhưng sự
khác biệt rất lớn là OpengL là mã nguồn mở, còn Direct3D thì không. Opengl
dành cho mọi hệ điều hành, trong khi Direct chỉ WinDows.
2. OpenGL làm việc như thế nào?
Sâu vào cốt lõi của OpenGL các tính toán được thực hiện trực tiếp trong các
GPU sử dụng tăng tốc phần cứng đến các điểm nổi.
CPU (Central Processing Unit) là bộ xử lý của một máy tính hoặc thiết
bị. GPU (Graphics Processing Unit) là card đồ họa của một máy tính hoặc thiết
bị. Card đồ họa đi kèm để giảm bớt cuộc sống của bộ xử lý vì nó có thể làm cho
rất nhiều tính toán để đối phó với hình ảnh trước khi mặt nội dung ra màn hình.
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
7


Vì vậy, trong sâu thẳm, những gì OpenGL làm là để cho tất cả các tính toán
khối lượng cho GPU, thay vì để tính toán tất cả trong CPU. GPU nhanh hơn nhiều
để đối phó với số point nổi hơn CPU. Đây là lý do cơ bản để một trò chơi 3D chạy
nhanh hơn với card đồ họa tốt hơn. Điều này thậm chí còn có lý do vì phần mềm
chuyên nghiệp 3D cung cấp cho bạn một tùy chọn để làm việc với "phần mềm của
Render" (xử lý CPU) hoặc "Card đồ họa của Render" (xử lý của CPU). Một số
phần mềm cũng cung cấp một tùy chọn "OpenGL". Lựa chọn đó là xử lý của
GPU! Nhưng OpenGL không hoàn toàn làm việc trong GPU
Chỉ cần một xử lý hình ảnh cứng và vài thứ khác. OpenGL cho chúng ta rất nhiều
tính năng để lưu trữ hình ảnh, dữ liệu và thông tin trong một định dạng được tối ưu
hóa. Những dữ liệu được tối ưu hóa sẽ được xử lý sau trực tiếp bởi GPU.
Nếu phần cứng (card đồ họa) không hỗ trợ OpenGL, chúng ta không thể sử
dụng nó. Phiên bản mới OpenGL thường cần các tính năng GPU mới.
Trong thực tế, tất cả các chip card đồ họa ngày nay có thực hiện với OpenGL. Vì
vậy, bạn có thể sử dụng OpenGL trong nhiều ngôn ngữ và các thiết bị. Ngay cả
trong Microsoft Windows.

3. Logic của OpenGL
OpenGL là một thư viện đồ họa rất ngắn gọn và tập trung.
Logic OpenGL gồm:
 Primitives
 Buffers
 Rasterize

3.1 Primitives
Primitives của OpenGL được giới hạn trong 3 loại đối tượng:
 Về một điểm trong không gian 3D (x, y, z)
 Về Dòng 3D trong không gian (tạo bởi hai điểm 3D)
 Về một Tam giác 3D trong không gian (tạo bởi ba điểm 3D)
Một điểm 3D có thể được sử dụng như một hạt trong không gian.

Một dòng 3D luôn luôn là một dòng đơn và có thể được sử dụng như một vector
3D.
Một Tam giác 3D có thể là một khuôn mặt của một lưới trong đó có hàng ngàn, có
lẽ hàng triệu mặt.
Một số phiên bản OpenGL cũng hỗ trợ Quads (tứ). Nhưng như OpenGL ES đã
được thực hiện để đạt được hiệu suất tối đa, Quads không được hỗ trợ, tất cả được
quy về tam giác.
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
8



3.2 Bộ đệm (Buffers)
Bây giờ hãy nói về bộ đệm. Nói cách đơn giản, bộ đệm là một tối ưu hóa lưu
trữ tạm thời đối với rất nhiều chất liệu
OpenGL làm việc với 3 loại bộ đệm:
 Khung đệm
 Làm đệm
 Đệm đối tượng
Khung đệm là trừu tượng nhất của ba yếu tố. Khi bạn thực hiện một của
OpenGL làm cho bạn có thể gửi hình ảnh cuối cùng trực tiếp đến màn hình của
thiết bị hoặc đến một khung đệm. OpenGL vẽ lại các hình ảnh về các đối tượng
3D, về độ sâu của các đối tượng trong không gian, giao điểm của các đối tượng và
về phần nhìn thấy được của các đối tượng. Vì vậy, khung đệm giống như một bộ
sưu tập các hình ảnh. Tất cả các lưu trữ như là một mảng nhị phân của thông tin
của điểm ảnh.
Làm đệm là một lưu trữ tạm thời của một hình ảnh duy nhất. Có thể thấy rõ
hơn rằng một khung đệm là một bộ sưu tập của Render đệm. Tồn tại vài loại
Render đệm: Màu sắc, độ sâu và Stencil.
Đệm đối tượng (Object Buffers) là một lưu trữ mà OpenGL gọi là "server-

side" (hoặc không gian địa chỉ của máy chủ). Các đệm đối tượng cũng là một lưu
trữ tạm thời, nhưng không vì thế tạm thời như những người khác. Một đối tượng
đệm có thể kéo dài suốt việc thực hiện ứng dụng. Đệm đối tượng có thể chứa
thông tin về các đối tượng 3D của bạn trong một định dạng được tối ưu
hóa. Những thông tin có thể được của hai loại: cấu trúc hoặc chỉ số.
Cấu trúc là mảng mô tả đối tượng 3D của bạn, giống như một mảng của đỉnh,
một loạt các tọa độ kết cấu hoặc một mảng của bất cứ điều gì bạn muốn. Các chỉ
số có nhiều chi tiết cụ thể. Mảng của các chỉ số được sử dụng để cho biết bao
khuôn mặt của lưới của bạn sẽ được xây dựng dựa trên một mảng của cấu trúc.

3.3 Rasterize
Các rasterize là quá trình mà OpenGL có tất cả các thông tin về các đối tượng
3D (tất cả những tọa độ, đỉnh, toán học, ) để tạo ra một hình ảnh 2D. Hình ảnh
này sẽ bị một số thay đổi và sau đó nó sẽ được trình bày trên màn hình của thiết bị
(thường).
Nhưng bước cuối cùng này, là cầu nối giữa thông tin pixel và màn hình của
thiết bị, đó là trách nhiệm của nhà cung cấp.
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
9


4. Đường ống dẫn của OpenGL
Các đường ống dẫn lập trình là thư viện đồ họa ủy thác cho các nhà phát
triển, trách nhiệm của tất cả mọi thứ liên quan đến máy ảnh, ánh sáng, vật liệu và
các hiệu ứng. Và có thể làm việc với Shaders. Vì vậy, mỗi khi bạn nghe về "đường
ống dẫn lập trình" thì nghĩ tới Shaders!
Shaders là những mảnh nhỏ của mã, giống như các chương trình nhỏ, làm
việc trực tiếp trong các GPU để thực hiện tính toán phức tạp. Điều này có nghĩa
bất cứ điều gì, nó rất phức tạp được xử lý bởi CPU và quá nhiều phức tạp để thư
viện đồ họa tiếp tục quan tâm. Vì vậy, các đường ống dẫn lập trình chỉ là chúng ta

quản lý các làm việc của GPU.
Đường ống cố định là thư viện đồ họa quan tâm đến tất cả các loại của sự vật
và đưa cho chúng tôi một API để thiết lập Máy ảnh, vật liệu, ánh sáng và các hiệu
ứng.
Để tạo các bóng đổ, có thể sử dụng một ngôn ngữ tương tự như C, sử dụng
OpenGL ngôn ngữ Shader (GLSL). OpenGL ES sử dụng một phiên bản ít nghiêm
ngặt hơn được gọi là OpenGL ES Shader Ngôn ngữ (còn gọi là GLSL ES hoặc
Essl). Sự khác biệt là bạn có nhiều chức năng cố định và có thể viết các biến hơn
trong GLSL hơn trong GLSL ES, nhưng sintax là như nhau.
Các shaders làm việc theo cặp: Vertex Shader và Fragment Shader. Đường
ống dẫn lập trình OpenGL của sử dụng một Shader Vertex và một Fragment
Shader.

4.1 Vertex Shader
Vertex Shader, còn được gọi là VS hay VSH là một chương trình nhỏ mà sẽ
được thực hiện tại mỗi Vertex của một lưới.
Những gì Vertex Shader sẽ làm là xác định vị trí cuối cùng của một Vertex.
Vị trí và ống kính của một máy ảnh có thể can thiệp vào vị trí cuối cùng của một
đỉnh. Vertex Shader cũng chịu trách nhiệm chuẩn bị và đầu ra một số biến vào
Fragment Shader. Trong OpenGL chúng ta có thể định nghĩa biến cho Vertex
Shader, nhưng chưa tính đến Fragment Shader. Bởi vì đó, các biến Fragment phải
đi qua Vertex Shader.

4.2 Fragment Shader
Bên trong Fragment Shader làm việc với tất cả mọi thứ liên quan đến "bề mặt
lưới, như nguyên vật liệu, hiệu ứng, bóng và hiệu ứng ánh sáng, phản xạ, khúc xạ,
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
10

kết cấu và các loại khác của hiệu ứng. Kết quả cuối cùng để các Fragment Shader

là một màu của điểm ảnh trong các định dạng RGBA.
Về cách VSH và FSH làm việc với nhau. Nó bắt buộc một Vertex Shader để
làm việc với một Fragment Shader, không nhiều thì ít, phải được chính xác 1-1.

Phần 2: Đi xâu vào OpenGL ES 2.0
1. Các kiểu dữ liệu OpenGL và đường ống dẫn lập trình
OpenGL phục vụ đa nền tảng và phụ thuộc vào việc thực hiện các nhà cung
cấp, nhiều kiểu dữ liệu có thể thay đổi từ một ngôn ngữ lập trình khác. Ví dụ, một
float trong C++ có thể đại diện cho 32 bit, nhưng trong JavaScript một float có thể
là chỉ 16 bit. Để tránh những loại xung đột, OpenGL luôn luôn làm việc với các
kiểu dữ liệu riêng của nó. Kiểu dữ liệu của OpenGL có tiền tố "GL",
như GLfloat hoặc GLint . Dưới đây là một danh sách đầy đủ các kiểu dữ liệu của
OpenGL:
OPENGL’S
DATA TYPE
SAME AS C DESCRIPTION
GLboolean
(1 bits) unsigned char 0 to 1
GLbyte
(8 bits) char -128 to 127
GLubyte
(8 bits) unsigned char 0 to 255
GLchar
(8 bits) char -128 to 127
GLshort
(16 bits) short -32,768 to 32,767
GLushort
(16 bits) unsigned short 0 to 65,353
GLint (32 bits) int
-2,147,483,648 to

2,147,483,647
GLuint
(32 bits) unsigned int 0 to 4,294,967,295
GLfixed (32 bits) int
-2,147,483,648 to
2,147,483,647
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
11

GLsizei (32 bits) int
-2,147,483,648 to
2,147,483,647
GLenum
(32 bits) unsigned int 0 to 4,294,967,295
GLdouble
(64
bits)
double
−9,223,372,036,854,775,808 to
9,223,372,036,854,775,807
GLbitfield
(32
bits)
unsigned int 0 to 4,294,967,295
GLfloat (32 bits) float
-2,147,483,648 to
2,147,483,647
GLclampx
(32
bits)

int
Integer clamped to the range 0
to 1
GLclampf
(32
bits)
float
Floating-point clamped to the
range 0 to 1
GLclampd
(64
bits)
double
Double clamped to the range 0
to 1
GLintptr

int pointer *
GLsizeiptr
int pointer *
GLvoid

void Can represent any data type
Một thông tin rất quan trọng về các loại dữ liệu là OpenGL ES không hỗ trợ 64
bit kiểu dữ liệu, bởi vì các hệ thống nhúng thường cần hiệu suất và một số thiết bị
không hỗ trợ bộ vi xử lý 64 bit. Bằng cách sử dụng các kiểu dữ liệu OpenGL, bạn
có thể dễ dàng và an toàn di chuyển ứng dụng OpenGL của bạn từ C ++
JavaScript với những thay đổi ít hơn.
Đây là một minh họa trực quan về các đường ống dẫn trong OpenGL:
Các vấn đề hiện đại CNPM – OpenGL ES 2.0

12


OpenGL đường ống dẫn lập trình.

2. Primitives
Khi nói rằng Primitives tức là nhắc tới điểm, đường và tam giác.
Tất cả đều sử dụng một hoặc nhiều điểm trong không gian được xây dựng,
còn được gọi là đỉnh.

Một đỉnh có 3 thông tin, vị trí X, Y và Z. Một điểm 3D được xây dựng bởi
một đỉnh, một dòng 3D được tạo bởi hai đỉnh và một hình tam giác được hình
thành bởi ba đỉnh. Như OpenGL luôn luôn muốn tăng hiệu suất, tất cả các thông
tin phải là một mảng chiều duy nhất, cụ thể hơn là một mảng các giá trị nổi. Như
thế này:
1
GLfloat Point3D = {1.0,0.0,0.5};
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
13

2
3
GLfloat line3D = {} 0.5,0.5,0.5,1.0,1.0,1.0;
GLfloat triangle3D = {} 0.0,0.0,0.0,0.5,1.0,0.0,1.0,0.0,0.0;
Các mảng float để OpenGL theo thứ tự, không phân biệt giữa các đỉnh,
OpenGL sẽ tự động hiểu được giá trị đầu tiên là giá trị X, thứ hai là giá trị Y và
thứ ba là giá trị Z. OpenGL sẽ lặp giải thích này ở tất cả các trình tự của 3 giá
trị. Tất cả những gì bạn cần là thông báo cho OpenGL nếu bạn muốn xây dựng
một điểm, một dòng hoặc một hình tam giác.
Các tọa độ trên sẽ xây dựng một cái gì đó như thế này:


Bây giờ, tất cả những gì chúng ta cần phải biết là 3D phức tạp nhất sẽ được
thực hiện với một loạt các hình tam giác. Gọi những hình tam giác của "khuôn
mặt". Vì vậy, tạo ra một khối lập phương 3D ta sử dụng một loạt các đỉnh.
1
2
3
4
5
6
7
8
9
10

/ / Mảng của đỉnh để một khối lập phương.
Cube3D GLfloat [] =
{
0.50, -0.50, -0.50, / / đỉnh 1
0.50, -0.50,0.50, / / đỉnh 2
-0.50, -0.50,0.50, / / đỉnh 3
-0.50, -0.50, -0.50, / / đỉnh 4
0.50,0.50, -0.50, / / đỉnh 5
-0.50,0.50, -0.50, / / đỉnh 6
0.50,0.50,0.50, / / đỉnh 7
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
14

11


12

-0.50,0.50,0.50 / / đỉnh 8
}
Thông thường mắt lưới có ba thông tin lớn: verticex, tọa độ kết cấu và pháp
tuyến. Đây được gọi là mảng của cấu trúc . Một ví dụ ngắn:
1
2
3
4
5
6
7
8
9
10

/ / Mảng của đỉnh để một khối lập phương.
Cube3D GLfloat [] =
{
0.50, -0.50, -0.50, / / đỉnh 1
0.00,0.33, / / kết cấu phối hợp 1
1.00,0.00,0.00 / / bình thường 1
0.50, -0.50,0.50, / / đỉnh 2
0.33,0.66, / / kết cấu phối hợp 2
0.00,1.00,0.00 / / bình thường 2

}

3. Bộ đệm (Buffers)

3.1 Khung đệm (Frame Buffers)
Một Frame Buffers là một lưu trữ tạm thời để cho đầu ra. Có thể chọn hiện nó
vào màn hình điện thoại hoặc lưu nó như một tập tin hình ảnh hoặc hoặc sử dụng
đầu ra như là một ảnh chụp
Đây là cặp chức năng liên quan đến bộ đệm khung hình:
GLvoid glGenFramebuffers (GLsizei n, GLuint * framebuffers)

 n : Số lượng đại diện cho bao nhiêu tên / id khung đệm sẽ được tạ
o ra
cùng một lúc.
 framebuffers : Một con trỏ tới một biến để lưu trữ các tạ
o ra tên /
id. Nếu có nhiều hơn một tên / id được tạo ra, con trỏ này sẽ trỏ đến đầu của mộ
t
mảng.
GLvoid glBindFramebuffer (Glenn target, GLuint framebuffer)

 target: Mục tiêu sẽ luôn luôn được GL_FRAMEBUFFER, đây chỉ

một ước nội bộ cho OpenGL.
 framebuffers : Tên / id của bộ đệm khung hình bị ràng buộc.
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
15

3.2 Làm đệm (Render Buffers)
Render Buffers là một lưu trữ tạm thời cho hình ảnh đến từ một của OpenGL
render. Đây là cặp chức năng liên quan để làm cho bộ đệm:
GLvoid glGenRenderbuffers (GLsizei n, GLuint * làm bộ đệm)

 n : Số lượng đại diện cho bao nhiêu làm cho tên / id bộ đệm sẽ

được tạo ra cùng một lúc.
 renderbuffers : Một con trỏ tới một biến để lưu trữ các tạ
o ra tên
/ id. Nếu có nhiều hơn một tên / id được tạo ra, con trỏ này sẽ trỏ đến đầ
u
của một mảng.
GLvoid glBindRenderbuffer (GLenum target, GLuint renderbuffer)

 target : Mục tiêu sẽ luôn luôn đượ
c GL_RENDERBUFFER, đây
chỉ là một ước nội bộ cho OpenGL.
 renderbuffer : render tên đệm / id bị ràng buộc.

GLvoid glRenderbufferStorage (Glenum target, GLenum in
ternalformat,
GLsizei width, Glsizei height)

 target : Mục tiêu sẽ luôn luôn đượ
c GL_RENDERBUFFER, đây
chỉ là một ước nội bộ cho OpenGL.
 internalformat : Điều này chỉ ra loại đệm và những gì màu đị
nh
dạng hình ảnh tạm thời này sẽ sử dụng. Tham số này có thể là:
o GL_RGBA4 , GL_RGB5_A1 hoặc GL_RGB56 đến một bộ
đệm làm với màu sắc cuối cùng;
o GL_DEPTH_COMPONENT16 đến một bộ đệm làm vớ
i Z
chiều sâu;
o GL_STENCIL_INDEX hoặc GL_STENCIL_INDEX8 đến mộ
t

bộ đệm làm với thông tin giấy nến.
 width : chiều rộng cuối cùng của một bộ đệm làm.
 height : Chiều cao cuối cùng của một bộ đệm làm.
Để đính kèm RenderBuffers làm vào một bộ đệm khung hình ta có chức năng
sau:
GLvoid glFramebufferRenderbuffer (Glenum target
, GLenum
attachment, GLenum renderbuffertarget, GLuint renderbuffer)

 target : Mục tiêu sẽ luôn luôn đượ
c GL_FRAMEBUFFER, đây
chỉ là một ước nội bộ cho OpenGL.
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
16

 attachment : này quy định những loại làm bộ đệ
m, chúng tôi
muốn đính kèm trong một bộ đệm khung hình, tham số này có thể là:
o GL_COLOR_ATTACHMENT0 : Để đính kèm một màu sắ
c
làm cho đệm;
o GL_DEPTH_ATTACHMENT : Để đính kèm một chiề
u sâu
làm cho đệm;
o GL_STENCIL_ATTACHMENT : Để đính kèm mộ
t stencil làm
đệm.
 renderbuffertarget : Các renderbuffertarget sẽ luôn luôn đượ
c
GL_RENDERBUFFER, đây chỉ là một ước nội bộ cho OpenGL.

 renderbuffer : Tên / id của bộ đệm làm cho chúng tôi muố
n đính
kèm.

Mối quan hệ giữa Khung đệm và Render đệm.

Các vấn đề hiện đại CNPM – OpenGL ES 2.0
17

Trong OpenGL luôn luôn làm việc với một bộ đệm khung. Này được gọi là
cửa sổ hệ thống cung cấp bộ đệm khung và khung đệm tên / id 0 được dành riêng
cho nó. Các bộ đệm khung hình mà chúng tôi kiểm soát được biết như khung ứng
dụng tạo ra các vùng đệm.
Để tối ưu hóa tất cả các State tùy chọn, OpenGL có một cách để bật và tắt State
GLvoid glEnable (GLenum capability)

 capability : Các tính năng được bật. Các giá trị có thể là:
o GL_TEXTURE_2D
o GL_CULL_FACE
o GL_BLEND
o GL_DITHER
o GL_STENCIL_TEST
o GL_DEPTH_TEST
o GL_SCISSOR_TEST
o GL_POLYGON_OFFSET_FILL
o GL_SAMPLE_ALPHA_TO_COVERAGE
o GL_SAMPLE_COVERAGE
GLvoid glDisable (GLenum capability)

 capability : Các tính năng được tắt. Các giá trị có thể được giố

ng
như glEnable .
Một khi chúng ta bật / tắt tính năng, hướng này sẽ ảnh hưởng đến toàn bộ bộ
máy OpenGL. Một số người thích để bật một tính năng chỉ trong một thời gian sử
dụng nó và sau đó tắt, nhưng điều này là không nên. Nó rất phức tạp. Cách tốt nhất
là bật một lần và tắt một lần. Hoặc nếu thực sự cần, giảm thiểu bật / tắt trong ứng
dụng của.
Như trong ví dụ khối của chúng ta, chúng ta chỉ cần một bộ đệm chiều sâu,
chúng ta có thể viết:
glEnable (GL_DEPTH_TEST);

3.3. Đối tượng bộ đệm (Buffer Objects)
Các đối tượng bộ đệm được tối ưu hóa lưu trữ cho các mảng của Primitive.Có
hai loại đối tượng bộ đệm, loại đầu tiên lưu trữ các mảng của đỉnh, bởi vì nó có
các đối tượng bộ đệm còn được gọi là Vertex Buffer Object (VBO). Sau khi đã tạo
ra các đối tượng bộ đệm, có thể hủy các dữ liệu ban đầu, bởi vì các đối tượng bộ
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
18

đệm (BO) thực hiện một bản sao từ nó. Các loại khác của đối tượng đệm là đối
tượng Index Buffer (nhà phân phối).
Cấu trúc:
GLvoid glGenBuffers (GLsizei n, GLuint * buffer)

 n : Số lượng đại diện cho bao nhiêu tên / id đối tượng bộ đệm sẽ
được tạo ra cùng một lúc.
 buffer : Một con trỏ tới một biến để lưu trữ các tạo ra t
ên /
id. Nếu có nhiều hơn một tên / id được tạo ra, con trỏ này sẽ trỏ đến đầu củ
a

một mảng.
GLvoid glBindBuffer (GLenum target, GLuint buffer)

 target : Mục tiêu sẽ xác định loại đối tượng bộ đệm sẽ đượ
c,
VBO hoặc nhà phân phối. Các giá trị có thể là:
o GL_ARRAY_BUFFER : Điều này sẽ thiết lập một VBO (hoặ
c
ABO, bất cứ điều gì).
o GL_ELEMENT_ARRAY_BUFFER : Điều này sẽ thiết lập mộ
t
nhà phân phối.
 buffer : Tên / id của bộ đệm khung hình bị ràng buộc.
Các BufferObject Hook trong thực tế là một cái móc đôi. Bởi vì nó có thể giữ
hai đối tượng bộ đệm, một trong mỗi
loại:GL_ARRAY_BUFFER và GL_ELEMENT_ARRAY_BUFFER .
Cấu trúc:
GLvoid glBufferData (GLenum target, GLsizeiptr
size, const GLvoid *
data, Glenum usage)

 target : Chỉ ra cho các loại đệm bạn muốn thiết lập các thuộc tính
cho. Param điều này có
thểGL_ARRAY_BUFFER hoặc GL_ELEMENT_ARRAY_BUFFER .
 size : Kích thước của bộ đệm trong các đơn vị cơ bản (byte).
 data : Một con trỏ tới dữ liệu.
 usage : Các loại sử dụng. Điều này giống như một mẹo để
giúp
OpenGL để tối ưu hóa dữ liệu.Điều này có thể của ba loại:
o GL_STATIC_DRAW : này biểu thị một dữ liệ

u không thay
đổi. Bạn đặt nó một lần và sử dụng bộ đệm thường.
o GL_DYNAMIC_DRAW : Đây có nghĩa là một dữ liệ
u có thể
thay đổi. Bạn đặt nó một lần và cập nhật nội dung của nó nhiều lần bằ
ng
cách sử dụng nó thường xuyên.
o GL_STREAM_DRAW : Đây có nghĩa là một dữ liệu tạ
m
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
19

thời. Đối với người của bạn đó là quen thuộc với Objective-C, điề
u này
giống như một autorelease. Bạn đặt nó một lần và sử dụng vài lầ
n.Sau
OpenGL sẽ tự động làm sạch và phá hủy bộ đệm này.
GLvoid glBufferSubData (GLenum target, GLintptr offset, GLsizeiptr
size,
const GLvoid * data)

 target : Chỉ ra cho các loại đệm bạn muốn thiết lập các thuộc tính
cho. Param điều này có
thểGL_ARRAY_BUFFER hoặc GL_ELEMENT_ARRAY_BUFFER .
 offset : Con số này đại diện cho bù đắp mà bạn sẽ bắt đầu thay đổ
i
vào đối tượng đệm được xác định trước đó. Con số này đượ
c đưa ra là đơn
vị cơ bản (byte).
 size : Con số này đại diện cho kích thước của những thay đổ

i vào
đối tượng đệm được xác định trước đó. Con số này được đưa ra là đơn vị

bản (byte).
 data : Một con trỏ tới dữ liệu.
Sử dụng chức năng glBufferData để thiết lập nội dung cho đối tượng bộ đệm
của bạn và thuộc tính của nó. Nếu bạn chọn loại sử dụng
GL_DYNAMIC_DRAW, nó có nghĩa là bạn muốn cập nhật đối tượng bộ đệm sau
đó và để làm điều này bạn cần phải sử dụng thứ hai, glBufferSubData.
Khi bạn sử dụng glBufferSubData kích thước của đối tượng bộ đệm của bạn
trước đây đã được xác định, vì vậy bạn không thể thay đổi nó. Nhưng để tối ưu
hóa các bản cập nhật, bạn có thể chọn chỉ là một phần nhỏ của đối tượng đệm toàn
bộ để được cập nhật.

4. Kết cấu (Texture)
Kết cấu là chủ đề rất lớn trong OpenGL.
Tất cả các kết cấu phải có chiều rộng và chiều cao. Tính bằng pixel như 2, 4, 8,
16, 32, 64, 128, 256, 512 hoặc 1024 pixel. Một kết cấu, 1024 là một kích thước
lớn hơn và thường cho biết kích thước tối đa có thể của một kết cấu. Vì vậy, tất cả
các kết cấu sẽ được sử dụng trong OpenGL phải có kích thước như: 64 x 128 hoặc
256 x 32 hoặc 512 x 512, ví dụ. Bạn không thể sử dụng 200 x 200 hoặc 256 x
100. Đây là một quy tắc để tối ưu hóa việc xử lý nội bộ OpenGL trong GPU.
Một điều quan trọng cần biết về kết cấu trong OpenGL là để đọc pixel. Thường
các định dạng tập tin ảnh lưu trữ các thông tin điểm ảnh bắt đầu từ góc trên bên
trái và di chuyển qua từng dòng để góc dưới bên phải. Định dạng tập tin như JPG,
PNG, BMP, GIF, TIFF và để những người khác sử dụng điểm ảnh này. Nhưng
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
20

trong OpenGL thứ tự này là lộn ngược. Các kết cấu trong OpenGL đọc các điểm

ảnh bắt đầu từ góc dưới bên trái và đi vào góc trên bên phải.

OpenGL đọc các điểm ảnh từ góc dưới bên trái vào góc trên bên phải.
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
21


Dữ liệu hình ảnh phải được lộn theo chiều dọc để phù hợp với quyền vào
OpenGL.
Bây giờ, về logic, các kết cấu trong OpenGL làm việc tại theo cách này: có
một tập tin hình ảnh, vì vậy phải trích xuất các thông tin màu nhị phân từ nó, giá
trị hexa. Có thể trích xuất các thông tin alpha, OpenGL hỗ trợ RGB và định dạng
RGBA. Trong trường hợp này sẽ cần phải trích xuất các hệ hexa + giá trị alpha từ
hình ảnh. Lưu trữ tất cả mọi thứ vào một mảng các điểm ảnh.
Với mảng này của điểm ảnh (còn gọi là texels, vì sẽ được sử dụng trong một
kết cấu). OpenGL sẽ sao chép mảng của bạn và lưu trữ nó trong một định dạng tối
ưu hóa để sử dụng trong các GPU và bộ đệm khung hình, nếu cần thiết.
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
22


Bạn có thể xác định lên đến 32 đơn vị Texture, nhưng chỉ lên đến 8 kết cấu
mỗi đổ bóng.
Chúng ta có thể tạo ra một đơn vị của kết cấu có thể được xử lý trực tiếp trong
GPU, cũng như Shaders. Có thể hạn chế số lượng các đơn vị kết cấu hiện tại đang
chạy trên GPU. Một bộ nhớ cache trong GPU, nó hoạt động nhanh chóng, tốt hơn.
Hai điều rất quan trọng cần nhớ là: đầu tiên, phải kích hoạt các đơn vị kết cấu
bằng cách sử dụng glActiveTexture () và sau đó liên kết các kết cấu tên / id sử
dụng glBindTexture () . Điều quan trọng thứ hai là ngay cả theo mặc định
OpenGL hỗ trợ lên đến 32 đơn vị kết cấu, bạn không thể sử dụng một số khe cắm

cao hơn so với các đơn vị kết cấu hỗ trợ tối đa trong việc thực hiện nhà cung cấp
của bạn, vì vậy nếu thực hiện OpenGL của bạn không hỗ trợ hơn 16 đơn vị kết
cấu, bạn chỉ có thể sử dụng các đơn vị kết cấu trong phạm vi 0-15.
Vâng, OpenGL đơn vị kết cấu phương pháp tiếp cận có thể được tốt hơn, tất
nhiên, nhưng như tôi đã nói, đó là những gì chúng tôi đã cho bây giờ! OK, một lần
nữa các mã này rất giống với những người khác trên: Tạo ra một đối tượng kết
Các vấn đề hiện đại CNPM – OpenGL ES 2.0
23

cấu, kết cấu Ràng buộc này và thiết lập thuộc tính của nó. Dưới đây là các chức
năng:
GLvoid glGenTextures (GLsizei n, GLuint * textures)

 n : Số lượng đại diện cho bao nhiêu tên / id kết cấu 'sẽ được tạ
o ra
cùng một lúc.
 textures : Một con trỏ tới một biến để lưu trữ các tạo ra t
ên /
id. Nếu có nhiều hơn một tên / id được tạo ra, con trỏ này sẽ trỏ đến đầu củ
a
một mảng.
GLvoid glBindTexture (Glenum target, GLuint textures)

 target : Mục tiêu sẽ xác định loại kết cấu sẽ được, một kết cấ
u 2D
hoặc 3D kết cấu. Các giá trị có thể là:
o GL_TEXTURE_2D : Điều này sẽ thiết lập một kết cấu 2D.
o GL_TEXTURE_CUBE_MAP : Điều này sẽ thiết lập một kế
t
cấu 3D.

 textures : Tên / id của kết cấu bị ràng buộc.
Để tải lên các dữ liệu kết cấu và thiết lập một số thuộc tính:
GLvoid glTexImage2D (GLenum target, Glint level, Glint in
ternalformat,
GLsizei width, Glsizei height, Glint border, Glenum format, GLenum type
,
const GLvoid * pixel)

 target : Để một kết cấu 2D này sẽ luôn luôn được
GL_TEXTURE_2D.
 level : thông số này thể hiện mức độ bản đồ mip. Cấp cơ sở là 0,
bây giờ chúng ta hãy chỉ sử dụng 0.
 internalformat : Điều này thể hiện định dạng màu sắc củ
a các
điểm ảnh. Tham số này có thể là:
o GL_RGBA : Đối với RGB + Alpha.
o GL_RGB : Đối với RGB chỉ.
o GL_LUMINANCE_ALPHA : Đối với Red + Alpha chỉ.
Trong
trường hợp này các kênh màu đỏ sẽ đại diện cho độ sáng.
o GL_LUMINANCE : Đối với chỉ đỏ. Trong trường hợ
p này các
kênh màu đỏ sẽ đại diện cho độ sáng.
o GL_ALPHA : Chỉ Alpha.
 width : chiều rộng của hình ảnh theo pixel.
 height : Chiều cao của hình ảnh theo pixel.
 Border : Thông số này được bỏ qua trong OpenGL ES.
Luôn
luôn sử dụng giá trị 0. Đây chỉ là một liên tục nội bộ để bảo tồ
n compatibly

Các vấn đề hiện đại CNPM – OpenGL ES 2.0
24

với các phiên bản máy tính để bàn.
 format : Các định dạng phải có cùng giá trị
của internalformat . Một lần nữa, đây chỉ là một ước OpenGL nội bộ.
 type : Đây đại diện cho các định dạng dữ liệu của các điể
m
ảnh. Tham số này có thể là:
o GL_UNSIGNED_BYTE : Định dạng này đại diệ
n cho 4 Bytes
mỗi điểm ảnh, vì vậy bạn có thể sử dụng 8 bit cho màu đỏ
, 8 bit cho màu
xanh lá cây, 8 bit cho màu xanh và 8 bit cho các kênh alpha, ví dụ. Đị
nh
nghĩa này được sử dụng với tất cả các định dạng màu sắc.
o GL_UNSIGNED_SHORT_4_4_4_4 : Định dạng này đại diệ
n
cho 2 byte cho mỗi điểm ảnh, vì vậy bạn có thể sử dụ
ng 4 bit cho màu
đỏ, 4 bit cho màu xanh lá cây
, 4 bit cho màu xanh và 4 bit cho các kênh
alpha, ví dụ. Định nghĩa này được sử dụng với chỉ RGBA.
o GL_UNSIGNED_SHORT_5_5_5_1 : Định dạng này đại diệ
n
cho 2 byte cho mỗi điểm ảnh, vì vậy bạn có thể sử dụ
ng 5 bit cho màu
đỏ, 5 bit cho màu xanh lá cây, 5 bit
cho màu xanh và 1 bit cho các kênh
alpha, ví dụ. Định nghĩa này được sử dụng với chỉ RGBA.

o GL_UNSIGNED_SHORT_5_6_5 : Định dạng này đại diệ
n cho
2 byte cho mỗi điểm ảnh, vì vậy bạn có thể sử dụng 5 bit cho màu đỏ
, 6
bit cho màu xanh lá cây và 5 bit cho màu xanh, ví dụ. Định nghĩa n
ày
được sử dụng với chỉ RGB.
 pixel : Các con trỏ đến mảng của bạn của các điểm ảnh.

5. Rasterize
Các Rasterize theo nghĩa hẹp là chỉ có quá trình mà OpenGL có một đối
tượng 3D và chuyển đổi bó của toán học thành một hình ảnh 2D. Sau đó, mỗi
mảnh của vùng hiển thị này sẽ được xử lý bởi các fragment shader.
Rasterize chỉ là một bước nhỏ thông qua các đường ống dẫn đồ họa. Nhưng
nó lại rất quan trọng.
Thực tế Rasterize là quá trình tạo ra một hình ảnh từ một đối tượng 3D. Các
Rasterize sẽ xảy ra cho từng đối tượng 3D trong khung cảnh và sẽ cập nhật bộ
đệm khung. Mặt khác có thể làm nhiễu bằng nhiều cách thực hiện trong quá trình
Rasterize.

5.1 Face Culling (Tiêu hủy)
OpenGL làm việc với các phương pháp để tìm và loại bỏ những mặt không
nhìn thấy được. Dựa trên thứ tự của đỉnh OpenGL có thể xác định đó là mặt trước

×