Trang chủ > Phát triển di động > Nội dung chính

OpenGL ES và biến đổi tọa độ (phần hai)


Chi tiết về cấu trúc dữ liệu bên trong Redis OpenGL ES và biến đổi tọa độ Bài thứ hai trong loạt bài viết này. Trong bài viết nàybóng đá wap, chúng ta sẽ tập trung thảo luận về các nội dung sau:

  1. Đầu tiênlịch bóng đá trực tiếp, chúng ta sẽ cùng tìm hiểu về cách diễn giải ba phép biến đổi model, view và projection trong Android thông qua ví dụ từ mã nguồn của một chương trình demo. Những phép biến đổi này đóng vai trò quan trọng trong việc định hình không gian hiển thị và giúp các đối tượng được thể hiện đúng vị trí trên màn hình. Dưới đây là cách mà chúng ta có thể sử dụng mã code để biểu diễn từng loại biến đổi này một cách rõ ràng và hiệu quả.
  2. Hãy cùng tìm hiểu về các lý thuyết liên quan và lần lượt phân tích quá trình tính toán cho hai loại biến đổi trong việc chuyển đổi mô hình: tỷ lệ (scaling) và dịch chuyển (translation). Hai loại biến đổi này khá trực quan và dễ hiểu. Tuy nhiênlive casino, đối với vấn đề xoay (rotation), do có nhiều khía cạnh phức tạp cần được giải thích chi tiết, chúng ta sẽ dành phần thảo luận về chủ đề này cho bài viết tiếp theo.
  3. Chúng ta hãy cùng phân tích cụ thể về việc áp dụng các phép biến đổi thu phóng (scaling) và dịch chuyển (translation) trong Androidbóng đá wap, so sánh lý thuyết đã suy diễn trước đó với thực tế mã nguồn để củng cố thêm sự hiểu biết. Qua đó, chúng ta có thể thấy rõ hơn cách mà các khái niệm lý thuyết được áp dụng vào thực tiễn lập trình một cách hiệu quả.

Khi một công trình hoàn thànhbóng đá wap, hãy gỡ bỏ sạch sẽ

Bài viết này nhằm làm cho cuộc thảo luận chi tiết trở nên rõ ràng hơnbóng đá wap, chắc chắn sẽ không đi theo phong cách của Gauss. Thay vào đó, ở phần tiếp theo, chúng tôi sẽ cố gắng giải thích từng bước suy luận một cách tỉ mỉ nhất có thể và nỗ lực hết sức để làm sáng tỏ toàn bộ tư duy đằng sau các phép tính. Điều này sẽ giúp độc giả dễ dàng nắm bắt được bản chất và logic đằng sau những kết quả mà chúng tôi trình bày.

Giới thiệu chương trình demo

Bài trước Địa chỉ của chương trình Demo đã được cung cấp trước đólịch bóng đá trực tiếp, nhưng để đảm bảo rõ ràng, mình sẽ chia sẻ lại địa chỉ một lần nữa. Tất cả các mã nguồn được đề cập trong bài viết này đều được lấy từ tập tin bên dưới:

Đầu tiênbóng đá wap, trong vertex shader, mã liên quan đến biến đổi tọa độ là dòng mã dưới đây:

								
									
										gl_Position
									 =
									 projection
									 *
									 view
									 *
									 model
									 *
									 vec4
									(
									position
									.
									xyz
									,
									 1
									);
									

								

Nó cho biết rằnglive casino, để thực hiện các phép biến đổi đối với một đỉnh tọa độ, chúng ta sẽ áp dụng tuần tự ba loại biến đổi: model (mô hình), view (xem) và projection (dự án). Mỗi loại biến đổi này được thực hiện bằng cách nhân trái (left-multiply) với một ma trận tương ứng. Trong dòng mã trên, có vẻ như thứ tự của ba phép biến đổi này dường như ngược lại so với những gì chúng ta mong đợi, nhưng đó chính là kết quả tất yếu từ việc nhân trái ma trận.

Trong mã này, vec4(position.xyzlive casino, 1)Bạn có thể biểu diễn tọa độ của đỉnh trong hệ tọa độ cục bộ (sử dụng một tọa độ đồng nhất bốn chiềulịch bóng đá trực tiếp, chúng ta sẽ giải thích thêm sau). Khi nhân tọa độ của đỉnh đó với ma trận model ở phía trái, bạn sẽ thu được tọa độ của đỉnh đó trong hệ tọa độ thế giới. Bài trước Chúng ta đã biết rằng quá trình biến đổi của model có thể bao gồm ba loại thay đổi cơ bản: tỷ lệ (scaling)bóng đá wap, xoay (rotation) và dịch chuyển (translation). Sau khi các tọa độ trong hệ tọa độ thế giới được nhân trái với một ma trận quan sát (view matrix), chúng sẽ được chuyển đổi sang hệ tọa độ máy ảnh. Cuối cùng, khi nhân trái thêm một ma trận chiếu (projection matrix), quá trình biến đổi chiếu sẽ hoàn tất, đưa tọa độ từ không gian 3D vào không gian 2D mà chúng ta nhìn thấy trên màn hình.

Vậy thìlive casino, trong đoạn mã này, ma trận model, view và projection có giá trị gì? Hãy cùng tìm hiểu cách chúng được tính toán riêng biệt trong chương trình Demo. Lấy ví dụ về hình lập phương thứ hai, mã để tính toán ma trận model như sau: ```cpp // Tính toán ma trận model cho hình lập phương thứ hai glm::mat4 model = glm::translate(glm::mat4(1.0f), glm::vec3(-1.5f, 0.0f, -10.0f)); model = glm::rotate(model, glm::radians(45.0f), glm::vec3(0.0f, 1.0f, 0.0f)); model = glm::scale(model, glm::vec3(0.5f, 0.5f, 0.5f)); ``` Trong đó, `glm::translate` di chuyển hình lập phương đến vị trí (-1.5, 0.0, -10.0), `glm::rotate` xoay nó 45 độ quanh trục Y và `glm::scale` thay đổi kích thước của nó thành một nửa kích thước ban đầu.

								
									
										Matrix
									.
									setIdentityM
									(
									modelMatrix2
									,
									 0
									);
									
