0

WebGL và Three.js cho hệ thống thử đồ ảo

Giới thiệu

Với sự phát triển nhanh chóng của thương mại điện tử, kỳ vọng của người tiêu dùng đối với trải nghiệm mua sắm trực tuyến ngày càng tăng. Công nghệ thử đồ ảo, như một cầu nối kết nối mua sắm trực tuyến với trải nghiệm cửa hàng thực tế, đang thay đổi hoàn toàn cách người tiêu dùng mua quần áo, mỹ phẩm và phụ kiện. Bài viết này sẽ đi sâu vào cách sử dụng công nghệ WebGL và Three.js để xây dựng hệ thống thử đồ ảo hiệu suất cao, phân tích các thách thức kỹ thuật trong quá trình thực hiện và giải pháp của chúng.

Giá trị thị trường của công nghệ thử đồ ảo

Theo dữ liệu từ Grand View Research, quy mô thị trường AR/VR trong bán lẻ toàn cầu dự kiến sẽ đạt 120,45 tỷ đô la Mỹ vào năm 2025, với tốc độ tăng trưởng kép hàng năm là 68,5%. Là một kịch bản ứng dụng quan trọng, thử đồ ảo đang cải thiện đáng kể tỷ lệ chuyển đổi và giảm tỷ lệ hoàn trả:

  • Các nhà bán lẻ triển khai thử đồ ảo báo cáo tỷ lệ chuyển đổi tăng hơn 40%
  • Tỷ lệ hoàn trả trung bình giảm 25%, giảm đáng kể chi phí vận hành
  • Mức độ tương tác của người dùng tăng 60%, thời lượng phiên trung bình kéo dài gấp 2 lần

Kiến trúc cơ bản của WebGL và Three.js

Khả năng cơ bản của WebGL

WebGL là một API JavaScript cho phép hiển thị đồ họa 3D tương tác trong trình duyệt mà không cần plugin. Nó dựa trên OpenGL ES, sử dụng trực tiếp GPU để tăng tốc, có những ưu điểm sau:

// Ví dụ về shader cơ bản WebGL
const vertexShaderSource = `
  attribute vec4 aVertexPosition;
  uniform mat4 uModelViewMatrix;
  uniform mat4 uProjectionMatrix;
  void main() {
    gl_Position = uProjectionMatrix * uModelViewMatrix * aVertexPosition;
  }
`;

Vai trò của Three.js

Three.js là thư viện đóng gói cấp cao của WebGL, đơn giản hóa rất nhiều sự phức tạp của lập trình 3D:

// Ví dụ khởi tạo cảnh Three.js
// Tạo đối tượng cảnh Three.js, dùng để chứa tất cả đối tượng 3D, nguồn sáng và camera
const scene = new THREE.Scene();

// Tạo camera phối cảnh, các tham số lần lượt là:
// 1. Góc trường nhìn (FOV) - 75 độ, quyết định độ rộng của tầm nhìn
// 2. Tỉ lệ khung hình - sử dụng tỉ lệ của cửa sổ để đảm bảo không bị biến dạng khi hiển thị
// 3. Mặt phẳng cắt gần - 0.1, khoảng cách gần nhất mà camera có thể nhìn thấy
// 4. Mặt phẳng cắt xa - 1000, khoảng cách xa nhất mà camera có thể nhìn thấy
const camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);

// Tạo trình hiển thị WebGL, kích hoạt khử răng cưa (antialias) để làm mịn cạnh
const renderer = new THREE.WebGLRenderer({ antialias: true });

// Thiết lập kích thước canvas đầu ra của trình hiển thị bằng với kích thước cửa sổ trình duyệt hiện tại
renderer.setSize(window.innerWidth, window.innerHeight);

// Thêm phần tử DOM của trình hiển thị (canvas) vào thẻ body của tài liệu HTML
// Nhờ đó nội dung 3D có thể hiển thị trên trang web
document.body.appendChild(renderer.domElement);

Thực hiện kỹ thuật cốt lõi của hệ thống thử đồ ảo

1. Mô hình hóa và theo dõi cơ thể người

Mô hình cơ thể chính xác là nền tảng của thử đồ ảo. Chúng tôi áp dụng phương pháp phân lớp:

