加载应用…
云澜 Clyune Clyune Component Gallery · 中文

Mirror Floor · How it works & code

Reflect the object across the floor and place the copy below the floor, then make the floor semi-transparent to create the illusion of a reflection.

Runtime logic

Visiting `/threejs/mirror-floor`, DemoHost lazy-loads `demos/kits/kit-three.js` (registry `mod: 'kit-three'`) and calls `mount(host, { variant: 'mirror-floor' })`. mount resolves the variant to family `mirror-floor`; `withControls` builds the control panel (6 presets + sliders). `createThreeStage` sets up WebGLRenderer, Scene, PerspectiveCamera and OrbitControls, plus the info panel. The family’s `build(S)` initialises state and returns the per-frame callback. Every `requestAnimationFrame`: read controls, advance a speed-scaled clock (dt ≤ 50 ms), run the frame callback; returned readouts go to the info panel. Changing parameters: colour/speed/size apply live; structural ones remount; leaving the page cancels rAF, removes listeners and frees resources.

Environment

Canvas 2D: 2D canvas drawing; WebGL (three.js): WebGL through three.js WebGLRenderer; requestAnimationFrame: Display-synced animation loop; ResizeObserver: Canvas follows container size; Pointer Events: Unified mouse/touch/pen events; devicePixelRatio: Crisp HiDPI rendering (capped at 2×) · react 18.3.1, react-router-dom 6.30.6, vite 5.4.21, three 0.170.0

Dependencies

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

Imported APIs

withControls — Wraps the demo in the shared control panel (presets, sliders, reset); hot-updates or remounts on change; paramsFromSpec — Turns the spec (colour/speed/size/count/extras) into control-panel parameter definitions; createThreeStage — Shared three.js stage: WebGLRenderer, scene, perspective camera, OrbitControls, auto framing and render loop; addLights — Adds ambient + key + fill lights; THREE — three.js namespace; fmt — Number formatting (fixed decimals); F — Formula block HTML; S.get — Reads current control values; S.onFrame — Registers a per-frame callback; its return value feeds the info panel; THREE.MeshStandardMaterial — PBR standard material; THREE.Mesh — Mesh (geometry + material); THREE.SphereGeometry — Sphere geometry; THREE.CircleGeometry — Circle geometry; THREE.RingGeometry — Ring geometry; THREE.MeshBasicMaterial — Unlit material; THREE.DoubleSide — Render both faces

Source code

frontend/src/demos/kits/kit-three.js: FAM.mirror-floor (L316-L343)

Code walkthrough

L317-317: Control definitions (colour/speed/size/count/extras): Ball Color, Float Speed, ball radius, Floor Reflectivity. L318-318: Preset buttons: name → parameter overrides (6). L319-319: 3D framing radius. L319-319: Camera target. L320-328: Info-panel content: live rows(v), formula, notes, params, steps. L329-342: Init function: sets up state and returns the per-frame callback: creates three.js objects `MeshStandardMaterial`, `Mesh`, `SphereGeometry`, `CircleGeometry`, `RingGeometry`, `MeshBasicMaterial` …; math via `Math.sin`; returns readouts `y`, `ym`, `gap`, `r`, `refl`, `Tp` to the info panel.

Principles

About the ground y = y₀ Mirror: y′ = 2·y₀ − y y(t) = 0.35 + 0.3·sin(1.6·t) Real mirror reflection calculations are expensive, and a small technique is often used in the game: putting objects into the game About a ground flip copy One is placed under the floor, and the floor is translucent, and it looks like a reflection of the ground. 镜像点满足:到地面的距离与原物体相等、方向相反,所以 y′ = 2y₀ − y。The ball goes up, the reflection goes down.

Open the interactive demo · GitHub