Matrix
									.
									translateM
									(
									modelMatrix2
									,
									 0
									,
									 0.5f
									,
									 1.0f
									,
									 -
									1.5f
									);
									
Matrix
									.
									rotateM
									(
									modelMatrix2
									,
									 0
									,
									 angle
									,
									 0.0f
									,
									 1.0f
									,
									 0.0f
									);
									
Matrix
									.
									scaleM
									(
									modelMatrix2
									,
									 0
									,
									 1.5f
									,
									 1.5f
									,
									 1.5f
									);
									

								

Đoạn mã này, modelMatrix2 Bạn cần tính toán ma trận modellịch bóng đá trực tiếp, đây là một ma trận 4x4 được lưu trữ trong một mảng float có độ dài 16. Ma trận này đóng vai trò quan trọng trong việc xác định vị trí, hướng và sự biến đổi của đối tượng trong không gian 3D. Mỗi phần tử trong mảng này đại diện cho một yếu tố riêng biệt trong ma trận, góp phần tạo nên các phép biến đổi như xoay, dịch chuyển hay phóng to thu nhỏ đối tượng. float[16] Tại sao không phải là ma trận 3x3 nhỉ? Điều này liên quan đến tọa độ thuần nhấtlive casino, chúng ta sẽ bàn về nó sau. Hiện tại, hãy tạm thời bỏ qua điều đó. Chúng ta vừa gọi đến SDK của Android, nơi cung cấp các công cụ mạnh mẽ để thực hiện... Matrix Phương pháp của lớp công cụ đã gán giá trị cho nó. setIdentityM Điều này biểu thị việc thiết lập một ma trận đơn vị ban đầulive casino, và translateM , rotateM Ghi giá trị scaleM Bạn có thể thực hiện các điều chỉnh trên ma trận này dựa trên ma trận đơn vị ban đầubóng đá wap, cụ thể là thực hiện tuần tự các thao tác dịch chuyển, xoay và thu nhỏ. Tuy nhiên, cần lưu ý rằng mặc dù thứ tự gọi trong mã nguồn là dịch chuyển trước, sau đó xoay, và cuối cùng thu nhỏ, nhưng ý nghĩa của các thao tác này lại cần được giải thích theo chiều ngược lại: tức là trước tiên đã thực hiện một phép thu nhỏ, tiếp theo là xoay, và cuối cùng mới tiến hành dịch chuyển. Nguyên nhân cho sự khác biệt này vẫn liên quan đến ý nghĩa của việc nhân trái (left multiplication) trong ma trận, và chúng ta sẽ giải thích kỹ hơn về vấn đề này ở phần cuối bài viết. Hiện tại, hãy tạm ghi nhớ thứ tự giải thích của các thao tác này, thì ý nghĩa chính xác của đoạn mã trên chính là:

  1. Thu nhỏ : Trước tiênlive casino, phóng to 1,5 lần trên ba trục tọa độ x, y, z;
  2. Quay : Sau đó xoay quanh vectơ [0.0live casino, 1.0, 0.0] T (tức là trục y) với góc angle
  3. Dịch chuyển Bạn có thể di chuyển 0bóng đá wap,5 đơn vị theo hướng dương của trục x, tiếp đó dịch chuyển 1,0 đơn vị theo hướng dương của trục y và cuối cùng, dịch chuyển 1,5 đơn vị theo hướng âm của trục z.

Nếu bạn đã chạy thử chương trình Demo và quan sát kỹ theo những gì được mô tả ở trênlive casino, bạn sẽ nhận thấy hình lập phương này chính là khối lập phương lớn nhất ở phần trên cùng của màn hình. Nó đang xoay liên tục quanh một trục. Nguyên nhân khiến nó xoay là do bước thứ hai đã thiết lập góc quay cụ thể, dẫn đến hiện tượng đó xảy ra một cách mượt mà trước mắt bạn. angle Là một giá trị độnglịch bóng đá trực tiếp, giá trị của nó thay đổi từng khung hình, vì vậy nó trông như đang xoay không ngừng.

Hình chụp màn hình đầu ra của chương trình ví dụ

Lúc nàybóng đá wap, có lẽ một số bạn sẽ không khỏi thắc mắc: Trong mô tả trên, trục y có phải là hướng lên trên màn hình hay không? Còn trục z có phải là vuông góc với màn hình hay không? Câu trả lời là không. Khi nói về tọa độ và các trục tọa độ, điều đầu tiên chúng ta cần làm rõ là đang đề cập đến hệ tọa độ nào. Quá trình tính toán thường yêu cầu chúng ta chuyển đổi liên tục giữa các hệ tọa độ khác nhau. Tùy thuộc vào... Bài trước Trong phần giới thiệu nàybóng đá wap, chúng ta đang nói về việc chuyển đổi từ hệ tọa độ cục bộ sang hệ tọa độ thế giới. Do đó, các trục x, y, z ở đây thực chất chính là các trục của hệ tọa độ thế giới. Tuy nhiên, vị trí và góc nhìn của hệ tọa độ thế giới đối với màn hình không có mối liên hệ trực tiếp nào. Điều này phụ thuộc vào bước biến đổi quan sát (view transformation), tức là từ góc độ nào bạn sẽ quan sát toàn bộ khung cảnh.

Tiếp theolive casino, hãy nhìn kỹ cách tính toán ma trận view trong chương trình demo.

								
									
										Matrix
									.
									setLookAtM
									(
									viewMatrix
									,
									 0
									,
									 3.0f
									,
									 3.0f
									,
									 10.0f
									,
									 0.0f
									,
									 0.0f
									,
									 0.0f
									,
									 0.0f
									,
									 1.0f
									,
									 0.0f
									);
									

								