// Mã giả ước tính tư thế dựa trên TensorFlow.js
/**
 * Ước tính tư thế cơ thể từ luồng video và chuyển đổi thành mô hình tương thích Three.js
 * @param {HTMLVideoElement} video - Phần tử video chứa người
 * @return {Object} Dữ liệu mô hình Three.js đã chuyển đổi
 */
async function estimateBodyPose(video) {
  // Tải mô hình mạng thần kinh PoseNet
  // posenet.load() trả về một Promise, chứa mô hình ước tính tư thế đã được khởi tạo
  const net = await posenet.load();
  
  // Sử dụng mô hình PoseNet để ước tính tư thế của một người từ khung hình video
  // Phương thức estimateSinglePose phân tích khung hình video và trả về tọa độ các điểm chính
  // Tham số flipHorizontal đặt thành true có nghĩa là lật ngang đầu vào, giúp ước tính tư thế phù hợp hơn với góc nhìn selfie
  const pose = await net.estimateSinglePose(video, {
    flipHorizontal: true
  });
  
  // Chuyển đổi dữ liệu tư thế 2D từ PoseNet thành dữ liệu mô hình 3D có thể sử dụng trong Three.js
  // Hàm này (không được định nghĩa trong mã) chịu trách nhiệm ánh xạ các điểm chính vào bộ xương nhân vật 3D
  return convertPoseToThreeJSModel(pose);
}

2. Mô hình quần áo và mô phỏng vật lý

Hiển thị quần áo cần xem xét chất liệu, ánh sáng và đặc tính vật lý:

// Định nghĩa chất liệu quần áo
// Tạo đối tượng chất liệu dựa trên vật lý để mô phỏng chân thực vẻ ngoài và đặc tính quang học của vải
const clothMaterial = new THREE.MeshPhysicalMaterial({
  // Bản đồ màu cơ bản (khuếch tán), xác định màu sắc và mẫu cơ bản của vải
  map: textureLoader.load('fabric_diffuse.jpg'),
  // Bản đồ pháp tuyến, dùng để mô phỏng chi tiết lồi lõm trên bề mặt vải mà không tăng độ phức tạp hình học
  normalMap: textureLoader.load('fabric_normal.jpg'),
  // Bản đồ độ nhám, kiểm soát độ nhám của từng phần chất liệu, ảnh hưởng đến cách ánh sáng bị tán xạ
  roughnessMap: textureLoader.load('fabric_roughness.jpg'),
  // Bản đồ bóng môi trường (AO), tăng cường chi tiết nếp nhăn và bóng đổ, nâng cao cảm giác chân thực của vải
  aoMap: textureLoader.load('fabric_ao.jpg'),
  // Thiết lập chất liệu để hiển thị hai mặt, làm cho cả hai mặt của vải đều có thể nhìn thấy, phù hợp để mô phỏng vải mỏng
  side: THREE.DoubleSide,
  // Kích hoạt độ trong suốt, cho phép chất liệu có hiệu ứng trong suốt
  transparent: true,
  // Thiết lập mức độ ánh sáng truyền qua chất liệu, 0.15 biểu thị độ trong suốt nhẹ, mô phỏng như vải voan mỏng
  transmission: 0.15, // Mô phỏng độ trong suốt
  // Giá trị độ nhám tổng thể, 0.65 biểu thị độ nhám trung bình khá cao, hiệu ứng bề mặt vải điển hình
  roughness: 0.65,
  // Giá trị độ kim loại, 0.05 biểu thị gần như là chất liệu phi kim loại, phù hợp với hầu hết các loại vải
  metalness: 0.05,
});

3. Tương tác thời gian thực và phát hiện va chạm

Trải nghiệm thử đồ ảo mượt mà đòi hỏi phát hiện va chạm hiệu quả:

// Mã giả thuật toán phát hiện va chạm được tối ưu hóa
function detectCollisions(clothMesh, bodyMesh) {
  // Sử dụng thuật toán phân vùng không gian để tối ưu hóa phát hiện va chạm
  const octree = new THREE.Octree({
    undeferred: false,
    depthMax: 8
  });
  octree.add(bodyMesh);
  
  for (const vertex of clothMesh.geometry.vertices) {
    const collisions = octree.search(vertex, 0.5);
    if (collisions.length > 0) {
      // Xử lý phản ứng va chạm...
    }
  }
}

