Clock
是 Three.js 中用于跟踪时间的类,通常用于动画、游戏循环或需要基于时间进行更新的场景。Clock
提供了简单而高效的 API,帮助开发者计算时间间隔(delta time)和总运行时间。这对于实现基于帧率的平滑动画、更新物体位置和处理时间相关的逻辑至关重要。
在这篇博客中,我们将详细介绍 Clock
的用法,探讨其所有的属性和方法,并通过丰富的示例来展示如何在实际项目中使用 Clock
来控制动画和时间逻辑。
Clock
Three.js 中的 Clock
类是一个轻量级的工具,用于测量应用程序运行时的时间。它主要有两个用途:
Clock
在动画或游戏开发中非常常用,因为它能够提供一种简单的方式来同步动画或移动,使其不依赖于帧率。
const clock = new THREE.Clock(autoStart);
autoStart
: 可选参数,默认为 true
,表示是否在创建 Clock
的同时启动它。Clock
的核心属性和方法start
启动时钟。如果时钟已经启动,则这个方法不会产生效果。
clock.start();
stop
停止时钟。如果时钟已经停止,则此方法不会产生效果。
clock.stop();
getElapsedTime
获取自时钟启动以来的总运行时间,以秒为单位返回一个浮点数。这个时间包括暂停和恢复期间的累积时间。
const elapsedTime = clock.getElapsedTime();
getDelta
获取自上次调用 getDelta
或启动时钟以来的时间差(delta time)。它通常用于每帧的动画更新,以确保动画与帧率无关。
const delta = clock.getDelta();
running
running
是一个只读属性,返回当前时钟是否在运行。如果时钟启动了但没有停止,则返回 true
,否则返回 false
。
console.log(clock.running); // true 或 false
Clock
的基础使用我们来看一个使用 Clock
创建简单动画的例子。在这个例子中,我们通过 Clock
来控制一个立方体的旋转,并确保旋转速度与帧率无关。
Clock
控制物体的旋转// 创建场景、相机和渲染器
const scene = new THREE.Scene();
const camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
const renderer = new THREE.WebGLRenderer();
renderer.setSize(window.innerWidth, window.innerHeight);
document.body.appendChild(renderer.domElement);
// 创建立方体
const geometry = new THREE.BoxGeometry();
const material = new THREE.MeshBasicMaterial({ color: 0x00ff00 });
const cube = new THREE.Mesh(geometry, material);
scene.add(cube);
// 设置相机位置
camera.position.z = 5;
// 创建一个 Clock 对象
const clock = new THREE.Clock();
// 渲染循环
function animate() {
requestAnimationFrame(animate);
// 获取时间差
const delta = clock.getDelta();
// 使用时间差控制立方体旋转
cube.rotation.x += delta;
cube.rotation.y += delta;
renderer.render(scene, camera);
}
animate();
在这个例子中,我们使用 clock.getDelta()
获取每帧之间的时间差,并将其应用于立方体的旋转速度,使得动画可以平滑地运行,并且不依赖于帧率。
Clock
的进阶使用通过调整 delta time
,我们可以轻松控制动画的快慢。例如,如果想让物体的旋转速度变为原来的两倍,可以在 delta
上乘以一个系数。
const speed = 2.0; // 设置速度为原来的两倍
cube.rotation.x += delta * speed;
cube.rotation.y += delta * speed;
我们可以在特定情况下暂停时钟,例如在游戏暂停时,或者当用户切换到其他窗口时暂停动画。通过 clock.stop()
暂停时钟,并通过 clock.start()
恢复时钟。
document.addEventListener('visibilitychange', function() {
if (document.hidden) {
clock.stop();
} else {
clock.start();
}
});
在这个例子中,当用户切换到其他窗口时,时钟会自动停止;当用户重新回到该窗口时,时钟会恢复。
getElapsedTime
方法返回自时钟启动以来的总时间,这对于跟踪总动画时间或在场景中控制特定事件的发生很有用。
const elapsedTime = clock.getElapsedTime();
if (elapsedTime > 5) {
console.log('5秒已过去');
}
Clock
控制多个物体动画在这个示例中,我们将创建多个物体,并使用 Clock
控制每个物体的不同动画。
// 创建场景、相机和渲染器
const scene = new THREE.Scene();
const camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
const renderer = new THREE.WebGLRenderer();
renderer.setSize(window.innerWidth, window.innerHeight);
document.body.appendChild(renderer.domElement);
// 创建多个立方体
const cubes = [];
for (let i = 0; i < 5; i++) {
const geometry = new THREE.BoxGeometry();
const material = new THREE.MeshBasicMaterial({ color: Math.random() * 0xffffff });
const cube = new THREE.Mesh(geometry, material);
cube.position.x = (i - 2) * 2; // 调整立方体位置
cubes.push(cube);
scene.add(cube);
}
// 设置相机位置
camera.position.z = 10;
// 创建一个 Clock 对象
const clock = new THREE.Clock();
function animate() {
requestAnimationFrame(animate);
// 获取时间差
const delta = clock.getDelta();
// 为每个立方体设置不同的旋转速度
cubes.forEach((cube, index) => {
cube.rotation.x += delta * (index + 1); // 不同立方体不同的旋转速度
cube.rotation.y += delta * (index + 1);
});
renderer.render(scene, camera);
}
animate();
在这个例子中,每个立方体的旋转速度都不同,通过 Clock
控制它们的动画,实现了流畅的帧率无关动画。
Clock
在复杂场景或游戏开发中,Clock
通常被用来同步多个动画、物理引擎或其他时间相关的逻辑。我们可以通过一个统一的时钟来控制整个场景的时间进度。
// 假设有一个物理引擎需要更新
function updatePhysics(delta) {
physicsEngine.step(delta);
}
// 渲染循环
function animate() {
requestAnimationFrame(animate);
// 获取时间差
const delta = clock.getDelta();
// 更新物理引擎
updatePhysics(delta);
// 渲染场景
renderer.render(scene, camera);
}
animate();
通过这种方式,我们可以确保物理引擎的更新频率与帧率同步,而不会因为帧率波动而影响物理模拟的准确性。
Clock
的最佳实践getDelta
:在动画循环中,确保每帧都调用 clock.getDelta()
,以确保获取的时间差准确无误。getElapsedTime
或 getDelta
:如果你需要跟踪总时间,使用 getElapsedTime
;如果你需要逐帧更新动画,使用 getDelta
。Clock
控制帧率无关的动画:通过 Clock
计算时间差,可以让动画和逻辑更新与帧率解耦,使得在不同设备上表现一致。Clock
是 Three.js 中非常实用的工具类,特别适合
在需要基于时间进行更新的场景中使用,如动画、游戏循环或物理模拟。通过 Clock
,我们可以方便地获取时间差、跟踪总运行时间,并通过帧率无关的方式更新场景和动画。
在本文中,我们详细介绍了 Clock
的各种属性和方法,并通过多个示例展示了它在实际项目中的应用。希望这些内容能帮助你更好地理解和掌握 Clock
的使用,为你的 Three.js 项目增添更多的控制力和表现力。