Trong dòng mã này, viewMatrix Là ma trận view cần tính toánlịch bóng đá trực tiếp, nó cũng là một ma trận 4x4. Chúng tôi vẫn đang gọi Matrix Phương pháp của lớp công cụ đã thực hiện việc gán giá trị. Ý nghĩa ở đây là chúng ta đặt "ánh mắt" (hoặc máy ảnh) tại điểm (3.0bóng đá wap, 3.0, 10.0) trong hệ tọa độ thế giới và hướng quan sát của nó chính xác về phía điểm gốc (0.0, 0.0, 0.0). Đồng thời, chúng ta cũng cần xác định hướng "chĩa lên" (up vector), và trong mã nguồn, hướng này được thiết lập là vectơ (0.0, 1.0, 0.0), tức là hướng thẳng lên trên. Thêm vào đó, việc cấu hình như vậy giúp tạo ra một góc quan sát hợp lý trong không gian 3D, đảm bảo rằng khung nhìn sẽ không bị méo mó hoặc sai lệch do sự không nhất quán trong cách định hướng. Điều này đặc biệt quan trọng khi xây dựng các mô phỏng hoặc môi trường đồ họa phức tạp, nơi mà sự chính xác trong vị trí và hướng có thể ảnh hưởng trực tiếp đến trải nghiệm người dùng.

Cuối cùngbóng đá wap, hãy nhìn vào cách tính toán ma trận projection:

								
									
										Matrix
									.
									perspectiveM
									(
									projectionMatrix
									,
									 0
									,
									 45.0f
									,
									 width
									 /
									 (
									float
									)
									 height
									,
									 0.1f
									,
									 100.0f
									);
									

								

Trong dòng mã này, projectionMatrix Là ma trận projection cần tính toánlive casino, nó cũng là một ma trận 4x4. Matrix.perspectiveM Đã gán giá trị cho ma trận nàylịch bóng đá trực tiếp, và các tham số đầu vào cần thiết cho cuộc gọi này như sau:

  • Góc quan sát được đặt thành 45bóng đá wap,0 độ. Giá trị này thường được gọi tắt là trường nhìn (field of view), viết tắt là fov. Ý nghĩa của nó đã được minh họa rõ ràng trong hình bên dưới. Trong nhiều hệ thống đồ họa hoặc mô phỏng, góc fov đóng vai trò quan trọng khi xác định phạm vi mà mắt nhìn có thể bao quát. Khi góc này lớn hơn, không gian hiển thị sẽ rộng hơn nhưng các chi tiết có thể trở nên mờ nhạt ở xa. Ngược lại, một giá trị nhỏ hơn giúp tập trung vào các đối tượng gần hơn và tạo ra hiệu ứng sâu hơn cho cảnh vật. Đây chính là lý do tại sao việc điều chỉnh góc fov rất cần thiết trong các trò chơi điện tử hoặc các phần mềm thiết kế đồ họa chuyên nghiệp.

Biểu đồ biến đổi chiếu

  • Tham số thứ hai là tỷ lệ chiều rộng/chiều caobóng đá wap, chỉ tỷ lệ chiều rộng/chiều cao của mặt phẳng gần (N).
  • Các tham số thứ ba và thứ tư lần lượt chỉ khoảng cách từ mặt phẳng gần (N) và mặt phẳng xa (F) đến máy ảnh.

Hiện tạilịch bóng đá trực tiếp, chúng ta đã quan sát qua mã nguồn liên quan đến việc tính toán ba ma trận model, view và projection, đồng thời cũng đã nắm được tổng quát về quy trình tính toán. Trong phần tiếp theo, chúng ta sẽ đi sâu hơn để phân tích định lượng quá trình tính toán của một số ma trận cụ thể. Hãy cùng tìm hiểu kỹ hơn về cách hoạt động của từng ma trận này, từ đó hiểu rõ hơn về vai trò mà mỗi ma trận đóng góp trong việc xây dựng khung cảnh 3D. Ma trận model, ví dụ như, chịu trách nhiệm cho việc dịch chuyển, xoay hoặc phóng to thu nhỏ đối tượng, trong khi ma trận view lại giúp điều chỉnh góc nhìn của người dùng. Cuối cùng, ma trận projection quyết định cách hình ảnh sẽ được nén xuống không gian hai chiều trước khi hiển thị lên màn hình. Chúng ta sẽ cùng khám phá chi tiết những bước toán học đằng sau từng loại ma trận này.

Phép biến đổi thu phóng và dịch chuyển

Giải thích về nền tảng lý thuyết đại số tuyến tính

