用 AI 和 Three.js 做一堂 3D 互动课:从能量课本到可运行原型
从四轮提示词做起,补齐八类储能探索、纸面展开与热饮/电池五镜头演示,再按完整教学流程实走验证;附源码与修复记录。

一本书从书架落下,最后静止在地上。它原本的重力势能去了哪里?把这个问题做成可预测、可操作、可解释的课件,就是一次具体的 3D 互动课程设计任务。
Techartist 发布的 3D 网页课件 Every Joule(每一焦耳)第一课,通过浏览器内的 Three.js 场景,把教科书插图做成了一本插图会从纸面立起的“纸雕互动书”。据原作者自述,课件使用 Opus 5.5 与 Three.js 构建;全书规划 10 课,当前公开且实际可体验的为第一课(教师备课页面注明面向 14–16 岁学生)。画面中包含从书架坠落的书本与右侧一组发光的“能量罐”,让学生观察重力势能减少并流向动能,最后在撞击后分散到书本、地面与周围空气热储存中的过程。
整体采用黑白纸面线稿设计,高亮彩色专门留给能量储存与传递路径。
这份指南的四轮中文提示词已由 Codex 从空目录顺序执行,做出了可运行的 Three.js 课件,并保留了各轮代码与实操记录。原作者没有公开开发提示词与耗时,下面的步骤为本指南另行设计。照做四轮会得到书本下落实验;要补齐原课的八类储能探索,还需要后面的补充轮。
让 AI 协助开发 3D 课件时,一个常见的认知偏差是把“立体视觉效果”等同于“教学目标达成”。如果仅凭泛化指令生成课件,容易得到模型位移与物理记账逻辑脱节的代码;如果页面缺乏明确的任务约束,学生往往只将三维场景当作随意拖动的玩具,难以形成“高度降低势能减少、动能增加”的物理联系。
Techartist 的教学闭环:预测、演示、操作与解释
把纸质图解搬进 3D 空间,核心不在于模型有多繁复,而在于如何通过任务序列让三维运动辅助物理理解。Every Joule 第一课围绕五个教学动作展开(原课包含预测、演示、操作、解释以及点亮 8 类储能的小挑战):
实际教学中建议教师引导学生“先预测再观察演示”,原课页面允许各模块独立体验,视频展示了这些操作。
1. 预测(Predict):在观察前暴露前概念
课件左页给出了一个针对书本落地的单选题:
“书本从书架掉落并着地。它原有的能量现在去哪了?”(The book falls off the shelf and lands. Where is its energy now?)
选项:被用光了(It has been used up) / 在周围的热储存中(In the thermal stores around it) / 依然在重力势能里(Still in its gravitational store)
以书落地为例,学生在未系统学习前往往直觉选择“能量被用光了”。教学上建议教师引导学生先做选择,将预测作为明确自身前概念的契机;若跳过思考直接观看动画,学生容易仅关注三维动效而忽略背后的守恒问题。
2. 演示(Watch):受控视角下的物理事实
触发演示时,镜头平滑切入场景:先给热饮特写展示热储存,接着切到电池剖面展示化学储存,随后转入低机位侧视观察书架与书本。在书本下落过程中,随着高度降低,重力势能(Gravitational Store)罐相应减少,动能(Kinetic Store)罐随之增加;着地碰撞后动能归零。三维镜头的作用是将下落高度 h 与能量罐的数值变化纳在同一视野中,建立几何空间与能量增减的直观联系。
3. 操作(Try):在场景中建立储能映射
演示告一段落后,场景进入可交互状态。学生可以点击场景中的具体物品(如高处的书本、热饮、拉伸弹簧、电池等)或下方按钮,点亮右页对应的能量罐。这个阶段的设计目标是让学生将具体物品与 8 类能量储存建立一一映射,并非让学生进行控制变量实验。
4. 解释(Explain):翻开纸片对比认知
左页设计了“Why? (lift the flap)”折叠纸片。学生点击掀开纸片后,可阅读原课给出的一段原理解释(以下为中文意译):
“下落时,书本的重力势能排空并转入动能;着地时,该能量转移到书本、地板与空气的热储存中,伴随部分声音传播。能量并未被消耗用尽,而是分散到了难以利用的地方。”
该解释针对预测题中“被用光了”这一典型直觉,用能量耗散的视角帮助学生建立“机械能转化为环境热储存”的守恒认识。
5. 挑战(Challenge):找全 8 类储能的任务反馈
在基础认知之外,原课还设置了一个小挑战:“点亮每一个罐子:找全所有 8 类储能”(Light every jar: find all eight stores)。学生需在场景中探索并找齐全部储能类型,获得即时的探索反馈,形成完整的学习闭环。
物理内核与记账隐喻:能量不是流体
在着手编写代码前,必须先厘清两个容易在动画制作中失真的物理与教学概念。
能量罐是“记账账户”,不是实体容器
本课沿用储能与传递途径(Stores and Pathways)模型来记录系统的能量变化:
- 储存(Stores):系统在特定物理状态下保存能量的方式(如动能、重力势能、弹性势能、热储存/内能、化学能、磁储存、静电储存、核能)。
- 途径(Pathways):能量在不同储存之间转移的过程机制(如机械做功、电流做功、热传递、辐射)。
课件中发光的“能量罐”以及物体与罐之间流动的光线,都属于便于教学观察的视觉隐喻,能量罐与流动光效本身均不是实体物质。区分储能与途径可以结合具体例子:
- 电池内部保存的是化学储能(Chemical Store);当接入电路点亮灯泡时,电路中传导能量的过程属于电流做功途径(Electrical Work Pathway),而非电池里储存着“电流”;
- 用毛皮摩擦过的气球则属于静电储能(Electrostatic Store)。
8 类储能是本课基于特定教学大纲(如 OCR J259)采用的分类方案。原课教师页明确注明,不同课程标准口径各异:例如 Cambridge IGCSE 仅列出 7 类储能(未将磁储存单列),而 AQA 规范正文并未逐一命名这 8 类储能。在课件设计中应将其呈现为特定教学模型的选择,而非放之四海皆准的唯一标准。
本指南的简化教学物理模型
本指南采用无空气阻力的自由落体加速模型作为独立教学原型的物理方案:
- 近地面匀强重力场中,重力场强设为 g = 9.8 N/kg(部分教材采用 10 N/kg,课件中可作为参数切换)。
- 以书落地静止时的质心高度为零势能基准,y 表示书底离地的间隙;书本质量 m = 1.0 kg、书架初始高度 h0 = 1.5 m 均为教学设定的参考值(原课教师页说明现实中并无标准书重与架高)。
- 书本从书架静止释放后,在重力作用下做初速度为 0 的加速下落运动(并非匀速下落)。初始静止时的重力势能: Ep = m · g · h0 = 1.0 × 9.8 × 1.5 = 14.7 J (Every Joule 页面显示为取整数值 15 J。在工程实现中,代码内部应使用 14.7 J 精确计算,UI 可显示取整数值)。
- 下落到高度 y 时: Ep(y) = m · g · y Ek(y) = m · g · (h0 − y) 下落全程机械能总量 Ep + Ek 严格保持 14.7 J 守恒。
- 落地瞬间(y = 0):碰撞变形以及伴随的声音耗散都被本指南模型简化为瞬时完成过程。书本动能归零,系统全部 14.7 J 记入书本、地面与周围环境的热储存(内能)中。教学中需向学生说明:声音是碰撞发生时通过机械功扰动空气传递能量的途径,最终同样耗散在周围环境的热储存中,并不是在 14.7 J 热内能之外另算一份额外能量。
这里的 Eth 只记本次下落造成的内能增量;初始记为 0 J,不表示书、地板和空气原本没有内能。
默认参数下,书架上 14.70 J 全在重力势能中;下降一半路程时,势能和动能各 7.35 J;落地静止后,14.70 J 全部计入物体及环境内能。三项相加始终为 14.70 J。
书的位置变了,三项能量怎样一起变?
基于自由下落无阻力简化教学模型(m = 1.0 kg, h₀ = 1.5 m, g = 9.8 N/kg)。本指南的二维状态示意;滑块表示已下降距离占比,不表示时间。图中位置和三项读数来自同一状态。
同一套记账:书架上 14.70 J 势能 → 路程一半时势能、动能各 7.35 J → 落地静止后 14.70 J 计入物体及环境内能。三项合计保持 14.70 J。
避开工程陷阱:单一数据源(Single Source of Truth)
初学者指挥 AI 写三维交互课件时,最容易出现代码解耦失控:
- AI 用
requestAnimationFrame写了书本下落的网格位移; - 另外用
setInterval写了一个数字从 15 倒数到 0 的计时器; - 能量条的高低又绑在了一个 CSS 渐变动画上。
一旦浏览器发生掉帧,就会出现书已经砸到了地面,而能量罐还停在半空显示 7 J 的尴尬穿帮。
核心工程设计:动画与数值必须派生自统一的物理状态计算。
需要特别注意:归一化变量 progress 定义为已下降距离占初始下落高度的比例(即 (h0 - y) / h0,取值范围 0.0 到 1.0),而非下落时间的简单百分比。
- 物理时间与播放映射:在无阻力自由落体中,物理总时长由加速度决定:
freeFallTime = Math.sqrt(2 * h0 / g)。当代入h0 = 1.5 m, g = 9.8 N/kg时,真实下落时长仅约 0.55 秒。这一速度对课堂观察过快,因此教学演示常设置放慢的展示时长(如displayDuration = 3.0 s)。播放时,动画播放流逝的归一化时间tau = elapsed / displayDuration映射到物理时间t = tau * freeFallTime,再通过初速度为 0 的匀加速位移公式派生出路程比例:progress = Math.min(1.0, Math.max(0.0, (t / freeFallTime) ** 2)) - 手动滑块的作用:页面中的手动滑块允许学生按距离进度
progress逐步查看不同高度下的静态能量切片,便于细致比对,而不是将其伪装成反转时间的真实物理实验。 - 状态结构:除了位置进度外,系统还需独立维护质量与高度、播放/暂停状态以及学生的预测状态;相机机位也可依据下落进度插值跟随,不必强求“全局仅用唯一标量”。
状态派生函数必须接收动态参数,并对边界与非法输入进行防御处理:
// 物理状态派生函数:接收进度、质量、重力场强与初始高度
function computePhysicsState(progress, m = 1.0, g = 9.8, h0 = 1.5) {
// 参数合法性防御
const validM = Number.isFinite(m) && m > 0 ? m : 1.0;
const validG = Number.isFinite(g) && g > 0 ? g : 9.8;
const validH0 = Number.isFinite(h0) && h0 > 0 ? h0 : 1.5;
// progress 强制截断到 [0, 1],代表已下降距离占 h0 的比例
const p = Math.min(1.0, Math.max(0.0, Number.isFinite(progress) ? progress : 0.0));
const total = validM * validG * validH0;
const y = validH0 * (1.0 - p); // 书底距离地面的高度
const ep = validM * validG * y;
const ek = p < 1.0 ? Math.max(0.0, total - ep) : 0.0;
const eth = p >= 1.0 ? total : 0.0;
return { progress: p, y, ep, ek, eth, total };
}
在 3D 渲染中,还需严格区分物理几何坐标与网格中心坐标:
若书本网格长方体厚度为 b、几何体中心为原点,物理高度 y 代表书本底面距离地面的间隙(以书落地静止时的质心高度为零势能基准)。在渲染网格时,模型的世界坐标应为 bookMesh.position.y = y + b / 2(或将模型放入底面为原点的 Group 中)。当书在架上时 y = h0,书底恰好平贴在高度为 h0 的书架面上;落地时 y = 0,书底接触地面 center.y = b / 2,消除初始悬空与穿模陷阱。此外,场景并不需要复杂的 3D 刚体碰撞模拟:将书本置于书架边缘释放或移走托板仅是触发动画的形式,不能让书本在处于托板内部时直接穿透木板。
分轮实施:从空白目录搭起独立原型
不要尝试用一段漫长的大提示词要求 AI 一次性生成完整的 3D 课件。大语言模型在同时处理三维几何构建、光照材质、物理计算、DOM 交互与界面排版时,极易顾此失彼。
正确的路径是分轮演进(Iterative Delivery):每一轮只做一件事,验证可用后再给下一轮提示词。
在电脑终端中先检查 Node.js 与 npm 环境:
node --version
npm --version
当前 Vite 官方文档要求 Node.js 版本为 20.19+ 或 22.12+。建议使用当前的 Node.js LTS 版本并确认版本兼容。随后在终端中初始化项目并安装依赖:
mkdir energy-interactive-lesson
cd energy-interactive-lesson
npm init -y
npm install three
npm install -D vite
安装完成后,在具备工作区文件编辑能力的 AI 编程工具中打开这个 energy-interactive-lesson 文件夹。各轮提示词均要求工具直接在工作区中创建或更新对应文件;若在仅支持纯对话的网页聊天窗口中使用,需按文件名将生成的完整代码手动复制替换到对应文件中。
项目基准文件结构如下:
energy-interactive-lesson/
├── index.html
├── package.json
├── package-lock.json
├── style.css
└── main.js
保留生成的 package-lock.json,以便后续通过 npm ci 可靠复现环境,让后续安装沿用本次实际记录的依赖版本。在 index.html 中必须通过 <script type="module" src="/main.js"></script> 引入模块脚本,并通过 <link rel="stylesheet" href="/style.css"> 关联样式。
每轮完成后先按验收点操作;有问题就把实际现象、控制台报错和相关文件交回同一会话修复,验收通过后再发送下一轮。
第一轮:跑通物理内核与最小 3D 场景
提示词说明:以下提示词由本指南独立设计,并非原作者未公开的原始指令。本次已由 Codex 在空白目录逐轮读取执行并完成浏览器实操验收,输入存入
implementation/prompts/,每轮均保留完整代码快照;但这不代表任意模型单次无干预即可得到完全相同代码。读者实操时中英文选其一发送,对照每轮验收点与排障记录确认无误后再进入下一轮。
中文提示词(第 1 轮) · 展开查看与复制
你是一个精通物理教学与 Three.js 的前端工程师。请为我构建一个“物理能量转换互动课件”的极简原型。
【技术栈】
- 原生 JavaScript (ES Modules) + Three.js + Vite。
- 根目录下包含 index.html, style.css, main.js。index.html 需通过 module script 引入 main.js 并链接 style.css。
【教学与物理规则】
1. 物理参数与坐标:
- 设定书本质量 m = 1.0 kg,初始书架高度 h0 = 1.5 m,重力场强 g = 9.8 N/kg。
- 能量总量 total = m * g * h0 = 14.7 J。
- 书本模型长方体厚度设定为 b = 0.2 m。物理高度 y 代表书底距离地面的高度;渲染时模型中心坐标为 center.y = y + b / 2。
- 书架板上表面位于 y = 1.5 m。初始时书底落在书架上(center.y = 1.6 m);落地时 y = 0 m,书底落在地面上(center.y = 0.1 m),严禁穿模或悬空。
2. 能量记账与状态派生:
- 定义 progress 为已下落距离占初始高度的比例(取值范围 0.0 到 1.0)。
- 下落阶段(progress < 1.0):y = h0 * (1.0 - progress),Ep = m * g * y,Ek = total - Ep,Eth = 0。
- 落地瞬间(progress >= 1.0):碰撞与声音耗散简化为瞬时完成,y = 0,Ep = 0,Ek = 0,Eth = total = 14.7 J。
- 派生函数 computePhysicsState(progress, m, g, h0) 需对参数做合法性检查与 progress 截断(0 到 1)。
3. 真实物理与播放时长映射:
- 自由落体总时间 freeFallTime = Math.sqrt(2 * h0 / g) ≈ 0.55 s。
- 为便于教学观察,演示播放时间设为 displayDuration = 3.0 s。播放过程中物理时间 t = (elapsed / displayDuration) * freeFallTime,位移比例 progress = Math.min(1.0, (t / freeFallTime) ** 2)。
- 手动滑块直接控制路程比例 progress,供学生逐步查看各高度状态。
【界面与 3D 场景】
1. 页面左侧:放置 3 个清晰的 HTML 能量罐(重力势能 Ep、动能 Ek、热内能 Eth),实时显示当前数值(保留 2 位小数)与高度填充百分比。
2. 页面右侧:Three.js 画布,包含透视相机、环境光/平行光、地面网格(y = 0)、位于架子边缘的书架与书本长方体。
3. 交互控件:
- 一个滑块(Range Input,0 到 100%),拖动时同步更新书本高度与能量罐;
- 真实可见的 HTML “释放书本”(Drop)与“重置”(Reset)按钮,支持鼠标点击与键盘(Tab/Enter/Space)无障碍操作。
请在当前项目工作区创建完整的 index.html、style.css 和 main.js。若无法写入文件,请按文件名输出完整代码,供我保存。
English Prompt (Round 1) · 展开查看与复制
You are a front-end engineer proficient in physics pedagogy and Three.js. Please build a minimal prototype for a "3D Interactive Energy Transformation Lesson".
[Tech Stack]
- Vanilla JavaScript (ES Modules) + Three.js + Vite.
- Root directory must contain index.html, style.css, main.js. index.html must load main.js via module script and link style.css.
[Pedagogy & Physics Rules]
1. Physical Parameters & Coordinates:
- Parameters: mass m = 1.0 kg, initial shelf height h0 = 1.5 m, gravitational field strength g = 9.8 N/kg.
- Total energy: total = m * g * h0 = 14.7 J.
- Book mesh thickness b = 0.2 m. Physical height y represents distance from book bottom to ground. Mesh center is rendered at center.y = y + b / 2.
- Shelf surface is at y = 1.5 m. Initially the book rests flush on the shelf (center.y = 1.6 m); at ground y = 0 m (center.y = 0.1 m). Avoid clipping through ground or floating.
2. Energy Accounting & State Derivation:
- Define progress as fallen distance ratio relative to h0 (clamped between 0.0 and 1.0).
- In-flight (progress < 1.0): y = h0 * (1.0 - progress), Ep = m * g * y, Ek = total - Ep, Eth = 0.
- On impact (progress >= 1.0): impact deformation and sound dissipation are modeled as instantaneous, y = 0, Ep = 0, Ek = 0, Eth = total = 14.7 J.
- computePhysicsState(progress, m, g, h0) must validate parameters and clamp progress to [0, 1].
3. Real Physics & Display Timing:
- Real free-fall duration: freeFallTime = Math.sqrt(2 * h0 / g) ≈ 0.55 s.
- For pedagogical observation, set animated displayDuration = 3.0 s. During playback, physical time t = (elapsed / displayDuration) * freeFallTime, and progress = Math.min(1.0, (t / freeFallTime) ** 2).
- A manual slider directly adjusts distance progress to allow stepping through height states.
[UI & 3D Scene Requirements]
1. Left panel: 3 visible HTML energy jars (Gravitational Ep, Kinetic Ek, Thermal Eth) showing real-time values (2 decimal places) and proportional bar fills.
2. Right panel: Three.js canvas featuring PerspectiveCamera, AmbientLight, DirectionalLight, ground plane at y = 0, a shelf, and the book mesh placed at the shelf edge.
3. Controls:
- A slider (0 to 100%) to inspect progress manually.
- Real, visible HTML "Drop Book" and "Reset" buttons, fully accessible via mouse and keyboard (Tab/Enter/Space).
Create complete index.html, style.css, and main.js files in the current project workspace. If you cannot write files, output the complete code under each filename so I can save it.
验收与调试(第 1 轮)
在终端中启动开发服务器:
npx vite
在浏览器中打开提示的本地地址(通常为 http://localhost:5173)。
- 通过标准:
- 页面打开正常显示,左侧呈现 3 个能量条与数值,右侧 3D 场景中书本平稳停在书架上,书底与架面紧贴。
- 拖动下方进度滑块,书本随着路程比例平滑下落,左侧 Ep 减少、Ek 增加,下落中机械能总和始终保持 14.70 J。
- 点击“释放书本”,书本在约 3 秒的教学展示时间内做平滑加速下落;着地瞬间书底贴紧地面不穿模,Ek 归零,Eth 变为 14.70 J。
- 常见报错与纠错:
- 若浏览器报
Cannot use import statement outside a module:检查index.html中的<script>是否声明type="module"属性(<script type="module" src="/main.js"></script>)。 - 若书本初始悬浮或落地穿模:检查网格中心坐标转换,确认是否使用了
center.y = y + b / 2。 - 若书本穿过托板:追加修复指令:“释放时将托板隐藏或移开,仅重置到书架初态时恢复;不要让垂直下落动画穿过实体木板。”
- 若浏览器报
第二轮:添加 3D 点击拾取与平滑运镜
现在最小物理逻辑已经成立。接下来为场景赋予直观的三维触控能力,让学生能通过点击三维物体触发动作。
中文提示词(第 2 轮) · 展开查看与复制
请在保留第 1 轮物理计算与能量条同步逻辑的前提下,更新 main.js、style.css 及必要的 index.html 控件,增加 3D 光线投射拾取(Raycaster Picking)、动态运镜与交互控制。
【修改需求】
1. 3D 物体点击拾取(Raycaster):
- 使用 THREE.Raycaster。注意计算归一化坐标时必须基于 canvas.getBoundingClientRect() 的相对偏移与尺寸,严禁直接使用全屏 window 宽高计算。
- 使用 Pointer Events 监听指针交互,设置轻微拖动位移阈值(如 > 6px 视为拖动而非点击),绝不允许禁用页面的默认缩放与手势滚动。
- 鼠标悬停在书本上时给予 Emissive 高亮反馈并将光标设为 pointer;点击或轻触书本触发释放下落。
2. 相机运镜与展示时长:
- 初始全景视角对准整书与书架。触发下落时,相机平滑插值(lerp)推向地面低机位,展示书本撞击地面的近景。
- 说明 3.0 秒展示时长属于教学观察设计(真实自由落体仅约 0.55 秒)。
- 点击“重置”时相机平滑复位至全景机位。
3. 控件与键盘无障碍:
- 保留页面上真实可见的 HTML“释放”、“暂停/继续”与“重置”按钮,支持 Tab、Enter 与 Space 键盘操作。
- 添加全局空格键(Space)切换暂停/播放,但必须做焦点判断:若当前聚焦在 input 或 button 等交互控件上,不得拦截其原生默认行为。按 Esc 键重置。
4. 响应式与无障碍模式:
- 使用 ResizeObserver(或 window resize 事件)监听画布容器尺寸变化,动态更新渲染器尺寸与相机宽高比,防止画面拉伸变形。
- 支持 prefers-reduced-motion 或静止模式,在减少动效模式下可直接通过滑块步进观察。
请在当前项目中更新这些文件。若无法写文件,请按文件名输出完整代码。
English Prompt (Round 2) · 展开查看与复制
Keeping all physics calculations and energy bar synchronization from Round 1 intact, update main.js, style.css, and any required index.html controls to add Three.js Raycaster picking, camera framing, and accessible controls.
[Requirements]
1. Raycaster 3D Picking:
- Implement THREE.Raycaster. Calculate normalized pointer coordinates strictly from canvas.getBoundingClientRect() relative offset and dimensions; do NOT assume full-window coordinates.
- Use Pointer Events with a drag movement threshold (e.g. > 6px considered dragging rather than click/tap). Never disable whole-page scrolling or pinch-to-zoom gestures.
- Subtle emissive highlight and pointer cursor on hover; clicking or tapping the book triggers the fall.
2. Camera Framing & Display Duration:
- Initial perspective frames the entire shelf and book. Upon drop initiation, smoothly lerp camera to a low-angle close-up of the landing zone.
- Retain the 3.0 s display duration as an intentional pedagogical choice for clear observation (contrasted with the ~0.55 s real fall time).
- Resetting smoothly restores the initial wide camera framing.
3. Accessible Controls & Keyboard:
- Keep real, visible HTML controls for "Drop", "Pause/Resume", and "Reset", fully operable via Tab, Enter, and Space.
- Add a global Spacebar shortcut to toggle pause/resume, ensuring it does NOT intercept default behavior when the focused element is an input, button, or other form control. Esc resets to initial state.
4. Responsiveness & Motion Sensitivity:
- Use ResizeObserver (or window resize event) to dynamically adjust canvas dimensions and camera aspect ratio without stretching.
- Support prefers-reduced-motion / static step mode, allowing direct slider stepping without rapid motion transitions.
Update these files in the current project workspace. If you cannot write files, output the complete code under each filename.
验收与调试(第 2 轮)
- 通过标准:
- 鼠标悬停在书本上时呈现高亮反馈与手型光标;在画布内点击书本能正常触发下落,且页面在移动端仍可正常上下滑动浏览,未被阻止默认手势。
- 下落过程中,相机平滑推进到地面低机位,3 秒教学演示清晰展示势能向动能的转换过程。
- 按空格键可暂停与恢复下落;若焦点在按钮上按空格,优先触发按钮本身行为,不会发生事件冲突;按 Esc 立即复位。
- 常见报错与纠错:
- 若拾取位置偏移或点击无效:核对归一化设备坐标计算,确认是否使用了
(e.clientX - rect.left) / rect.width * 2 - 1,排除了页面滚动和画布边距干扰。
- 若拾取位置偏移或点击无效:核对归一化设备坐标计算,确认是否使用了
第三轮:纸面线稿视觉与“预测-解释”教学闭环
三维课件如果充满浓重廉价的塑料感渲染,会分散认知精力。Every Joule 的精髓在于把页面做成黑白素描底色的“笔记本”,让彩色能量罐成为视觉焦点,并补齐课前的预测与课后的揭晓纸片。
中文提示词(第 3 轮) · 展开查看与复制
请更新 index.html、style.css 和 main.js,将界面视觉升级为“纸雕线稿风格”,并补齐“预测-演示-操作-解释”的教学闭环。
【视觉风格升级】
1. 背景与材质:
- 采用温和的纸张米白底色(#faf9f6,深色模式 #1a1a1c)。
- 3D 模型采用浅色漫反射材质与 EdgesGeometry 描边轮廓线,呈现手绘纸雕素描质感。
- 能量罐使用发光色彩强调:重力势能天蓝、动能翠绿、热内能琥珀黄。
2. 移动端与降级适配:
- 响应式排版:桌面端左右分栏,移动端采用上下堆叠排版,确保三维特写运镜时能量罐数值依然清晰可见,不被遮挡。
- 若浏览器不支持 WebGL,优雅降级显示基础 HTML 文本、按钮与数值公式示意卡片,确保核心教学概念仍可阅读。
【教学流程组件】
1. 预测卡片(Predict Card):
- 题目:“预测:当书从书架掉落砸在地上,原本的能量现在去哪了?”
- 选项:
A. 被完全消耗用光了
B. 转移到了周围环境与书本的热储存中
C. 依然保留在重力势能里
- 流程说明:将“先预测后操作”作为本指南推荐的可选教学引导设计(非原课强制),并提供一个“自由探索/直接演示”开关,允许教师或学生按需选择先预测还是直接探索。
- 学生选择预测选项时,不提前剧透对错。
2. 解释折叠卡片(Lift-the-flap "Why?"):
- 书本落地后呈现“为什么?点击翻开解析”折叠卡片。
- 展开后展示完整原理解释:明确区分下落做功(势能转动能)与落地耗散(动能最终转入书、地板和空气内能;少量先经声音传播后耗散,最终已经包含在 Eth = total 中),并针对选项详细解释为什么 A(能量不会凭空消失)和 C(高度为零重力势能排空)不正确,同时将学生的初始预测选项并列对比。
请在当前项目中更新完整的 index.html、style.css 和 main.js。若无法写文件,请按文件名输出完整代码。
English Prompt (Round 3) · 展开查看与复制
Update index.html, style.css, and main.js to adopt a papercraft line-art visual style and implement the complete "Predict-Watch-Try-Explain" pedagogical flow.
[Visual & Layout Enhancements]
1. Styling & Papercraft Aesthetics:
- Warm paper background (#faf9f6, with dark mode #1a1a1c).
- 3D models with clean matte surfaces and ink EdgesGeometry outlines to create a minimalist papercraft look.
- Reserve vivid emissive colors exclusively for energy jars (Sky Blue for Ep, Emerald Green for Ek, Amber Yellow for Eth).
2. Mobile & Fallback Support:
- Responsive layout: side-by-side columns on desktop, vertical stacked layout on mobile to prevent 3D close-ups from obscuring energy numbers.
- WebGL fallback: If WebGL context is unavailable, display a clean fallback card with HTML text, formula steps, and numeric readouts so learning is uninterrupted.
[Pedagogical Flow Panel]
1. Predict Card:
- Prompt: "Predict: The book falls off the shelf and lands. Where is its energy now?"
- 3 options:
A. It has been used up
B. In the thermal stores around it
C. Still in its gravitational store
- Interaction guidance: Implement predicting-before-dropping as an optional recommended pedagogical scaffold (not a mandatory original lesson lock), providing a "Free Explore / Direct Demo" mode toggle so educators or students can choose to explore directly without forced gating.
- Selecting an option does not prematurely reveal correctness.
2. Lift-the-flap Explanation ("Why?"):
- Upon landing, display a "Why? (Click to lift flap)" card.
- Unfolding provides the full physical explanation: distinguishing mechanical work (Ep -> Ek) from landing dissipation (Ek ultimately becomes internal energy of the book, floor, and air; the small amount first carried by sound is already included in Eth = total after dissipation). Explicitly explain why A (energy cannot vanish) and C (zero height means zero gravitational store) are misconceptions, displaying the user's initial prediction side-by-side for comparison.
Update complete index.html, style.css, and main.js files in the current project workspace. If you cannot write files, output complete code under each filename.
验收与调试(第 3 轮)
- 通过标准:
- 页面呈现纸雕素描质感,移动端上下排版正常,能量数值始终清晰外露。
- 预测卡片可正常点选,教师可自由切换推荐预测引导或直接演示模式,选择预测时不提前弹出答案。
- 书本落地后翻开“Why?”纸片,解析详细分析各选项物理误区,并与用户先前的预测并排展示对比。
第四轮:教师参数抽屉与生产打包验收
为课件增加教师备课视图,公开教学假设与参数,并完成最终打包。
中文提示词(第 4 轮) · 展开查看与复制
请完善当前项目,增加“教师备课笔记面板(Teachers' Notes)”,支持动态参数调整,并满足工程规范。
【功能需求】
1. 教师备课抽屉与动态参数调节(必做):
- 页面右上角增加“教师说明(Teachers' Notes)”切换按钮,抽屉可用键盘操作(Esc 键关闭),关闭后焦点返回触发按钮。
- 抽屉内包含教学背景说明:
* 模型简化说明:去除空气阻力,将撞击与声音耗散简化为瞬时完成;
* 课标差异说明:本课默认 g = 9.8 N/kg(AQA 标准),教材若采用 g = 10 N/kg 理论值会有所不同(如 m=1, h0=1.5 时为 15.0 J);
* 记账隐喻提示:强调能量罐与光效是状态记账模型,不是物质实体。
- 教师参数沙盒(必须实现):
* 提供质量 m (0.5 kg ~ 2.0 kg)、高度 h0 (1.0 m ~ 2.0 m) 的调节滑块,以及 g (9.8 与 10 N/kg) 的单选切换。
* 当任何参数修改时:立即暂停当前播放并重置到初始状态;依据通式 total = m * g * h0 重新计算总能量;动态更新 3D 书架几何高度、书本初始位置与相机取景;重新计算能量条最大分母刻度、数值标签与解释文本。逻辑与视图中绝不允许硬编码 14.7 或 15。
2. 代码与工程规范:
- 清理所有控制台调试代码,确保 ES Module 严格规范。
- 确保窗口与容器尺寸变化时 Three.js 画布与相机纵横比自适应重绘。
请在当前项目中更新所有受影响文件。若无法写文件,请按文件名输出完整代码。
English Prompt (Round 4) · 展开查看与复制
Finalize the project by implementing a "Teachers' Notes Drawer" with dynamic parameter controls and strict engineering standards.
[Requirements]
1. Teachers' Notes Drawer & Parameter Sandbox (Required):
- Add a "Teachers' Notes" toggle button in the top-right corner. The drawer must be keyboard accessible (Esc closes), and focus must return to the toggle button upon closing.
- Drawer pedagogy content:
* Model Simplifications: Explicitly clarify that air resistance is omitted and impact/sound dissipation is treated as instantaneous.
* Specification Differences: Default g = 9.8 N/kg (AQA), noting differences for courses using g = 10 N/kg (yielding 15.0 J when m=1, h0=1.5).
* Metaphor Warning: Remind teachers that jars and light effects are accounting metaphors, not physical substances.
- Parameter Sandbox (Must Implement):
* Controls to adjust mass m (0.5 to 2.0 kg), height h0 (1.0 to 2.0 m), and a toggle between g = 9.8 and 10 N/kg.
* When any parameter changes: immediately pause playback and reset to initial position; recompute total = m * g * h0 using general formulas; update shelf 3D height, book initial mesh position, and camera framing; update energy bar scale denominators, labels, and explanation readouts. Absolutely NO hardcoded 14.7 or 15 in logic or templates.
2. Engineering Standards:
- Remove console debug logs and ensure strict ES module imports.
- Maintain responsive canvas rendering and camera aspect ratio on resize.
Update all affected project files in the current workspace. If you cannot write files, output complete code under each filename.
最终打包与验证
在终端中执行 Vite 生产打包命令:
npx vite build
打包成功后,本地预览打包产物:
npx vite preview
控制台会输出本地预览地址(如 http://localhost:4173)。在隐身窗口中打开,按以下验收点逐项验证:
- 基准参数核对:
m = 1.0, h0 = 1.5, g = 9.8时,初始总能量为 14.70 J;在下落半程(progress = 0.5,即y = 0.75 m)时,Ep = 7.35 J, Ek = 7.35 J,两者之和严格保持 14.70 J。 - 大参数与重力切换:调节参数至
m = 2.0, h0 = 2.0, g = 10,总能量正确重算为 40.00 J,书架高度与能量条比例同步伸展。 - 暂停与重置一致性:播放途中调节参数,课件能正确暂停并重置至新参数的初始状态,无旧数值残留。
- 键盘无障碍:教师抽屉打开后按 Esc 能正常关闭,且键盘焦点回到触发按钮上。
静态产物打包在 dist/ 目录中,但若要部署至子路径(例如 GitHub Pages 的 username.github.io/repo-name/),需在 vite.config.js 中配置 base: './' 或 base: '/repo-name/' 并重新构建,不能直接将文件上传到任意静态路径。
实跑结果与跟做排障
本次实跑在 Node 22.22.3、npm 10.9.8 环境下执行,依赖锁定为 Three.js 0.186.1 与 Vite 8.3.5(package-lock.json 锁定本次安装的依赖版本)。可直接打开本次自制 3D 课件(在线版,无需安装),下载本次完整源码包,内含 README、锁文件、源码、四轮快照,以及本次自制截图与演示片段。解压后进入含 package.json 的目录,执行 npm ci,完成后再执行 npm run dev;不要直接双击 index.html。四轮实施的关键观测读数与排障要点整理如下:
| 轮次 | 核心验收与观测读数 | 跟做检查与排障指引 |
|---|---|---|
| 第 1 轮(物理内核) | 滑块 progress = 0.5 时精准读取 y = 0.75 m、Ep = 7.35 J、Ek = 7.35 J、Eth = 0 J;点击释放加速下落约 3 秒,落地瞬时读数稳定为 y = 0 m、Ep = 0 J、Ek = 0 J、Eth = 14.70 J。WebGL 画布初始化正常。 |
实跑中书本释放时需同步移走托板以契合几何条件。若模型生成时未主动移除托板导致穿模,无需修改原提示词,直接追加一条可复制修复指令:“书本释放下落时将托板网格同步隐藏或移开,仅重置至书架初态时恢复可见,避免书本与托板穿模。” |
| 第 2 轮(拾取运镜) | 画布内点击 3D 书本网格可靠触发释放;点击“释放”再点击“暂停”后数值与动画精确悬停;焦点在按钮时按空格键触发原生按钮点击,不被全局快捷键抢夺焦点;静态步进模式下可直接以 25% 步长调取状态;切出页面时通过 visibilitychange 自动暂停,防止切页后动画在后台跑完。 |
拾取计算必须基于 canvas.getBoundingClientRect() 相对偏移;移动端保留 > 6px 拖动阈值,避免页面上下滚动被阻止。 |
| 第 3 轮(纸雕教学闭环) | 初始点选预测选项 A 仅记录状态,不剧透正误,“Why?”折叠纸片保持隐藏;书本着地后翻开“Why?”,能与用户初始选择 A 并排对照,完整解释机械功与碰撞耗散;在主动选择的文字降级模式下,纯 HTML/CSS 结构依然可用滑块拉到半程并准确显示 7.35 J / 7.35 J。 | 降级机制属于 WebGL 缺失时的图形降级,仍依赖 JavaScript 处理物理状态派生与 DOM 渲染,不可与“完全禁用 JavaScript”混淆。 |
| 第 4 轮(参数与打包) | 调节参数至 m = 2.0 kg, h0 = 2.0 m, g = 10 N/kg 时,总能量读数重算为 40.00 J;progress = 0.5 时同步读出 y = 1.0 m、Ep = 20.00 J、Ek = 20.00 J;“Why?”解析内的总量与选项分析动态同步为 40 J;打开教师抽屉后按 Esc 键关闭,键盘焦点精准返回触发按钮。npm run build 成功。 |
Three.js 打包后单 chunk 约为 540 kB,终端会出现 Vite 针对大于 500 kB 的体积优化提示(Chunk size limit warning),属于常见打包提示而非构建失败,不必误判为报错。 |
读者环境与命令行调试建议:
- 网络重试与依赖完整性:执行
npm install时若遭遇网络波动(如 registryECONNRESET),npm 会自动重试或需重新执行;必须等待安装完全结束且目录生成node_modules后再启动服务。若过早启动终端会报错vite: command not found,待依赖完整安装后再运行即可恢复。 - 工作目录与构建命令:从空目录跟做时,在包含
package.json的项目目录执行npx vite build。npm run build还要求package.json里有对应脚本;本次下载包已提供脚本,自己用npm init -y新建的项目默认没有。遇到Missing script: "build",先查目录,再查 scripts;可以直接改用npx vite build。
本次软件验收覆盖桌面 Chromium 与 390 像素模拟手机,未在真实 iOS、Android、微信或教室投影设备上测试;也没有完成真实课堂的学习效果验证。需要说明的是,原四轮实操曾只实现书本下落这一单一实验;在完成八类储能探索后,课件进一步增加了将纸面展开与剖面特写接入完整流程的进阶补充轮,代码快照保留了各轮演进状态。
课件拓展:原课 8 类储能映射与后续开发
Every Joule 的第一课已经包含全部 8 类储能的物体模型。原课在右页设置了 8 个发光罐,学生点击场景里的具体物体即可点亮对应储能。扩展简化原型时,可以参考这些对象与数值处理:
| 储能类型(Store) | 原课对应物体 | 原课现状与数值表示 | 读者后续拓展参考建议 |
|---|---|---|---|
| 动能(Kinetic) | 骑车者(Cyclist) | 动态演示移动物体,点击后点亮动能罐 | 可绑定车速与质量公式:Ek = 0.5 · m · v^2 |
| 重力势能(Gravitational) | 高处的书(Book on shelf) | 演示自由下落,计算 Ep = 1 × 9.8 × 1.5 ≈ 15 J(精确值 14.7 J) | 可接入本指南第四轮实现的 m、h0、g 参数沙盒 |
| 弹性势能(Elastic) | 拉伸弹簧(Stretched spring) | 呈现受拉伸弹簧形态,点击点亮弹性储能罐 | 可关联胡克定律与弹性储能公式:Ee = 0.5 · k · (Δx)^2 |
| 热储存(Thermal) | 热饮(Hot drink) | 镜头特写杯中热饮,点选后显示热储存及其计算依据 | 可用 ΔE = m · c · Δθ 计算温差对应的内能变化;模拟冷却曲线还需另选传热模型 |
| 化学储存(Chemical) | AA 电池(AA Battery) | 展现电池剖面,标注 14,000 J 上限估算(容量 × 额定电压) | 需向学生说明 14,000 J 为特定电池估算值,非所有电池通用 |
| 磁储存(Magnetic) | 磁铁(Magnets) | 定性展示磁体间储能,无引用典型值故不设固定能量数值 | 维持定性教学,避免凭空编造无权威依据的实测焦耳数 |
| 静电储存(Electrostatic) | 摩擦起电的气球(Rubbed balloon) | 定性展示带电气球,无权威典型数据故不标具体数值 | 维持定性展示,向学生区分静电储能与电流做功途径 |
| 核能储存(Nuclear) | 太阳(Sun) | 展现核反应储能,演示数值取太阳 1 秒的辐射输出 | 需明确告知学生该数值仅代表 1 秒辐射能量,并非太阳核能总储量 |
本轮遗漏复盘:从单一落体到八类储能探索闭环
四轮做出了书本下落与三项能量记账,还没有覆盖原课另一项核心目标:让学生在生活例子中识别八类储能,完成找全 8/8 的探索挑战。
在文章中列出表格供读者参考,并不等于课件本身做出了对应的交互。这项交互已作为四轮之后的独立补充加入本次课件。下面保留补充提示词,读者跟做时也需要追加这一轮。
资源边界与媒体说明
- 无需外部媒体资产的程序几何体:本课件原型中的全部 3D 模型(书架、书本、自行车、弹簧、热饮、电池、磁铁、气球、太阳)均通过 Three.js 内置几何体(如
BoxGeometry、CylinderGeometry、TorusGeometry、SphereGeometry等)组合构建,外加EdgesGeometry轮廓线模拟线稿质感。运行课件无需下载任何外部 GLB/OBJ 模型、纹理贴图或音频文件,安装依赖后即可运行,代码包亦不应混入无再分发许可的第三方媒体素材。 - 原作素材的参考定位:文中引用的原作者截图(
lesson-desktop.png)与原作者演示视频(source-demo.mp4)仅作为设计对照与溯源依据,并非本次自制代码的产物。自制课件的运行截图与录屏应明确标明“自制课件录屏/截图”,且界面外观与操作正常仅证明软件交互成立,不能直接等同于教学成效的达成。 - 进阶视觉效果与功能边界:针对原课中的纸面立起展开动效、热饮特写与电池剖面运镜编排,当前课件已作为进阶轮补齐了独立的自制实现(基于自绘 CanvasTexture 书页底板、铰链立起动画与程序几何剖面,非真实纸张受力模拟或复制原版源码);而声音开关、针对六种课程标准的筛选以及其余 9 课的内容目前仍未制作。自制课件旨在跑通教学与交互闭环,并不声称与原作在视觉上达到像素级一致,交互顺畅亦不能直接等同于真实课堂成效。
补充提示词:八类储能探索与课堂提问
读者可在前四轮代码均通过验收后,向同一对话会话发送以下补充提示词,为课件增设独立的八类储能探索区与进阶课堂提问功能。
中文提示词(补充轮) · 展开查看与复制
请在保留前四轮书本下落与教师抽屉功能完全正常的前提下,继续更新 index.html、style.css 与 main.js,为课件增设“八类储能探索区(8 Energy Stores Explorer)”及配套的课堂概念提问模块。
【功能与交互规格】
1. 八类储能 3D 程序几何模型与双入口交互:
- 在书架场景旁或下方独立区域,使用 Three.js 原生几何体构建 8 个特征鲜明的程序线稿模型(结合 EdgesGeometry 描边,无需外部资产):
* 动能(Kinetic):简化骑车者模型(车轮环、车架与人,配运动方向箭头;不要用无运动线索的静止自行车代表动能);
* 重力势能(Gravitational):高处的书本与托架;
* 弹性势能(Elastic):受拉伸的弹簧结构(螺旋圆环组合);
* 热储存(Thermal):热饮杯模型(带杯口热气线框);
* 化学储存(Chemical):AA 电池(圆柱体加正极凸台);
* 磁储存(Magnetic):一对带 N/S 磁极标识的条形磁铁;
* 静电储存(Electrostatic):摩擦起电的气球(球体加下垂绳索);
* 核能储存(Nuclear):发光太阳模型(中心球体与外围发散射线)。
- 双入口同步响应:界面提供对应的 8 个 HTML 文字按钮,点击画布中的 3D 模型或点击 HTML 按钮均指向同一套数据映射。
- 交互反馈与去重计数:点击任一物体时,3D 模型高亮显示,对应储能徽记点亮,侧边栏显示物体名称、所属储能类型及物理说明;使用 JavaScript Set 集合记录已探索过的储能类型,显示探索进度(如 3/8 直至 8/8 挑战完成),重复点击已发现物体不重复计入总数。提供“重置探索进度”按钮。
2. 物理记账的独立性与定性展示原则:
- 核心原则:八类储能探索是“识别物体保存能量的方式”,不是单一下落物理事件;8 个案例相互独立,能量互不相加,严禁与书本下落的 14.7 J 账本混算或合并为一个伪总数。
- 数值定性处理:除书本落体采用定量计算外,其余 7 类探索对象均采用定性文字与状态卡片说明,不绘制伪精确的共用能量条;磁储存与静电储存因无权威典型值,明确标注为“定性展示(无单一典型数值)”,严禁标为 0 J;太阳说明核反应释放能量并以辐射形式向外传递,严禁将太阳 1 秒的辐射能量标为总核能储备;如引用原课 AA 电池的 14,000 J,必须标明为特定电池的上限估算;最小版本可只作定性解释,不强行塞入未经校准的动态能量罐。
3. 能量传递途径(Pathways)明确标注:
- 在物理解析卡片中,明确指出能量转移所依赖的四种途径(Pathways):
* 下落的书本:通过力与位移的“机械做功(Mechanical work)”;
* 电池供电:化学储能通过电路中的“电流做功(Electrical work)”驱动用电器;
* 热饮冷却:因杯身与环境温差,通过“热传递(Heating)”将热内能转移到周围介质;
* 太阳辐射:核聚变释放能量,通过电磁波“辐射(Radiation)”向外太空传递。
- 在界面中以醒目文字强调:“光”与“电流”属于能量传递的途径,不是孤立的能量储存罐,避免学生混淆。
4. 教师备课视图内容补齐:
- 在现有的 Teachers' Notes 抽屉中补充目标、术语与授课说明;迁移题放在课件可见区域:
* 学习目标(Learning Objectives):识别 8 种储能并在生活中举例;描述书本下落过程中的能量转化;区分四种传递途径;理解“能量罐是记账隐喻,能量不是流体”。
* 核心术语定义卡片:系统(System)、储能(Energy store)、途径(Pathway)、焦耳(Joule)。
* 课标与学情说明:以原课的 14–16 岁学习者为设计参考,说明所需质量、高度与乘法前提;不要声称已对齐某版中国教材。
* 新情境迁移问题与延迟揭晓:增加“课堂追问(Questions to Ask)”模块,包含思考题:“一只上紧发条的玩具车,释放前储存了什么能量?玩具停下后,这些能量最终去了哪里?”
配备“显示解析”折叠按钮,点击展开参考答案(上紧发条储存弹性势能;释放后通过机械做功转化为动能;摩擦阻力与碰撞最终将其耗散为玩具、地面与空气的热储存中)。
- 探索进度只在当前浏览器会话中临时记录,支持随时一键重置;明确提示教师“学生点全 8/8 仅代表完成交互操作,不能直接证明物理概念已经内化掌握”。
请输出完整的修改代码或针对 main.js、index.html 和 style.css 的增量补丁,必要时可拆出 physics.js、stores.js 与 exploration.js,保留清晰的模块引用。修改后重新验收前四轮关键状态。
English Prompt (Supplementary Round) · 展开查看与复制
Keeping all functionality from Rounds 1 to 4 (book drop physics, 3D controls, line-art styling, and Teachers' Notes drawer) fully operational, update index.html, style.css, and main.js to add a dedicated "8 Energy Stores Explorer" and classroom pedagogy questions.
[Requirements]
1. 8 Procedural 3D Models & Dual Input:
- In a distinct section of the scene, generate 8 identifiable procedural line-art 3D objects using native Three.js geometries and EdgesGeometry (zero external asset files):
* Kinetic: Moving cyclist (wheel rings, frame and rider, with a direction arrow);
* Gravitational: Elevated book on shelf;
* Elastic: Stretched spring structure;
* Thermal: Hot drink mug with steam wireframe;
* Chemical: AA battery (cylinder with positive terminal nipple);
* Magnetic: Pair of bar magnets with polarity markers;
* Electrostatic: Charged balloon with dangling string;
* Nuclear: Sun sphere with radiating beams.
- Dual-input accessibility: Provide 8 corresponding HTML buttons. Clicking either the 3D mesh via Raycaster or clicking its HTML button triggers the identical store data mapping.
- Feedback & Deduplication: Clicking highlights the object, lights up the corresponding store badge, and reveals its name and explanation. Track discovery progress using a JavaScript Set (e.g., 3/8 up to 8/8 challenge complete). Repeated clicks on discovered objects must not increment the counter. Provide a "Reset Discovery" button.
2. Ledger Independence & Qualitative Display:
- Core rule: The 8-store explorer is for identifying store types across separate everyday objects, NOT a single falling event. The 8 stores do not sum together and must NEVER be mixed with the falling book's 14.7 J ledger.
- Qualitative representations: Use qualitative text cards without arbitrary common scale bars. Magnetic and electrostatic stores must be labeled as "Qualitative (no typical single value)", never as 0 J. The sun card explains nuclear fusion released via radiation without claiming 1-second radiation output as total nuclear inventory. If quoting the original battery example of 14,000 J, identify it as an upper estimate for a specified battery. The minimum explorer may remain qualitative.
3. Explicit Pathways Recognition:
- Detail the 4 transfer pathways in the explanation panels:
* Falling book: Mechanical work done by gravitational force;
* Battery: Chemical store transfers via electrical work through currents;
* Hot drink: Heat transferred to surroundings via heating due to temperature difference;
* Sun: Nuclear energy transferred outward via electromagnetic radiation.
- Note explicitly: Light and electric currents are transfer pathways, not energy stores.
4. Teachers' Notes Enrichment:
- Append to the Teachers' Notes drawer:
* Learning objectives, key vocabulary (System, Store, Pathway, Joule), and 14–16 age reference and prerequisites; do not claim alignment with a particular Chinese curriculum.
* New transfer question: "Which store does a wound-up toy hold before release, and where has that energy gone once it stops?" Include a delayed-reveal toggle explaining the transfer from elastic store -> kinetic -> dissipated into thermal stores of surroundings.
* Clarify that explorer progress is session-only, resettable, and that completing 8/8 interactions does not constitute proof of conceptual mastery.
Output the complete code or clean incremental updates across main.js, index.html, and style.css. You may extract physics.js, stores.js and exploration.js as needed; rerun the earlier acceptance checks.
补充轮验收要点
- 双入口一致性:在画布中点击 3D 气球或点击下方的“摩擦过的气球”HTML 按钮,均能正确高亮该对象并展开对应说明。
- 去重计数校验:依次点击 8 个不同对象,探索进度计数器从 1/8 逐一递增至 8/8 并触发全亮挑战反馈;重复点击已点亮物体时,说明看板正常切换但计数不再递增。
- 记账隔离验证:点击 8 类储能中的任何物体,书本下落区的总能量(14.70 J 或自定义参数值)与三个能量罐不受任何数值污染,两者状态各自独立。
- 途径与提问展开:物理解析文本中清晰列出机械功、电流做功、热传递与辐射四种途径,强调光与电流非储能;课件中能够顺利展开玩具车思考题解析,并可通过重置按钮清空探索记录。
进阶衔接:怎样把展示效果接进完整教学流程
在完成八类储能探索后,课件已经具备了分类识别的能力;但若要还原原作“纸雕画卷立起、镜头引导观察、再转入亲手操作”的完整教学节奏,还需要将纸面展开、热饮特写与电池剖面运镜平滑接回系统。
在工程上把运镜展示塞进交互课件,最忌讳的是把“视觉展示”与“物理记账”揉成一团乱麻。必须在状态层将四种完全不同的状态严格隔离:
- 纸面展开状态(Unfold Progress,0.0–1.0):控制双页底板上立体模型的铰接立起过程。这属于教具舞台的几何展开补间动画,在此期间书本静止在书架上,绝不能将其误当成物理时间或下落进度;
- 电池剖面状态(Cutaway Progress,0.0–1.0):控制电池外壳的铰开角度与内部层状内芯的暴露程度。这一状态仅在观察电池时生效,退出特写或返回总览时必须强制闭合复位,严禁泄漏到其他模型,更不能与全局能量数值产生混算;
- 书本物理记账状态(Falling Physics State):严格由单一状态派生函数
computePhysicsState(progress, m, g, h0)驱动。书本在书架与地面之间的机械能守恒(如 14.70 J)与碰撞落地后的内能增量严格自洽。热饮的热储存与电池的化学储存属于独立的定性生活案例,绝不能相加或并入书本的 14.7 J 账本;同时,运镜中演示的书本下落必须与手动下落滑块共用这套物理函数与当前教师参数,保证视线所及的数值处处一致; - 学生认知与探索状态(Pedagogy & Interaction State):包括学生对落地去向的预测初选(A/B/C)、已点亮的储能集合(Set 0/8~8/8)、Why 纸片的阅读标记以及导出的 JSON 记录。观看 5 镜头运镜属于被动观察(Watch),从新页面开始看完演示后发现计数应保持 0/8;已有发现计数也不得因演示增加或清空,绝不能因播放动画自动增加发现数(必须由学生亲手点击物体探索才点亮);同时,教师调参、退出演示或重复播放运镜时,绝不能清空学生已有的预测初选与作答。
进阶补充提示词:立体书展开与剖面运镜
读者可在前四轮与八类探索轮均验收可用后,向同一对话会话发送以下进阶提示词。
中文提示词(进阶补充轮) · 展开查看与复制
请在保留前四轮物理内核、教师抽屉以及八类储能探索功能完全正常的前提下,重构并升级场景架构,将“立体书纸面展开、热饮特写与电池剖面运镜”无缝接入完整的“预测-演示-操作-解释-挑战”教学闭环中。
【架构重构与模型复用】
1. 程序模型工厂抽取(store-models.js):
- 将原有的 8 个程序几何模型工厂函数抽取为独立模块 store-models.js,供探索区与演示场景共享基础模型;杯口、电池开壳和动态书可在基础模型上增强,严禁引入外部 GLB 模型、纹理图片或音频文件。
- 热饮模型:中空圆柱杯体、液面、杯柄,以及杯口上方 3 条随时间波动上升的墨线线条(模拟热气)。暂停时蒸汽摆动相位必须精准冻结;静止模式下保持静态。明确仅为定性示意,不做分子粒子动力学模拟,无液体剖面。
- 电池模型:圆柱外壳增加可铰接打开的剖面机制,展开时露出简化的分层内芯与中心杆,并提供 0–100% 剖面滑块。明确标注为定性结构示意,不按真实 AA 电池比例,严禁标注锌/锰等具体化学材料,严禁将发光材质解释为实体“电能流”。
2. 立体书纸面展开底板(guided-scene.js):
- 使用 Three.js 构建双页书本底板,使用自绘 CanvasTexture 呈现手绘印刷字与黑白线稿质感(模拟 print→peel→shade→live 过程)。
- 8 个模型初始在右页上平铺为线稿平面,随着立起进度(0–100%)通过铰链旋转逐渐升起为三维立体模型。提供手动立起滑块,点击“播放完整演示”后自动平滑展开;在 prefers-reduced-motion 或静止模式下,支持直接比对 0% 与 100% 静态形态。明确说明此为几何补间动画,非真实纸张力学形变仿真。
【五镜头运镜系统与状态管理(guided-state.js)】
1. 镜头元数据与编排:
- 设定连续 5 个运镜阶段,总时长 15.5 秒:
* Shot 1(3.0 秒):全景鸟瞰,立体书展开与模型立起;
* Shot 2(4.0 秒):相机平滑推近热饮杯口,展示三条摇曳热气墨线与热储存;
* Shot 3(4.0 秒):镜头转向电池,外壳铰接展开剖面,展示内部化学储能结构;
* Shot 4(3.0 秒):转为低机位侧视书架,电池外壳自动闭合,书本从架上下落撞击地面;
* Shot 5(1.5 秒):镜头拉回全景总览,进入自由操作状态。
2. 播放控制与无障碍入口:
- 提供真实可见的 HTML 运镜控制面板:“播放/暂停/继续”、“从头播放”、“上一镜头”、“下一镜头”、五镜头直接跳转按钮组,以及“退出演示返回总览”按钮。
- 交互双入口:除了点击控制面板外,在总览模式下直接点击 3D 场景中的热饮、电池或高处的书,也能平滑切入对应的特写运镜。
3. 状态清理与生命周期隔离:
- 键盘 Space 键优先控制当前运镜播放/暂停;若处于运镜中,空格绝不能误触书本下落。
- 页面切出(visibilitychange)或打开教师备课抽屉时,当前运镜立即自动暂停;暂停时运镜插值、剖面展开、蒸汽摇曳与物理下落必须同步冻结。
- 当教师在抽屉中修改物理参数(m, h0, g)时,强制复位至总览初态。
- 退出演示或切出电池镜头时,电池外壳必须闭合复位,不留剖面残影。
【物理内核共享与数据隔离】
1. 单一下落物理核心:
- 演示第 4 镜头中的书本下落必须直接调用通用的 computePhysicsState(progress, m, g, h0),与右侧手动探索区严格共享当前质量、高度与重力参数;当在手动模式下拉动书本下落滑块时,立体书内的书本网格高度与左侧 14.7 J 账本必须完全同步。
- 热饮与电池属于独立的定性生活情境,严禁将其估算数值并入或污染书本落地的 14.7 J 账本。
2. 认知数据保护与 JSON 导出:
- 演示区点击热饮、电池或书只切换特写,不计发现;只有八类探索区的模型与同名按钮修改发现集合。观看 5 镜头运镜演示属于观察输入,从新页面开始观看,全程及结束后的探索进度应保持 0/8;若已有探索记录,保持原计数不增加、不清空,严禁因播放动画自动为学生增加发现计数。只有学生亲手在 3D 画布或按钮中点击探索物体,计数器才递增。
- 调参、退出演示或重复播放运镜时,绝不能清空学生在课前已选的预测选项(A/B/C)与作答;Why 曾被阅读的历史标记也应保留,但重新开始下落时可收起解析,避免旧终态解释与当前画面冲突。
- 完善状态导出:提供“导出学习记录”按钮,先生成可见的“下载本次 JSON”链接,并提供可展开的只读 JSON 作为下载受限时的读回入口;不得只弹成功提示。记录包含 prediction、exploration.found(已发现集合)、guided(当前镜头、展开进度、剖面进度、是否完成)、whyViewed 与 transferReferenceViewed的 JSON 数据;导出说明中必须明确提示教师“8/8 探索与运镜完成仅代表交互动作,不能作为真实教学成效证明”。
English Prompt (Advanced Supplementary Round) · 展开查看与复制
Keeping all physics logic, Teachers' Notes drawer, and 8-store explorer features fully functional, refactor the application architecture to integrate papercraft unfolding and cinematic close-ups (hot drink and battery cutaway) into the complete "Predict-Watch-Try-Explain-Challenge" pedagogical flow.
[Architecture Refactoring & Procedural Models]
1. Procedural Model Factory Extraction (store-models.js):
- Extract the 8 procedural line-art geometries into a modular store-models.js factory shared across both the explorer and cinematic scene. Do NOT load external GLB/OBJ models, image textures, or audio assets.
- Hot Drink: Hollow mug cylinder, liquid surface, handle, and 3 rising procedural ink lines for steam waving over time. When paused, steam animation phase must freeze completely; remain static in reduced-motion mode. Treat strictly as a qualitative everyday example without molecular particle simulation or liquid cross-section.
- Battery: Cylindrical casing with a hinged cutaway displaying simplified layered core and central rod, controlled by a 0–100% cutaway slider. Explicitly label as a qualitative diagram: not to scale, no zinc/manganese material labels, and never depict emissive glows as physical energy fluids.
2. Unfolding Papercraft Stage (guided-scene.js):
- Build a Three.js pop-up book spread using programmatic CanvasTexture for printed text and ink linework (reflecting the print -> peel -> shade -> live sequence).
- 8 models start flattened as flat linework on the page and pivot upwards on hinges as unfolding progresses (0–100%). Provide a manual unfold slider alongside smooth unfolding after the user starts the demo; under prefers-reduced-motion, allow comparing 0% and 100% static states. Clarify that this is keyframe tweening, not continuum paper elasticity simulation.
[5-Shot Cinematic System & State Management (guided-state.js)]
1. Shot Metadata & Choreography:
- Implement 5 sequential shots totaling 15.5 seconds:
* Shot 1 (3.0 s): Overview bird's-eye view, book spread unfolding and models erecting;
* Shot 2 (4.0 s): Camera pushes in to hot drink mug, revealing 3 oscillating steam lines and thermal store;
* Shot 3 (4.0 s): Camera pans to battery, casing hinges open to reveal cutaway and chemical store;
* Shot 4 (3.0 s): Low-angle view of the bookshelf, battery closes, book drops and hits the ground;
* Shot 5 (1.5 s): Camera pulls back smoothly to full overview for free exploration.
2. Accessible Playback Controls:
- Provide visible HTML controls: Play/Pause/Resume, Replay, Prev Shot, Next Shot, five-shot button group, and "Exit Demo to Overview".
- Dual input: In overview mode, clicking the 3D hot drink, battery, or shelf book directly transitions camera framing to that close-up shot.
3. State Isolation & Lifecycle Cleanup:
- Global Spacebar toggles demo play/pause during cinematic mode without falsely triggering book drop.
- Switching browser tabs (visibilitychange) or opening the Teachers' Notes drawer must pause playback immediately; pausing freezes camera interpolation, cutaway extension, steam wave phase, and physics.
- Adjusting teacher parameters (m, h0, g) immediately resets the cinematic scene to initial state.
- Exiting the demo or switching away from the battery shot must close the battery cutaway casing.
[Physics Engine Sharing & Data Isolation]
1. Unified Physics Derivation:
- Shot 4 falling animation must directly invoke the shared computePhysicsState(progress, m, g, h0), synchronized with active teacher parameters; dragging the manual fall slider updates the pop-up book mesh and 14.7 J ledger in lockstep.
- Qualitative stores (hot drink and battery) are strictly isolated; their values (e.g. battery 14,000 J estimate) must NEVER contaminate or sum into the falling book's 14.7 J ledger.
2. Learning State Integrity & JSON Export:
- Clicks in the cinematic scene change the close-up only; discoveries are counted only in the dedicated8-store explorer. Watching the demo is an observation phase: a fresh page remains at 0/8 after demo completion; existing discoveries must neither increase nor be erased. Never increment the found counter from passive viewing; only direct user clicks on 3D meshes or HTML buttons count.
- Changing parameters, exiting, or replaying the demo must NEVER erase student's initial predict choice (A/B/C) or transfer answer; preserve a separate Why-viewed history flag even if the explanation is folded again for a new fall.
- Implement "Export Learning Log" by creating a visible download link plus a read-only JSON preview for fallback; do not merely show a success toast. The payload contains prediction, exploration.found array, guided (shot, unfold, cutaway, completed), whyViewed and transferReferenceViewed. Add an explicit disclaimer that 8/8 completion is an interaction log, not evidence of conceptual mastery.
进阶轮验收要点
- 模型共享与独立渲染:
store-models.js成功为探索区与立体书场景提供几何体,项目网络面板无任何.glb或图片贴图请求。 - 运镜与冻结一致性:播放演示时按空格或切出标签页,镜头推进、蒸汽摆动、电池剖面展开与书本下落同步停滞;恢复后继续平滑衔接。
- 退出演示状态复位:在电池特写阶段点击“退出演示”,电池外壳自动闭合,相机平滑退回全景总览,无破面残留。
- 记账与发现隔离:演示播放完毕后,发现进度保持
0/8;书本 14.7 J 账本未受热饮或电池数值影响。
试用验收:全流程走测与教学观察
在课件接入全部功能后,建议读者或同行教师按完整的教学动作闭环执行一次全流程走测。这套走测步骤用于验证软件交互与物理状态的自洽性,以下记录读者可操作的检查路径、预期读数与常见异常修法;软件操作记录与真实学生的课堂理解分别判断:
读者可操作的完整走测路径
-
第一步:前概念预测(Predict)
- 操作步骤:进入初始页面,不点击演示或下落。直接在左页预测卡片中点选一个前概念选项(例如选 A:“被完全消耗用光了”)。
- 预期现象与读数:单选框被选中,卡片保持平静;“Why? 揭晓”折叠纸片保持隐藏折叠状态,界面绝不提前提示选项对错。右侧八类储能进度保持为
0/8。 - 异常排查与修法:若点选后立即弹出对错或自动翻开解释,说明事件回调中混入了判定逻辑;应检查单选监听,将判定严格推迟至书本落地且手动翻开时。
-
第二步:五镜头运镜走测(Watch)
- 操作步骤:点击“播放完整演示”或“从头播放”,依次经历 Shot 1 至 Shot 5(总长 15.5 秒)。在 Shot 2(热饮)中按下空格键暂停,并在 Shot 3(电池)中手动拖动剖面滑块,随后点击“继续”,直至运镜走完退回总览。
- 预期现象与读数:
- Shot 1(3.0 s):双页底板上的平铺线稿升起为立体几何体;
- Shot 2(4.0 s):相机推向热饮杯口,3 条墨线摇曳;按下空格暂停时,镜头推近停滞,蒸汽波动相位完全冻结;再次按空格平滑继续;
- Shot 3(4.0 s):镜头对准电池,外壳铰接打开,露出分层内芯与中心杆;
- Shot 4(3.0 s):转为低机位侧视,电池外壳自动闭合;书本加速坠落,重力势能柱从 14.70 J 排空流入动能,撞击瞬间动能归零、内能增量变为 14.70 J;
- Shot 5(1.5 s):镜头平滑退回总览机位。
- 核心检验点:完整看完 15.5 秒演示后,右页八类储能发现计数器必须严格保持为 0/8。
- 异常排查与修法:
- 若暂停后蒸汽仍在摆动:检查动画循环,确保时间增量
dt在暂停标志为 true 时置为 0,防止着色器或顶点偏移继续步进; - 若退出演示后电池外壳保持开裂:检查镜头切换与退出钩子,确认是否调用了剖面复位函数(将剖面角度设回 0);
- 若看完演示发现计数变成了 3/8:检查运镜切换逻辑,确认是否误将相机对准物体的动作派发为了探索点击事件;应将
selectStore限制为仅由用户主动点击触发。
- 若暂停后蒸汽仍在摆动:检查动画循环,确保时间增量
-
第三步:亲手操作与动态调参(Try & Parameters)
- 操作步骤:返回总览后,手动拖动书本下落滑块至 50% 位置;随后点击右上角“教师说明(Teachers' Notes)”,将参数修改为大参数:
m = 2.0 kg, h0 = 2.0 m, g = 10 N/kg,按 Esc 关闭抽屉。 - 预期现象与读数:
- 默认参数(m=1.0, h0=1.5, g=9.8)半程(
progress = 0.5)时,书底物理高度精确显示y = 0.75 m,能量罐显示Ep = 7.35 J、Ek = 7.35 J、Eth = 0.00 J,三者自洽等于 14.70 J;立体书内的书本与右侧下落模型高度完全同步。 - 调为大参数后,场景自动重置为初态,总能量重新计算为
total = 2.0 × 10 × 2.0 = 40.00 J;再次拖到半程(progress = 0.5)时,数值精准变为y = 1.00 m、Ep = 20.00 J、Ek = 20.00 J、Eth = 0.00 J。 - 核心检验点:打开抽屉、调节滑块或关闭抽屉,第一步中学生选中的预测选项(如 A)完好保留,不被意外清空。
- 默认参数(m=1.0, h0=1.5, g=9.8)半程(
- 异常排查与修法:若默认半程不等于 7.35 J + 7.35 J,先检查滑块是否精确为路程的 50%,是否误用了时间比例;统一从物理状态派生并在显示时才取两位小数,不要手工改数字凑守恒;若调参清空了学生的预测状态,检查参数更新函数,确保只复位物理进度与当前运镜,不重置预测、发现集合与作答。
- 操作步骤:返回总览后,手动拖动书本下落滑块至 50% 位置;随后点击右上角“教师说明(Teachers' Notes)”,将参数修改为大参数:
-
第四步:掀开纸片对比解释(Explain)
- 操作步骤:先将书本下落滑块推至 100% 或释放书本等待落地,再点击“为什么?翻开解析”。沿用上一步大参数,此时应显示 40.00 J 内能增量。
- 预期现象与读数:纸片展开,并排呈现原理解释与学生的初始选择:“你的预测 A”。解析中详细指出下落做功与撞击向环境热储存耗散的物理过程,并针对 A 选项说明“能量不会凭空消失,而是耗散到了周围难以利用的内能中”。
- 异常排查与修法:若展开后未显示学生的初选,检查渲染模板是否正确读取了 当前
prediction,并更新prediction-comparison节点。
-
第五步:找全八类储能挑战(Challenge)
- 操作步骤:在下方八类探索区依次点击模型或对应的 8 个 HTML 按钮,找齐 8 种储能;对同一物体(如热饮)连续重复点击 3 次。
- 预期现象与读数:每点击一个新物体,探索计数器由
1/8递增至8/8,点全后八个徽记点亮并显示完成反馈;重复点击已探索物体时,说明看板正常切换但计数器稳定不变。本条路径沿用大参数,书本落体区的 40.00 J 账本不受影响。 - 异常排查与修法:若重复点击导致计数虚增,检查去重集合是否生效(使用
foundSet.add(storeKey)并以foundSet.size作为已发现数量,总数 8 保持不变)。
-
第六步:新情境迁移概念追问(Transfer)
- 操作步骤:在页面底部阅读发条玩具问题,先在“我的解释”中独立写出能量去向,再展开“写好后,展开参考思路”比较。
- 预期现象与读数:解析正常展开,清晰呈现“发条弹性储能 → 机械做功驱动动能 → 阻力与地面碰撞转化为玩具、地面与空气的热储存”的能量流动链。
-
第七步:学习记录导出与读回(Export)
- 操作步骤:点击“导出学习记录”,再点击出现的“下载本次 JSON”;若内置浏览器不保存文件,可展开“查看本次学习记录 JSON”读回并复制保存。
- 预期现象与读数:JSON 数据格式完整,包含
prediction: "A"、exploration.found: [...](包含 8 类键名),以及本次新增的guided结构(包含shot字符串镜头 ID、unfold与cutaway的 0–1 比例,以及completed当前完成标志);同时核对whyViewed、transferReferenceViewed和transferAnswer;guided.completed表示当前运镜状态,调参或退出会将它复位为 false,不是“曾经完整看过”的历史成绩。记录附带说明:“注意:点击 8/8 与运镜完成仅代表交互操作,不能作为物理概念掌握的充分证明”。 - 异常排查与修法:若导出的
exploration.found为空数组,检查序列化前是否将Set正确转为Array.from(set)。
本轮由 Codex 实际走过上述流程:选 A 后完整播放五镜头,发现数仍为 0/8;手动默认半程为 7.35 J + 7.35 J,改为 2 kg、2 m、10 N/kg 后半程两处读数均为 20 J + 20 J,落地为 40 J 内能增量。随后打开 Why、找齐 8/8、独立填写发条玩具解释,再展开参考思路并下载 JSON;读回的预测、8 个发现键、40 J、作答和两个阅读标记与页面一致。
排查与走测中修复了控制与读回问题:退出特写后空格控制权未交回下落实验;暂停时蒸汽相位回到初始值;手动剖面比例在暂停刷新时显示回跳;下载按钮仅请求保存却无法确认新文件。当前版本使用明确的模式退出、可冻结的蒸汽时间与显式下载链接,并提供 JSON 读回区。guided.completed 是当前状态,调参后复位为 false,不代表学生没有看过演示。
课堂环境中的教学观察维度
这套走测用于检查软件能否按预期运行。在正式将课件应用于课堂时,教师仍需通过面对面的观察来评估学生的真实学习状态:
- 观察预测环节的行为表现:记录学习者进入页面后是先阅读预测题并进行思考,还是直接寻找演示按钮跳过。如果学习者跳过预测,不应单纯断定为注意力不集中,也可能是题目表述不够明确、界面层级干扰或移动端点击区域过小所致,需在走测后简短追问定位原因。
- 观察下落时的视线转移:在书本下落过程中,观察学习者的注意力是仅聚焦于三维长方体的位移,还是会留意到能量罐柱状图与数字的此消彼长。若学习者完全未察觉能量数值变动,可引导其观察能量柱的高度升降。
- 观察落地后的概念复述与迁移:书本下落静止后,询问学习者:“书本初始的 14.7 焦耳(原课显示约为 15 焦耳)现在去哪了?”引导其用自己的话复述机械能向环境内能耗散的过程。随后借助发条玩具问题追问,观察其能否将“系统做功与终态耗散”的记账模型迁移至新情境中。这种口头表达可作为形成性评价,但切忌将交互层面的点全 8/8 盲目等同于物理概念的真正内化。
一本书落地的能量去哪了?3D 交互课件的物理记账与教学闭环
一本书从书架落下,最后静止在地上。它原本的重力势能去了哪里?把这个问题做成可预测、可操作、可解释的课件,就是一次具体的 3D 互动课程设计任务。
核心机制:能量不是流体,能量罐是状态记账账户
课件中发光的“能量罐”以及物体与罐之间流动的光线,都属于便于教学观察的视觉隐喻,能量罐与流动光效本身均不是实体物质。下落时重力做功将重力势能转化为动能;撞击瞬间动能归零,系统机械能全部耗散并转入书本、地面与周围空气的热储存中,全程总量严格守恒。
(y = 1.50 m)
(y = 0.75 m)
(y = 0.00 m)
跟做路线:四轮基础,再加两轮补充
教学闭环:为什么不能只做三维动效
让 AI 协助开发 3D 课件时,一个常见的认知偏差是把“立体视觉效果”等同于“教学目标达成”。如果跳过思考直接观看三维动画,学生容易只关注动效而忽略守恒问题。Every Joule 围绕五个教学动作构建认知闭环:
核心概念辨析:光与电流属于能量传递的“途径(Pathways)”,而不是孤立的“储存(Stores)”。教学中须向学生明确区分储存与途径,避免将其误解为实体流体。
工程核心:单一物理数据源(Single Source of Truth)
初学者指挥 AI 编写 3D 交互时,极易让位移动画、数字计时器与 CSS 能量条各自为政。一旦浏览器掉帧,就会出现书已落地而能量罐仍停在半空的穿帮。核心工程设计:动画与数值必须派生自统一的物理状态计算。
纯函数状态派生与坐标对齐:定义 progress 为已下降路程占初始高度的比例,通过单一函数 computePhysicsState(progress, m, g, h0) 计算绝对高度 y 与能量分配。书本长方体模型中心严格渲染在 center.y = y + b/2,杜绝悬空与地面穿模;教师调节质量或高度时动态重构分母刻度,逻辑中绝不硬编码固定数值。
数据隔离:单一下落记账 vs 八类储能探索
在接入纸面展开、电池剖面与探索挑战时,必须在状态层严格隔离不同生命周期的状态,防止数据污染与假性闭环:
由 computePhysicsState 严格驱动,默认下落中 Ep + Ek = 14.70 J;落地后 Ep = Ek = 0,Eth = 14.70 J。调参后按 mgh₀ 重算总量并复位。
热饮、电池等生活案例互不相加,严禁混入 14.7 J 账本;新页面看完 5 镜头仍为 0/8;已有发现数保留,仅主动探索方可点亮。
学习数据保护:调参、重播运镜或退出演示时,严禁清空学生课前已选的预测初选(A/B/C)与作答;导出记录明确注明“8/8 交互完成不等于物理概念内化”。
