加载应用…
云澜 Clyune 云澜组件库 Clyune Component Gallery · English

几何体画廊 · 原理与代码

内置几何体与射线拾取。

运行逻辑

访问 `/threejs/gallery` 时,DemoHost 按 registry 的 `mod: 'gallery'` 懒加载 `demos/gallery.js`,调用 `mountGallery(host, { variant: 'gallery' })`。 `createThreeStage` 创建 WebGLRenderer、Scene、PerspectiveCamera 与 OrbitControls,并接上信息面板。 模块用 `S.onFrame` 注册每帧回调。 每个 `requestAnimationFrame`:读取控件值,按速度缩放模拟时钟(dt 上限 50 ms),执行帧回调绘制;返回的读数写入信息面板。 改变参数:颜色/速度/大小等即时生效,需要重建的参数触发重新挂载;离开页面时取消 rAF、移除监听并释放资源。

运行环境

Canvas 2D: 2D 画布绘图; WebGL (three.js): three.js 通过 WebGLRenderer 使用 WebGL; requestAnimationFrame: 与屏幕刷新同步的动画循环; ResizeObserver: 画布随容器尺寸自适应; Pointer Events: 鼠标/触摸/触控笔统一事件; devicePixelRatio: HiDPI 清晰渲染(上限 2×) · react 18.3.1, react-router-dom 6.30.6, vite 5.4.21, three 0.170.0

引入的组件与依赖

three 0.170.0, three/addons/controls/OrbitControls.js 0.170.0, react 18.3.1

引入的组件函数

createThreeStage — 共享 Three.js 舞台:WebGLRenderer、场景、透视相机、OrbitControls、自适应取景与渲染循环; addLights — 添加环境光 + 主光 + 补光; THREE — three.js 命名空间; fmt — 数字格式化(固定小数位); triCount — 统计几何体三角形数量; F — 公式块 HTML; S.setFitRadius — 调整 3D 取景半径; S.onFrame — 注册每帧回调,返回值进入信息面板读数; THREE.BoxGeometry — 立方体几何体; THREE.SphereGeometry — 球体几何体; THREE.ConeGeometry — 圆锥几何体; THREE.TorusGeometry — 圆环面几何体; THREE.OctahedronGeometry — 八面体几何体; THREE.IcosahedronGeometry — 二十面体几何体; THREE.Mesh — 网格物体(几何体 + 材质); THREE.MeshStandardMaterial — PBR 标准材质; THREE.GridHelper — 网格辅助线; THREE.Raycaster — 射线拾取; THREE.Vector2 — 二维向量; THREE.Color — 颜色对象

本 demo 代码

frontend/src/demos/gallery.js: gallery.js (L1-L89)

代码解释

L4-10: `PARAMS_SPEC`(常量/表)。 L11-18: `SPECS`(常量/表);创建 three.js 对象 `BoxGeometry`, `SphereGeometry`, `ConeGeometry`, `TorusGeometry`, `OctahedronGeometry`, `IcosahedronGeometry`。 L19-34: `DOC`(常量/表)。 L36-89: `mountGallery`(函数)。 L37-59: 定义 `S`;创建 three.js 对象 `Mesh`, `MeshStandardMaterial`, `GridHelper`, `Raycaster`, `Vector2`;数学计算用到 `Math.max`, `Math.ceil`, `Math.floor`。 L60-88: 定义 `onUp`;创建 three.js 对象 `Color`;数学计算用到 `Math.hypot`;返回读数 `name`, `verts`, `tris`, `ctor`, `s`, `layout` 给信息面板。

原理

射线 R(t) = 相机位置 + t · 方向 鼠标像素 → NDC:x = 2·px/W − 1,y = 1 − 2·py/H Three.js 内置了很多 几何体 ,它们都由很多三角形拼成;分段越多越圆滑,但三角形也越多。 点击时,程序把鼠标位置换算成 −1~1 的“标准坐标”,从相机朝这个方向发出一条 射线 Raycaster ,第一个被射线穿过的物体就是你点中的那个,然后给它加上自发光高亮。

打开交互演示 · GitHub