Trước đó (bao gồm Bài trước Khi nhắc đến việc biến đổi tọa độlive casino, chúng ta thường nói về việc thay đổi các đỉnh. Tuy nhiên, trong đại số tuyến tính, những khái niệm mà chúng ta nghiên cứu đều xoay quanh vectơ và không có khái niệm điểm. Vectơ, theo bản chất ban đầu của nó, là một đối tượng có thể được xem như một đoạn thẳng có hướng, xuất phát từ một điểm gốc (thường được gọi là gốc tọa độ), và kết thúc tại một điểm đích trong không gian. Vectơ không chỉ đơn thuần là một đoạn thẳng mà còn mang thông tin về hướng và độ dài. Điều này làm cho vectơ trở thành một công cụ mạnh mẽ để mô tả sự dịch chuyển hoặc mối liên hệ giữa các điểm trong không gian. Khi thực hiện các phép biến đổi tọa độ, chúng ta thực chất đang di chuyển hoặc điều chỉnh vectơ đó, nhưng không phải trực tiếp tác động lên điểm. Thay vào đó, chúng ta sử dụng vectơ như một đại diện để mô tả vị trí và hướng của điểm trong không gian. Vì vậy, khi nói về biến đổi tọa độ, chúng ta cần hiểu rằng các phép toán thực tế được thực hiện trên vectơ, và các điểm chỉ là kết quả gián tiếp được xác định thông qua mối quan hệ giữa vectơ và hệ tọa độ. n Các phần hợp thành n Mảng. Khi ánh xạ vectơ sang không gian hình họclịch bóng đá trực tiếp, chúng ta mới có khái niệm điểm và mối quan hệ giữa điểm và vectơ.

Biểu đồ khái niệm điểm và vectơ

Như hình trênbóng đá wap, chúng ta đã xây dựng một hệ tọa độ vuông góc,Đây là một vectơbóng đá wap, biểu thị một lượng có độ lớn và hướng. Khi biểu diễn nó trong hệ tọa độ, điểm bắt đầu tại gốc tọa độ O lịch bóng đá trực tiếp, điểm kết thúc tại điểm P . Tọa độ của vectơ này và điểm P Tọa độ của điểm và tọa độ của vectơ từ gốc tọa độ đến điểm đó có thể được biểu diễn giống nhaulịch bóng đá trực tiếp, chẳng hạn như (1, 2). Điều này có nghĩa là bất kỳ điểm nào cũng có thể được ánh xạ một cách duy nhất với một vectơ dẫn từ gốc tọa độ đến điểm đó. Trong OpenGL ES, việc biến đổi tọa độ đỉnh (vertex) mà chúng ta đang học có thể được liên hệ trực tiếp với các khái niệm về biến đổi tuyến tính và biến đổi tọa độ trong đại số tuyến tính. Từ đó, chúng ta có thể thấy rằng những kiến thức toán học nền tảng này không chỉ mang ý nghĩa lý thuyết mà còn được áp dụng cụ thể trong lập trình đồ họa để tạo ra các hiệu ứng thị giác sinh động.

Trong phần mô tả tiếp theobóng đá wap, đôi khi chúng ta có thể nói về việc biến đổi một vectơ, và đôi khi lại đề cập đến việc biến đổi một điểm (hoặc đỉnh), nhưng cả hai cách diễn đạt này đều mang ý nghĩa tương đương. Lý do là vì một điểm và một vectơ có nguồn tại gốc tọa độ và đầu mút nằm tại điểm đó hoàn toàn tương ứng với nhau. Với cách hiểu này, việc sử dụng thuật ngữ nào cũng không quan trọng, vì cả hai đều biểu thị cùng một ý nghĩa toán học cơ bản.

Trong hệ tọa độ Descarteslịch bóng đá trực tiếp, một vector còn có một tính chất đặc biệt, đó là nó không phụ thuộc vào vị trí của điểm gốc. Điều này có nghĩa là, khi một vector được di chuyển theo bất kỳ hướng nào mà không thay đổi độ dài và hướng, nó vẫn giữ nguyên giá trị. Hãy tưởng tượng trong hình ảnh minh họa phía trên, nếu bạn di chuyển vector từ vị trí ban đầu sang một vị trí khác trong hệ trục tọa độ, dù nó nằm ở đâu, vector đó vẫn duy trì cùng một giá trị đại số và vectơ học. Được xác định bởi vectơ Khi thực hiện phép tịnh tiếnlive casino, vectơ sau khi di chuyển sẽ có cùng độ dài và hướng như trước tịnh tiến. Điều này có nghĩa là chúng biểu diễn cùng một vectơ. Vì vậy, vectơ sau khi được dịch chuyển vẫn giữ nguyên giá trị và ý nghĩa đại diện cho chính nó trước khi di chuyển.Vẫn được biểu thị bằng tọa độ (1bóng đá wap,2).

Nếu như việc dịch chuyển một vectơ không làm thay đổi tọa độ của nóbóng đá wap, thì để thực hiện phép biến đổi tịnh tiến cho một đỉnh, chúng ta không thể chỉ đơn giản dựa vào việc dịch chuyển một vectơ. Thay vào đó, chúng ta cần sử dụng phép cộng giữa hai vectơ (và ở phần tiếp theo, bạn sẽ hiểu rõ hơn về cách này). Điều này mở ra một cách tiếp cận mới để giải quyết vấn đề mà không cần thay đổi trực tiếp tọa độ ban đầu.

Trong đại số tuyến tínhbóng đá wap, khái niệm biến đổi tuyến tính là một phần quan trọng với nền tảng lý thuyết phong phú và hoàn chỉnh. Tuy nhiên, các quy trình biến đổi trong OpenGL ES mà chúng ta sẽ thảo luận không thể được hoàn toàn diễn tả thông qua biến đổi tuyến tính. Ví dụ như việc thu nhỏ (scale) và xoay (rotate) có thể được biểu diễn dưới dạng biến đổi tuyến tính, nhưng phép dịch chuyển (translate) thì không. Những loại biến đổi mà chúng ta sẽ tìm hiểu sau này, chẳng hạn như biến đổi quan sát (view transformation) và biến đổi chiếu (projection transformation), cũng không thuộc phạm vi của biến đổi tuyến tính. Trên thực tế, chúng thuộc về biến đổi affine, vốn mở rộng thêm khả năng bao gồm cả các phép dịch chuyển trong không gian. Affine Transformation Chúng ta sẽ không vội vàng đi sâu vào những khái niệm trừu tượng này ngay từ đầubóng đá wap, mà thay vào đó sẽ tập trung thảo luận từng bước chuyển đổi cụ thể và cách chúng được suy ra. Có lẽ đến cuối cùng, khi quay lại nhìn những khái niệm trừu tượng ấy, chúng ta sẽ hiểu rõ hơn và có cái nhìn toàn diện hơn về chúng.

Quá trình suy ra ma trận dịch chuyển

Đầu tiênbóng đá wap, chúng ta hãy cùng xem xét việc dịch chuyển (translation) của đỉnh. Điều này có thể được thực hiện thông qua phép cộng vectơ. Hãy tham khảo hình minh họa dưới đây: Trong hình vẽ, chúng ta thấy rằng mỗi đỉnh được di chuyển theo một hướng cụ thể, và cách thức này hoàn toàn phụ thuộc vào giá trị của vectơ chỉ định. Việc sử dụng vectơ không chỉ giúp xác định độ dài mà còn chỉ ra phương hướng của sự dịch chuyển, từ đó tạo nên một sự thay đổi chính xác trong vị trí của các đỉnh.

Biểu đồ cộng vectơ

Trong hình này, A Điểm dịch chuyển tới B Điểmlịch bóng đá trực tiếp, tương đương với việc thực hiện phép cộng vectơ:

Chúng ta thấy rằnglive casino, trong hệ tọa độ vuông góc, phép cộng vectơ tuân theo quy tắc tam giác. Trong đó, vectơĐại diện cho độ lớn và hướng của sự dịch chuyển được gọi là vectơ dịch (translation vector). Để dễ dàng nhận biết tọa độ của vectơ dịch này hơnlive casino, chúng ta có thể di chuyển nó về gốc tọa độ. Khi đó, vectơ dịch sẽ song song với một vectơ khác, cho phép chúng ta so sánh và phân tích rõ ràng hơn về hướng cũng như độ dài của nó. Việc này không chỉ giúp hiểu sâu hơn về tính chất của vectơ mà còn hỗ trợ trong việc xác định mối quan hệ giữa các điểm trong không gian.Bằng nhaubóng đá wap, điều này cho thấy tọa độ của nó là (0.5,1). VectơCộng thêm một vectơ dịch chuyển như vậylive casino, tương đương với việc dịch chuyển điểm A Dọc theo trục x 0bóng đá wap,5 đơn vị và dọc theo trục y 1 đơn vị, do đó dịch chuyển tới vị trí của điểm B Ví dụ trên là vectơ 2 chiềulịch bóng đá trực tiếp, bây giờ chúng ta mở rộng sang 3 chiều, biểu thị phép biến đổi dịch chuyển bằng tọa độ vectơ, như sau:

Trong biểu thức trênlive casino,

Đại diện cho giá trị của vectơ dịch chuyển (translation vector) được đề cập trước đó.

live casino, để nhân nó với tọa độ 3 chiều của đỉnh:

Trong đại số tuyến tínhbóng đá wap, một biến đổi thường được biểu diễn thông qua phép nhân ma trận. Hơn nữa, OpenGL ES tận dụng sức mạnh của GPU để thực hiện các phép tính, và GPU có những thuật toán cực kỳ hiệu quả cho việc nhân ma trận. Chúng ta cũng mong muốn biến đổi dịch (translation) trong trường hợp này có thể được trình bày dưới dạng nhân ma trận ( cụ thể hơn là nhân trái). Chúng ta hãy tưởng tượng một ma trận 3x3 mà sẽ đóng vai trò quan trọng trong việc thực hiện điều này. Trong ngữ cảnh này, ma trận 3x3 không chỉ đơn giản là một cấu trúc toán học mà còn mang ý nghĩa sâu sắc trong việc định hình cách các điểm hoặc vector được thay đổi vị trí trong không gian hai chiều. Một ma trận 3x3 điển hình có thể trông như sau: \[ M = \begin{bmatrix} 1 & 0 & t_x \\ 0 & 1 & t_y \\ 0 & 0 & 1 \\ \end{bmatrix} \] Ở đây, \(t_x\) và \(t_y\) là các yếu tố quyết định hướng và khoảng cách dịch chuyển của đối tượng trong hệ tọa độ. Ma trận này sẽ được nhân với một ma trận khác (thường là ma trận điểm hoặc vector) để tạo ra kết quả mong muốn. Điều này không chỉ làm tăng hiệu suất mà còn giúp tối ưu hóa việc xử lý đồ họa trong môi trường GPU. A Chúng ta phát hiện ra rằnglive casino, bất kể ma trận

Chuyển đổi thành tọa độ đồng nhất sẽ là: A Bạn có thể tự hỏi các giá trị của các phần tử khác nhau sẽ ra saolịch bóng đá trực tiếp, nhưng chúng ta chỉ có thể nhận được tổ hợp tuyến tính của \( x, y, z \), không bao giờ đạt được kết quả giống như phép cộng vector trước đó (trong đó \( x, y, z \) mỗi cái đều được cộng thêm một hằng số). Để giải quyết vấn đề này, chúng ta sẽ chuyển từ tọa độ 3 chiều sang tọa độ đồng nhất (homogeneous coordinates) trong không gian 4 chiều. Tọa độ đồng nhất là cách mà ta thêm một chiều thứ tư vào hệ tọa độ 3 chiều và đặt giá trị của nó bằng 1. Nói cách khác, với một điểm trong không gian 3 chiều, thay vì chỉ có \( (x, y, z) \), chúng ta sẽ biểu diễn nó dưới dạng \( (x, y, z, 1) \). Điều này mở ra một cách tiếp cận mới cho phép tính toán phức tạp hơn trong hình học.

bóng đá wap, chính là một tọa độ đồng nhất.

Bạn có thể tưởng tượng rằng thành phần thứ 4 của tọa độ thuần nhất không nhất thiết phải là 1. Tuy nhiênlive casino, trong phạm vi hiện tại mà chúng ta đang nghiên cứu, ta chưa cần đến trường hợp này. Chúng ta sẽ đi sâu vào vấn đề này khi thảo luận về phép biến đổi chiếu và phép chia theo chiều nhìn (perspective division). Hiện tại, hãy tạm coi tọa độ thuần nhất như một đại lượng được mở rộng thêm một chiều, với giá trị cố định là 1. Điều đó có nghĩa là việc thêm vào một thành phần này không gây hại gì cho hệ thống, miễn là khi cần thiết, ta chỉ việc loại bỏ nó để lấy lại tọa độ ba chiều ban đầu. Trong thực tế, trong OpenGL ES, các tọa độ đỉnh luôn được biểu diễn dưới dạng tọa độ thuần nhất bốn chiều. Hãy nhớ lại chương trình vertex shader mà chúng ta đã học trước đây, nơi...vec4(position.xyzlive casino, 1) Trong ma trận trên:

Cách làm rất đơn giản: một tọa độ đỉnh trong không gian 4 chiềulive casino, khi nhân trái với một ma trận, sẽ cho ra một kết quả cũng là một tọa độ đỉnh trong không gian 4 chiều (vẫn là dạng tọa độ đồng nhất). Ma trận này phải có kích thước 4x4. Theo định nghĩa của phép nhân ma trận, việc tạo ra một ma trận để biểu diễn phép dịch chuyển giờ đây trở nên khá dễ dàng: Chúng ta chỉ cần thêm vào một dòng và một cột đặc biệt để định nghĩa một phép dịch chuyển trong không gian 3 chiều. Cụ thể hơn, ma trận này sẽ có dạng như sau: [1 0 0 dx] [0 1 0 dy] [0 0 1 dz] [0 0 0 1] Trong đó, các giá trị dx, dy, dz đại diện cho khoảng cách dịch chuyển theo các trục X, Y, Z tương ứng. Khi nhân ma trận này với tọa độ của một điểm trong không gian, nó sẽ dịch chuyển điểm đó đúng theo những giá trị đã cho. Đây là cách mà chúng ta có thể dễ dàng biểu diễn một phép dịch chuyển trong không gian 3 chiều bằng cách sử dụng ma trận 4x4.

Quá trình suy ra ma trận thu phóng

Đó chính là ma trận biến đổi tịnh tiến mà chúng ta cần suy ra. Nó có kích thước 4x4. Khi quan sátlịch bóng đá trực tiếp, ta thấy phần trên bên trái của nó là một ma trận đơn vị 3x3, và cột thứ 4 ở ba phần tử đầu tiên chính là vector tịnh tiến. Có thể nhận thấy rằng, nhờ việc sử dụng hệ tọa độ thuần nhất (homogeneous coordinates), với việc thêm một chiều thứ tư bằng 1, kết quả sau khi thực hiện phép nhân ma trận đã cho ra dạng cộng vector (x, y, z cộng với vector tịnh tiến). Điều này đã tạo nên sự linh hoạt trong việc biểu diễn các phép biến đổi không gian trong không gian ba chiều, cho phép vừa xoay, vừa dịch chuyển một cách liền mạch.

Biểu đồ thu phóng vectơ

Hình trên biểu thị quá trình thu phóng vectơ 2 chiều. Vectơ

Khi được phóng to 1bóng đá wap,5 lần trên cả hai trục x và y sẽ tạo ra vectơKhi thu nhỏ 0bóng đá wap,5 lần trên trục x và phóng to 2 lần trên trục y, sẽ tạo ra vectơTọa độ đã thay đổi từ (2live casino,1) thành (3,1.5). Cách biến đổi này khá phù hợp với khái niệm "phóng to" hoặc " thu nhỏ" mà chúng ta thường nghĩ đến - tức là các chiều đều được "phóng to" hoặc "thu nhỏ" theo cùng một tỷ lệ. Nếu trong không gian 3 chiều, tất cả các đỉnh của một đối tượng đều được "phóng to" hoặc "thu nhỏ" theo tỷ lệ giống nhau, thì toàn bộ đối tượng đó sẽ tự động được "phóng to" hoặc "thu nhỏ" đúng như tỷ lệ đã cho. Điều này giúp tạo ra những chuyển đổi đồng nhất và hài hòa giữa các kích thước, đảm bảo rằng hình dạng tổng thể của đối tượng vẫn được giữ nguyên, chỉ khác ở kích cỡ.

Tuy nhiênlịch bóng đá trực tiếp, phép biến đổi tỷ lệ trong OpenGL ES có thể biểu diễn các trường hợp tổng quát hơn, tức là các chiều khác nhau có thể được thu nhỏ với các hệ số khác nhau. Hãy tiếp tục lấy ví dụ về vector hai chiều từ hình trên làm minh họa, khi vector này được áp dụng phép biến đổi tỷ lệ, mỗi thành phần của nó sẽ bị thay đổi theo một hệ số riêng biệt tùy thuộc vào hướng mà nó đang hoạt động. Điều này giúp tạo ra những hiệu ứng phức tạp hơn và linh hoạt hơn so với việc chỉ sử dụng một giá trị cố định cho tất cả các chiều.live casino, tọa độ thay đổi từ (2,1) thành (1,2), đây cũng là một phép biến đổi thu phóng.Biểu thức trên có nghĩa làbóng đá wap, tọa độ x, y, z của một vectơ sau khi thực hiện phép biến đổi thu phóng lần lượt trở thành các giá trị ban đầu S

Qua các ví dụ trên có thể thấybóng đá wap, phép biến đổi tỷ lệ là việc thay đổi tọa độ của từng chiều theo một hệ số "tăng" hoặc "giảm". Khi mở rộng sang không gian 3 chiều (3D), chúng ta vẫn sử dụng tọa độ đồng nhất 4 chiều (homogeneous coordinates). Quá trình này có thể được biểu diễn dưới dạng nhân ma trận như sau:

Nhân. Và ma trận 4x4 mà nhân bên trái trong biểu thức này chính là ma trận thu phóng mà chúng ta cần suy ra: x ,S y ,S z Hiện thực hóa thu phóng và dịch chuyển trong Android

(Vui lòng chú ý đến tên gói)bóng đá wap, dùng để tính toán các ma trận biến đổi phổ biến.

Cuối cùnglive casino, chúng ta hãy cùng tìm hiểu cách ma trận dịch chuyển và ma trận thu phóng được tính toán trong Android dựa trên kết quả từ phần trước. Trong Android, có một lớp công cụ có tên là **Matrix**, đây là một trong những thành phần quan trọng giúp xử lý các phép biến đổi hình học như dịch chuyển, thu phóng, xoay hoặc biến dạng đối tượng đồ họa. Lớp **Matrix** cho phép chúng ta thực hiện nhiều thao tác khác nhau, chẳng hạn như di chuyển điểm đến vị trí mới, thay đổi kích thước của đối tượng, hoặc phối hợp giữa nhiều phép biến đổi phức tạp. Một số phương thức phổ biến của nó bao gồm `postTranslate()` để dịch chuyển, `preScale()` để thu phóng, và `set()` để thiết lập trực tiếp ma trận từ đầu. Ví dụ, nếu bạn muốn tạo một ma trận dịch chuyển để di chuyển một hình chữ nhật sang bên phải 50 pixel và xuống dưới 100 pixel, bạn có thể làm như sau: ```java Matrix matrix = new Matrix(); matrix.postTranslate(50, 100); ``` Tương tự, để thu nhỏ một hình ảnh theo tỷ lệ 0.5 về chiều rộng và chiều cao, bạn sẽ viết: ```java Matrix matrix = new Matrix(); matrix.preScale(0.5f, 0.5f); ``` Nhờ lớp **Matrix**, việc xử lý các phép biến đổi trong Android trở nên linh hoạt và mạnh mẽ hơn, cho phép các nhà phát triển tạo ra các hiệu ứng trực quan đẹp mắt cho ứng dụng của mình. android.opengl.Matrix Ba phương pháp công cụ). Đoạn mã này chúng tôi sẽ lặp lại một lần nữabóng đá wap, như sau:

