---
title: "WebGL及Unity3D WebGL框架速览"
author: "Perrin Yong"
author_profile: https://www.pystone.net/profile/
published_by: "Perrin Yong"
canonical: https://www.pystone.net/notes/webgl-unity3d-framework-quick-reference/
type: note
content_role: unspecified
visibility: public
id_stability: rename-stable
source_path: "10-计算机、信息技术与工程/05-游戏图形与运行时/WebGL/WebGL及Unity3D WebGL框架速览.md"
content_hash: 0935a4e5e04fc7b173c383f394ed4c6422d8750e9a523e2d01a133a55ae9b6db
knowledge_version: 224c990773de.5fa8af6e39fa
site_commit: 224c990773de166d23a886306577dd90379529ce
notes_commit: 5fa8af6e39fa3891d1b9b4832bfa6c4e0ecaaf0a
---
### WebGL显示链路

```text
HTML/CSS/DOM(可选)
        │
        ▼            JS 引擎(V8/SpiderMonkey…)
JavaScript 业务逻辑 ──► **WebGL API (ES 2.0/3.0 语义)**
        │                    │   ↳ 生成 GPU 命令缓冲
        ▼                    ▼
  浏览器驱动层 ─────────► GPU 驱动(OpenGL ES / Metal)
                                   │
                                   ▼
                              帧缓冲 → 显示器
```

* **核心要点**
  1. HTML / DOM 只是创建 `<canvas>` 的容器；WebGL 本身完全脱离 DOM 渲染流程。
  2. WebGL 1/2 只是 **OpenGL ES 2.0/3.0 的 JavaScript 绑定**。API 调用被 JS 引擎打包为 GPU 命令。
  3. 所有顶点/片元运算都在 **开发者自编写的 GLSL ES 着色器** 中完成；没有固定功能管线。

---

### Unity3D与`.wasm`

| 目标                   | Unity 的做法                                                                                                                 | 结果                                 |
| -------------------- | ------------------------------------------------------------------------------------------------------------------------- | ---------------------------------- |
| **让 C#/C++ 逻辑在浏览器跑** | IL2CPP 把 C# ➜ C++ ➜ 交给 **Emscripten** 编译成 **WebAssembly (.wasm)**                                                         | 把 CPU 密集逻辑、物理、ECS 等全部搬进高性能 Wasm VM |
| **调用浏览器 API**        | Emscripten 生成 **Glue JS (`framework.js`)**，负责：• 加载 `.wasm`• 把 JS 字符串 ↔ Wasm 内存• 把 Wasm 函数导出给 JS（`Module.xxx`） | JS ↔ Wasm 像互调 DLL；渲染仍通过 `gl.*`     |
| **保证性能与安全**          | Wasm 经过 JIT → 机器码，沙盒隔离                                                                                                    | 速度接近原生，避免 JS 动态开销                  |

> **`.wasm` 处在链路里的位置**


```makefile
JavaScript Glue (framework.js)
	│   ↕ FFI(import/export)
	▼
WebAssembly VM (unity.wasm)
	│   ↕  调用 WebGL API / Audio / Input
	▼
GPU 驱动 …
```


> * **渲染指令**：Wasm 内部调用 Emscripten‑提供的 `glBindBuffer` 等函数，这些又回到浏览器的 WebGL 实现；因此 `.wasm` 主要承担 **CPU 侧游戏逻辑**，GPU 命令仍走 WebGL。
> * **生命周期**：下载 `.wasm` → `WebAssembly.instantiateStreaming()` ➜ `Module.onRuntimeInitialized` → 游戏开始。([Unity Documentation][1])

### Unity WebGL 小游戏 vs 纯微信小游戏：技术栈对照

| 维度       | **Unity WebGL 转小游戏**                                                                 | **原生微信小游戏（小游戏 IDE）**                          |
| -------- | ------------------------------------------------------------------------------------ | --------------------------------------------- |
| **主语言**  | C# (逻辑) + Wasm C++(编译后) + 少量 JS Glue                                                 | JavaScript/TypeScript                         |
| **运行时**  | `unity.wasm` + `framework.js` + **minigame‑unity‑webgl‑transform** 适配层 ([GitHub][2]) | WeChat Game Runtime（基于 QQ Game Engine），直接跑 JS |
| **渲染层**  | Unity 自带渲染管线 ➜ WebGL context（单 Canvas）                                               | 微信提供 `wx.createCanvas()` ➜ WebGL/2D context   |
| **脚本热更** | IL2CPP 编译期静态；热更需 AssetBundle / Lua / C# 热更新框架                                        | JS 热重载、分包加载                                   |
| **资源管线** | Unity Importer ➜ AssetBundle ➜ LZ4 压缩                                                | IDE & 自定义打包；纹理可 KTX2, Basis                   |
| **包体体积** | `.wasm` + 引擎数据 5‑15 MB 起；首包常借微信「分包加载」拆分                                              | JS+资源，一般 < 4 MB 首包，动态拉取其余                     |
| **多线程**  | WebAssembly Pthreads ⚠ 仅在特定浏览器/小游戏版本开放，需 `SharedArrayBuffer` 安全头；小游戏端仍在灰度            | Worker 线程可做下载/解析，但 WebGL context 只能在主线程       |
| **平台能力** | 通过转换工具桥接到 `wx.*` API (支付、分享、云开发)                                                     | 直接调 `wx.*`                                    |
| **调试**   | 浏览器 DevTools + WeChat DevTools (查看 wasm)                                             | WeChat DevTools (调 JS)                        |

> **使用场景取舍**
>
> * 如果你已有完整 Unity 项目、需要重用 C# 生态→ 适配方案节省大量人天。
> * 若从零做轻量小游戏、包体/加载时长极敏感→ JS/TS 原生小游戏更轻。

