☰
floorplan-3d 的 2D→3D 电影级切换:相机球坐标插值与墙体从地面升起的动画原理
2026/10/4 6:52:23 网站建设 项目流程

floorplan-3d 的 2D→3D 电影级切换:相机球坐标插值与墙体从地面升起的动画原理

【免费下载链接】floorplan-3d项目地址: https://gitcode.com/gh_mirrors/fl/floorplan-3d

🏠floorplan-3d是一个纯前端的户型装修设计工具,整个应用只有一个index.html,无需构建、打开即用。它的招牌体验是:在 2D 平面图上摆好家具后,按T键一键切换到 Three.js 3D 场景,镜头会像电影运镜一样从正俯视角平滑环绕到斜视角度,同时墙体从地面"生长"升起、家具依次长出来。本文将拆解这套2D→3D 切换动画背后的两个核心技术:相机球坐标插值与墙体升起动画。

floorplan-3d 项目说明

快速开始:3 分钟跑起这个 3D 户型工具 🚀

仓库是只读的,克隆下来直接用浏览器打开即可:

git clone https://gitcode.com/gh_mirrors/fl/floorplan-3d cd floorplan-3d

然后双击index.html即可(Three.js 通过 CDN 加载,首次打开 3D 场景需要联网)。完整功能说明见 README.md,项目采用 MIT 协议。

💡 切到 3D 后,右侧房间列表点击任意房间,镜头还会自动"飞"过去——这一招同样基于本文的球坐标插值。

切换动画的三步拆解 🎬

进入 3D 的入口是View3D.enter(),位于 index.html。它把整段动画拆成三个协同的步骤:

第一步:让 3D 起点与 2D 画面"完全重合"

动画的起点位姿由planPose()计算,见 index.html。它根据当前 2D 视口中心和缩放比例,反推出一个正俯视的透视相机高度——在这个高度下,3D 相机看到的范围恰好等于 2D 平面图当前显示的范围。

于是切换时 3D 画布与 2D 平面图像素级重合,先做 420ms 交叉淡入(await wait(420)),用户完全察觉不到"两个世界"的存在。这是"电影级"观感的第一块基石:起点无跳变。

第二步:相机球坐标插值——镜头走弧线而非直线

进入 3D 后,镜头要从"正上方俯视"变到"斜 45° 鸟瞰"。如果直接对相机坐标做线性插值,镜头会生硬地直线平移,甚至穿过建筑。

关键实现在camTween(),位于 index.html:

  • 先把起止两个相机位置,都换算成相对于注视点的球坐标:半径radius(距离)、仰角phi、方位角theta;
  • 三个分量各自做插值,再用setFromSpherical转回世界坐标。

这样镜头实际是沿着以注视点为球心的球面弧线倾斜环绕过去,轨迹天然不穿墙、节奏自然,正是 OrbitControls 交互时的运动方式,两者无缝衔接。

还有一个细节:方位角差值用Math.atan2(sin, cos)归一化到 [-π, π],避免绕远路多转一圈。

整个插值过程由缓动函数驱动(见 index.html):前半段三次方加速、后半段三次方减速(ease-in-out cubic),起步和收尾都柔和平稳。

第三步:墙体从地面升起 + 家具分批"生长"

进入 3D 的 1700ms 动画窗口内,grow和furnGrow两个进度变量被编排成错峰时间轴(见 index.html):

轨道时间轴作用
相机插值0 ~ 85%俯视角环绕到斜视角度
grow墙体生长10% ~ 65%墙体、窗户从地面升起
furnGrow家具生长45% ~ 95%家具、灯具随后长出来

"生长"的实现非常巧妙,applyGrow()在 index.html:它不逐块缩放墙体,而是把整个建筑组archUp的 Y 轴缩放设为grow,家具组furnG同理。模型底部都贴着地面(y=0),所以 Y 缩放的效果就是所有墙体、窗框从地面统一升起——一行代码实现全局生长动画。

退出 3D 时,exit()把整套流程倒放:相机沿弧线回到正俯视,墙体与家具反向"压平",等 3D 画面再次与 2D 完全重合后才淡出画布(index.html),全程无跳切。

点击房间自动飞行:同一套插值的复用 ✈️

3D 右侧房间列表点击某个房间时,会触发flyToRoom()(index.html):

  1. 计算房间外接矩形中心作为注视点,按房间尺寸推算合适的观察距离;
  2. 保持当前相机方位方向,让镜头从"你正在看的位置"自然飞向房间。

主循环里每帧调用同一个camTween()(index.html),900ms 的飞行同样走球面弧线——进入/退出/飞行三类运镜共享一套插值函数,是典型的"单一事实来源"设计,行为一致且容易调参。

小结:为什么这套动画"电影感" 🎞️

技巧解决的问题
起点与 2D 视口完全重合 + 交叉淡入切换无跳变,两个世界无缝衔接
球坐标插值代替线性插值镜头走弧线,不穿墙、不呆板
缓动函数 + 错峰时间轴相机先行、墙体后起、家具再跟上,节奏像分镜
整组 Y 轴缩放实现"生长"一行代码让全屋墙体从地面升起

这套2D→3D 相机球坐标插值方案不依赖任何动画库,全部基于 Three.js 原生 API,非常适合想在自己的 Three.js 项目里复刻"平面图飞入 3D"效果的朋友参考。核心代码都集中在 index.html 的"相机位姿 / 动画"区块,不到百行,值得逐行品读。

【免费下载链接】floorplan-3d项目地址: https://gitcode.com/gh_mirrors/fl/floorplan-3d

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询