Chúng ta đã từng tiến hành suy diễn công thức của ma trận dịch chuyển và ma trận thu nhỏbóng đá wap, cả hai đều được biểu diễn dưới dạng ma trận 4x4 và có hình thức không quá phức tạp. Vì vậy, việc hiện thực hóa chúng bằng mã code dường như cũng khá rõ ràng. Tuy nhiên, nếu so sánh cẩn thận đoạn mã trong phần đầu tiên của bài viết này với các biểu thức ma trận đã được suy ra, bạn sẽ nhận ra rằng vấn đề chưa hề đơn giản như ban đầu tưởng tượng. Có vẻ như còn nhiều điều cần khám phá sâu hơn để hiểu rõ cách thức hoạt động thực sự của chúng.

Về mặt lý thuyếtbóng đá wap, quá trình biến đổi đỉnh có thể được biểu diễn như sau: một tọa độ đỉnh dạng đồng nhất (homogeneous) trong không gian 4 chiều, khi nhân trái với một ma trận biến đổi 4x4, sẽ cho ra tọa độ đỉnh dạng đồng nhất đã được biến đổi. Nếu một đỉnh cần thực hiện nhiều phép biến đổi, ví dụ như trước tiên thực hiện phép biến đổi tỷ lệ (scale), sau đó là phép dịch chuyển (translation), thì bạn nên nhân trái với ma trận tỷ lệ trước, sau đó nhân trái với ma trận dịch chuyển. Tuy nhiên, trong đoạn mã mà chúng ta đã giới thiệu ở phần đầu tiên, thay vì làm việc trực tiếp theo cách trên, các phép biến đổi đã được thực hiện tuần tự trên một ma trận đơn vị ban đầu, nghĩa là lần lượt tiến hành các bước điều chỉnh dịch chuyển, xoay (rotation), và tỷ lệ (scale) (tức là các hàm tương ứng đã được gọi riêng biệt). Lưu ý rằng khi thực hiện các phép biến đổi này, thứ tự đóng vai trò quan trọng. Việc thay đổi thứ tự phép biến đổi có thể dẫn đến kết quả hoàn toàn khác nhau, vì vậy bạn phải cẩn thận khi sắp xếp thứ tự các phép toán ma trận để đảm bảo đạt được hiệu quả mong muốn. Matrix và quá trình translateM , rotateM , scaleM Ma trận cuối cùng

								
									
										Matrix
									.
									setIdentityM
									(
									modelMatrix2
									,
									 0
									);
									