Chiến lược tối ưu hóa hiệu suất

Trong quá trình thực hiện, chúng tôi đã gặp một số thách thức hiệu suất nghiêm trọng, đặc biệt là trên thiết bị di động:

1. Thực hiện LOD (Level of Detail)

// Ví dụ thực hiện LOD
const lod = new THREE.LOD();
const highDetailModel = createHighDetailModel();
const mediumDetailModel = createMediumDetailModel();
const lowDetailModel = createLowDetailModel();

lod.addLevel(highDetailModel, 0);    // Khoảng cách gần
lod.addLevel(mediumDetailModel, 10); // Khoảng cách trung bình
lod.addLevel(lowDetailModel, 50);    // Khoảng cách xa
scene.add(lod);

2. Tối ưu hóa shader

Chúng tôi đã thực hiện tối ưu hóa cấp shader cho tính toán ánh sáng và bóng đổ:

// Ví dụ về shader đoạn được tối ưu hóa
precision mediump float;

// Dữ liệu ánh sáng được tính toán trước
uniform sampler2D uLightMap;
uniform sampler2D uBaseTexture;
varying vec2 vUv;

void main() {
  // Sử dụng bản đồ ánh sáng đã nướng sẵn thay vì tính toán thời gian thực
  vec4 lightingData = texture2D(uLightMap, vUv);
  vec4 baseColor = texture2D(uBaseTexture, vUv);
  
  gl_FragColor = baseColor * lightingData;
}

3. Tách luồng công việc

// Sử dụng Web Worker để giảm tải tính toán phức tạp
const physicsWorker = new Worker('physics-worker.js');

physicsWorker.postMessage({
  type: 'simulate',
  clothVertices: clothMesh.geometry.vertices,
  bodyModel: serializeBodyModel()
});

physicsWorker.onmessage = function(e) {
  updateClothGeometry(e.data.updatedVertices);
};

Hướng nghiên cứu mới nhất

Với sự tiến bộ không ngừng của học máy và đồ họa máy tính, chúng tôi đang khám phá các hướng mới sau:

  1. Dò tia được tăng tốc bởi mạng thần kinh - Sử dụng học sâu để giảm chi phí kết xuất dò tia
  2. Chuyển giao phong cách tùy chỉnh quần áo - Áp dụng thông minh các mẫu do người dùng tải lên vào mô hình quần áo 3D
  3. Trải nghiệm tương tác thực tế hỗn hợp (MR) - Trải nghiệm mua sắm hoàn toàn mới kết hợp công nghệ AR và VR

Kết luận và nền tảng trải nghiệm Demo

Công nghệ thử đồ ảo đang phát triển nhanh chóng, thông qua sự kết hợp của WebGL và Three.js, chúng ta có thể thực hiện trải nghiệm thử đồ 3D hiệu suất cao trong trình duyệt thông thường. Điều này không chỉ nâng cao trải nghiệm mua sắm của người tiêu dùng mà còn mang lại giá trị thương mại đáng kể cho các nhà bán lẻ.

Đây là hiệu ứng Demo đã được tối ưu hóa, những ai quan tâm có thể trải nghiệm, hoặc thông qua giải pháp để áp dụng trực tiếp công nghệ này vào nền tảng, vì đối với các nhà phát triển độc lập, khối lượng công việc phát triển một hệ thống ảo hoàn chỉnh là quá lớn.

Tài liệu tham khảo

  1. Fernando, R., & Kilgard, M. J. (2003). The Cg Tutorial: The definitive guide to programmable real-time graphics. Addison-Wesley Professional.
  2. Dirksen, J. (2018). Three.js Cookbook. Packt Publishing.
  3. Marschner, S., & Shirley, P. (2018). Fundamentals of Computer Graphics. CRC Press.
  4. WebGL Fundamentals. (2021). Retrieved from https://webglfundamentals.org/
  5. Three.js Documentation. (2023). Retrieved from https://threejs.org/docs/

All rights reserved

Viblo
Hãy đăng ký một tài khoản Viblo để nhận được nhiều bài viết thú vị hơn.
Đăng kí