[1]: https://docs.unity3d.com/2021.3/Documentation/Manual/webgl-technical-overview.html?utm_source=chatgpt.com "Unity - Manual: Advanced overview"
[2]: https://github.com/wechat-miniprogram/minigame-unity-webgl-transform?utm_source=chatgpt.com "wechat-miniprogram/minigame-unity-webgl-transform - GitHub"


# WebGL及Unity3D WebGL框架速览
```mermaid
graph TD
  %% ───────── 物理硬件 ─────────
  subgraph Hardware
    CPU([CPU])
    GPU([GPU])
  end

  %% ───────── 操作系统抽象层 ─────────
  subgraph OS["Windows • macOS • Linux • Android …"]
    Kernel["内核 &amp; 驱动(文件、进程、GPU Driver)"]
    GraphicsAPI["平台图形 APIDirectX · OpenGL · Metal · Vulkan"]
  end
  Hardware --> Kernel
  Kernel --> GraphicsAPI

  %% ───────── 浏览器可移植代码库 ─────────
  subgraph Browser["浏览器通用代码库 (C/C++)"]
    Engine["排版 &amp; 渲染引擎Blink / WebKit / Gecko"]
    JSVM["JavaScript VMV8 / SpiderMonkey / JSC"]
    NetStack["网络栈HTTP/2 · TLS · Cache"]
    WebGL_Impl["WebGL 实现 + ANGLEOpenGL ES 语义 → 平台 API"]
  end
  GraphicsAPI --> WebGL_Impl
  Engine --> WebGL_Impl
  JSVM --> Engine
  NetStack --> Engine

  %% ───────── Web 内容运行时 ─────────
  subgraph Runtime["Web 内容"]
    HTML_Node["HTML / CSS"]
    JS_Node["JavaScript"]
    Wasm_Node["WebAssembly"]
  end
  HTML_Node --> Engine
  JS_Node --> JSVM
  Wasm_Node --> JSVM

  %% ───────── 宿主基座 / WebView ─────────
  subgraph Hosts["宿主基座 (App WebView)"]
    WeChat["WeChat Mini‑Game"]
    TikTok["TikTok In‑App Browser"]
    FB["Facebook In‑App Browser"]
  end
  Engine -. 嵌入 .-> Hosts
  Hosts -. 调用系统 WebView .-> Browser


```

![Web 平台与 WebGL 运行栈](/media/d2801687418797f17545.png)

---

> 浏览器跨平台的根本是 **“通用代码 + 薄适配”**，而 WebGL 跨平台靠 **标准 JS API + ANGLE 翻译层**；无论是桌面浏览器还是嵌入式 WebView（微信、抖音、Facebook），只要内核遵守同一规范并映射到本地 GPU 驱动，**同一份 Web 内容 & WebGL 代码即可无差别运行**。

## 1. 浏览器为何跨平台？

| 关键点              | 说明                                                                                                 |
| ---------------- | -------------------------------------------------------------------------------------------------- |
| **同一份 C/C++ 代码** | Chrome/Firefox/Safari 内核 95 % 以上用标准 C/C++ 实现。只需为不同 OS **重新编译（Clang/LLVM、MSVC、Xcode）**，就能得到本机可执行文件。 |
| **平台抽象层**        | 内核中有 *Platform* 模块，把文件、线程、网络、窗口、GPU 等统一抽象；各 OS 只写少量适配。                                             |
| **标准化 Web 语法**   | HTML5、CSSOM、ECMAScript 由 W3C/WHATWG/TC39 统一；渲染和 JS 行为在所有操作系统一致。                                    |

---

## 2. WebGL 为什么跨平台？

| 链条               | 作用                                                                                                                                          |
| ---------------- | ------------------------------------------------------------------------------------------------------------------------------------------- |
| **WebGL 规范**     | 定义 *OpenGL ES 2/3* 的 JS 绑定；写死函数名、状态机和 GLSL ES 行为。                                                                                           |
| **浏览器实现层**       | Blink/Gecko 不直接调用 OpenGL；而是先经过 **ANGLE**——一个把 OpenGL ES 调到 **DirectX / Metal / Vulkan / EGL** 的翻译库。所以 *同一段 JS WebGL 代码* 在任何系统都能落到可用的底层 API。 |
| **GPU 驱动负责最后一步** | 各厂商驱动把平台图形 API 指令变成本机指令；因此只要系统有合规 GPU 驱动，WebGL 就能跑。                                                                                         |

---

## 3. `.wasm`、JS、HTML 如何一起跑？

1. **HTML/CSS** ➜ 排版引擎（树 + 盒模型）。
2. **JS** ➜ JS VM (V8…) **解释 → JIT**，调用 DOM/Canvas/WebGL。
3. **WebAssembly** ➜ JS VM 中的 Wasm Runtime **验证 → baseline JIT → 优化 JIT** ➜ 本机机器码。
4. **JS ↔ Wasm ↔ Web APIs (含 WebGL)** 通过导入/导出函数与共享内存交互。

> JS 与 Wasm 都 **跑在同一 JS 引擎里**，因此跨平台能力继承自浏览器本身。

---

## 4. 为何同一 WebGL 可跑在微信/抖音/FB？

* **这些 App 内嵌系统 WebView**（Android WebView、iOS WKWebView、Chromium Embedded），本质还是浏览器内核 ➜ 承袭同一跨平台链条。
* 宿主只额外提供 JS Bridge (`wx.*`, `tiktok.*`) → 业务层调用，不影响 WebGL API。
* 仅需注意 **WebView 版本差异**（低版本可能缺 WebGL 2 / 线程 / WebAssembly SIMD）。

---