Matrix
									.
									translateM
									(
									modelMatrix2
									,
									 0
									,
									 0.5f
									,
									 1.0f
									,
									 -
									1.5f
									);
									
Matrix
									.
									rotateM
									(
									modelMatrix2
									,
									 0
									,
									 angle
									,
									 0.0f
									,
									 1.0f
									,
									 0.0f
									);
									
Matrix
									.
									scaleM
									(
									modelMatrix2
									,
									 0
									,
									 1.5f
									,
									 1.5f
									,
									 1.5f
									);
									

								

Trước tiênlịch bóng đá trực tiếp, hãy quan sát riêng modelMatrix2 Khi dữ liệu được truyền đến vertex shaderlive casino, nó thực hiện các phép toán ma trận theo một thứ tự khác so với cách bạn gọi trong mã. Cụ thể, thay vì làm theo trình tự mà bạn định nghĩa trong code (như đầu tiên là phép tịnh tiến, sau đó xoay và cuối cùng là thu nhỏ), trong vertex shader, nó sẽ thực hiện theo thứ tự ngược lại: trước tiên là phép thu nhỏ, tiếp đến là phép xoay, và cuối cùng là phép tịnh tiến. Điều này có thể gây nhầm lẫn khi bạn cố gắng hiểu tại sao kết quả không giống như kỳ vọng. Thực tế, đây là một đặc điểm của hệ thống xử lý đồ họa, nơi thứ tự nhân ma trận ảnh hưởng trực tiếp đến cách không gian của đối tượng được biến đổi.

Cuộc gọi nàylive casino, phân tích một chút. Chữ ký của phương pháp này như sau: Matrix.scaleM Nó biểu thị ý nghĩa làlive casino, mảng đầu vào

								
									
										public
									 static
									 void
									 scaleM
									(
									float
									[]
									 m
									,
									 int
									 mOffset
									,
									
            float
									 x
									,
									 float
									 y
									,
									 float
									 z
									);
									

								

Tại vị trí dịch chuyển float Đã lưu trữ sẵn một ma trận biến đổi (là ma trận 4x4)live casino, gọi ma trận này là m . Sau khi mOffset . Ma trận mới nhận được cuối cùng M Nhân trái vào tọa độ đỉnhlive casino, hiệu quả cuối cùng là trước tiên co rút ba chiều của tọa độ đỉnh xuống lần lượt thành scaleM Sau khi thực hiện cuộc gọi nàylịch bóng đá trực tiếp, ma trận biến đổi được nhập vào sẽ được điều chỉnh tại chỗ với một số thay đổi nhất định. Thao tác thu nhỏ (scale) sẽ được thêm vào, tạo ra một ma trận biến đổi mới, được ký hiệu là M’ Nhân với các biến đổi ban đầu M’ . Lưu ý: ở đây x , y , z Ba tham số này tương đương với S M Trước đóbóng đá wap, suy ra ma trận thu phóng x , y , z , tức là: x ,S y ,S z

Tất nhiên có: S Chỉ có như vậylịch bóng đá trực tiếp, khi nhân trái ma trận

Vào một tọa độ đỉnh nào đólive casino, mới có thể giải thích thành: trước tiên thu phóng, sau đó thực hiện biến đổi

M’ = M S

Lưu ý: công thức này biểu thị ý nghĩa có thể tóm tắt làlive casino, sau khi xử lý, tương đương với việc thêm vào ma trận biến đổi ban đầu M’ Nhân phải M

Một ma trận thu phóng. scaleM Để rõ ràng hơn bước "nhân phải" này thực hiện tác động gìlive casino, chúng ta đặt ma trận biến đổi bất kỳ Nhân phải với Sau đó, nhận được:

Biểu thức trên biểu thị M Phải thực hiện thao tác: nhân từng phần tử của cột thứ nhất đến thứ ba của ma trận biến đổi ban đầu

Với S S ; Cột thứ tư giữ nguyên.

Bây giờ chúng ta hãy xem scaleM Mã thực hiện: M Đoạn mã này chính xác là những gì biểu thức trước đó biểu thị. Cần lưu ý một điều ở đây: x ,S y ,S z Ma trậnbóng đá wap, mỗi cột thực tế chứa từng hàng của ma trận. Cụ thể, thứ tự lưu trữ dữ liệu là như sau:

Vì vậy đoạn mã trước đây scaleM Đã dễ hiểu hơn.

								
									public
									 static
									 void
									 scaleM
									(
									float
									[]
									 m
									,
									 int
									 mOffset
									,
									
            float
									 x
									,
									 float
									 y
									,
									 float
									 z
									)
									 {
									
        for
									 (
									int
									 i
									=
									0
									 ;
									 i
									<
									4
									 ;
									 i
									++)
									 {
									
            int
									 mi
									 =
									 mOffset
									 +
									 i
									;
									
            m
									[
									     mi
									]
									 *=
									 x
									;
									
            m
									[
									 4
									 +
									 mi
									]
									 *=
									 y
									;
									
            m
									[
									 8
									 +
									 mi
									]
									 *=
									 z
									;
									
        }
									
    }
									

								

Bằng cách sử dụng cùng suy nghĩ nàylịch bóng đá trực tiếp, chúng ta cũng có thể suy ra android.opengl.Matrix Trong đólịch bóng đá trực tiếp, ma trận được lưu trữ theo thứ tự cột (column-major order), do đó trong mã nguồn bạn sẽ thấy rằng: m Quá trình tính toán. Nó tương đương với việc nhân phải ma trận biến đổi bất kỳ

  m[offset +  0] m[offset +  4] m[offset +  8] m[offset + 12]
  m[offset +  1] m[offset +  5] m[offset +  9] m[offset + 13]
  m[offset +  2] m[offset +  6] m[offset + 10] m[offset + 14]
  m[offset +  3] m[offset +  7] m[offset + 11] m[offset + 15]

Ma trận dịch chuyển scaleM live casino, nhận được một ma trận biến đổi mới

Theo lý thuyết suy ra ở phần trướcbóng đá wap, chúng ta biết rằng giá trị của ma trận dịch chuyển là: Matrix.translateM Tính toán M Biểu thức này biểu thị T Phải thực hiện thao tác. Có thể thấy rằnglịch bóng đá trực tiếp, ba cột đầu tiên của ma trận biến đổi ban đầu M’

Không thay đổibóng đá wap, chỉ có cột thứ tư thay đổi.

Chúng ta hãy xem mã thực hiện M’ Phải thực hiện thao tác: nhân từng phần tử của cột thứ nhất đến thứ ba của ma trận biến đổi ban đầu

Của nó thực sự tính toán biểu thức trước đó: translateM Do bài viết này chưa thảo luận sâu về phép biến đổi quaylịch bóng đá trực tiếp, vì vậy M Đây không bàn đếnlive casino, chúng ta sẽ để lại cho bài viết tiếp theo.

Bài viết tiếp theo sẽ thảo luận về một phép biến đổi rất quan trọng trong biến đổi tọa độ — quay. translateM Đây không bàn đếnbóng đá wap, chúng ta sẽ để lại cho bài viết tiếp theo.

								
									public
									 static
									 void
									 translateM
									(
									
            float
									[]
									 m
									,
									 int
									 mOffset
									,
									
            float
									 x
									,
									 float
									 y
									,
									 float
									 z
									)
									 {
									
        for
									 (
									int
									 i
									=
									0
									 ;
									 i
									<
									4
									 ;
									 i
									++)
									 {
									
            int
									 mi
									 =
									 mOffset
									 +
									 i
									;
									
            m
									[
									12
									 +
									 mi
									]
									 +=
									 m
									[
									mi
									]
									 *
									 x
									 +
									 m
									[
									4
									 +
									 mi
									]
									 *
									 y
									 +
									 m
									[
									8
									 +
									 mi
									]
									 *
									 z
									;
									
        }
									
    }
									

								

Bài viết tiếp theo sẽ thảo luận về một phép biến đổi rất quan trọng trong biến đổi tọa độ — quay. Matrix.rotateM


Bài viết này chủ yếu tập trung vào việc tính toán ma trận dịch chuyển và ma trận thu phóng trong quá trình biến đổi mô hình cũng như cách thực hiện mã nguồn tương ứng. Mặc dù phần còn lại về việc biến đổi tọa độ đỉnh chưa được đề cập chi tiếtbóng đá wap, nhưng cách tiếp cận phân tích tổng thể đã được trình bày rõ ràng. Các bài viết tiếp theo trong loạt bài này sẽ vẫn duy trì hướng tư duy này, và những độc giả tò mò có thể bắt đầu hành trình khám phá của riêng mình dựa trên phương pháp tương tự mà bài viết đã gợi ý.

——

(Kết thúc)

Các bài viết được chọn lọc khác


Bài viết gốclive casino, vui lòng ghi rõ nguồn và bao gồm mã QR bên dưới! Nếu không, từ chối tái bản!
Liên kết bài viết này: /ehh7t2ct.html
Hãy theo dõi tài khoản Weibo cá nhân của tôi: Tìm kiếm tên tôi "Trương Thiết Lệ" trên Weibo.
Tài khoản WeChat của tôi: tielei-blog (Trương Thiết Lệ)
Bài trước: Tại sao một số sách kỹ thuật lại khó đọc?
Bài sau: Tài năng có phải là một giả thuyết không?