【threejs教程8】threejs添加3D场景键盘控制

【完整效果代码位于文章末】

目录

准备工作

目标

步骤1:初始化按键状态对象

步骤2:监听键盘事件

步骤3:编写事件处理函数

步骤4:更新相机移动方向

总结

完整代码如下

在3D应用开发中,用户交互是一个关键环节,特别是对于游戏和虚拟现实体验来说,能够通过键盘控制相机移动是提升沉浸感的重要手段。本文将指导你如何利用简单的代码,实现对THREE.js 3D场景中相机的键盘控制功能。

准备工作

确保你的项目中已经集成了THREE.js库,这是创建3D场景的基础。本文不涉及THREE.js的安装和基本使用,假设你已有相关基础。查看3D场景创建基础看查看往期文章:

【threejs教程1】threejs基础开发示例

【threejs教程2】threejs物体点击交互事件

【threejs教程3】threejs物体轮廓发光

【threejs教程4】threejs添加跳动标注

【threejs教程5】threejs添加文字标注,且始终面向屏幕

【threejs教程6】threejs加载glb模型文件(小米su7)

【threejs教程7】threejs聚光灯、摄影机灯和汽车运动效果

目标

我们将实现当按下键盘上的W、S、A、D键时,3D场景中的相机分别向前、后、左、右平移。这个过程分为三步:监听键盘事件、管理按键状态、根据按键状态更新相机移动方向。

步骤1:初始化按键状态对象

首先,我们需要一个对象来记录键盘按键的状态(按下或抬起)。这将帮助我们判断何时以及如何改变相机的移动方向。

javascript 复制代码
const keyState = {
  KeyW: false,
  KeyS: false,
  KeyA: false,
  KeyD: false,
};

步骤2:监听键盘事件

接下来,我们需要在文档级别监听键盘的keydown和keyup事件,以便在用户按下或释放特定按键时触发相应的处理函数。

javascript 复制代码
document.addEventListener('keydown', onDocumentKeyDown, false);
document.addEventListener('keyup', onDocumentKeyUp, false);

步骤3:编写事件处理函数

  • keydown事件处理:当按键被按下时,更新keyState中对应按键的状态为true,并调用updateMoveDirection()更新相机移动方向。
javascript 复制代码
function onDocumentKeyDown(event) {
  keyState[event.code] = true;
  updateMoveDirection();
}
  • keyup事件处理:当按键被释放时,将其状态设回false,同样调用updateMoveDirection()确保移动状态正确反映按键情况。
javascript 复制代码
function onDocumentKeyUp(event) {
  keyState[event.code] = false;
  updateMoveDirection();
}

步骤4:更新相机移动方向

最后,定义updateMoveDirection()函数,根据当前按键状态计算相机的移动方向,并应用到相机位置上。

javascript 复制代码
// 定义键盘控制速度(可根据需要调整)
const moveSpeed = 0.5
​​​​​​​function updateMoveDirection() {
  const direction = new THREE.Vector3(); // 存储相机前方方向
  const moveDirection = new THREE.Vector3(); // 计算移动向量
  const upVector = new THREE.Vector3(0, 1, 0); // 作为旋转轴辅助计算

  // 获取相机面向的方向
  camera.getWorldDirection(direction);
        
  // 根据按键状态调整移动向量
  if (keyState['KeyW']) moveDirection.add(direction);
  if (keyState['KeyS']) moveDirection.sub(direction);
  if (keyState['KeyA']) moveDirection.add(upVector.clone().cross(direction)); // 左转
  if (keyState['KeyD']) moveDirection.sub(upVector.clone().cross(direction)); // 右转

  // 确保移动向量有明确的方向,避免无效移动
  moveDirection.normalize();

  // 应用移动,乘以速度常量控制速度
  camera.position.add(moveDirection.multiplyScalar(moveSpeed));
}

总结

至此,你已成功为3D场景中的相机添加了基本的键盘控制功能。通过监听键盘事件、维护按键状态、并据此更新相机的移动方向,你的用户现在可以使用WASD键自由探索你创造的3D世界。记得调整moveSpeed常量以获得理想的移动速度,并根据需要进一步优化和扩展控制逻辑,如添加更多按键控制或平滑移动效果等。

完整代码如下

javascript 复制代码
// 用于跟踪按键状态的对象
  const keyState = {
    KeyW: false,
    KeyS: false,
    KeyA: false,
    KeyD: false,
  };
   

  // 监听键盘按键按下和抬起事件
  document.addEventListener('keydown', onDocumentKeyDown, false);
  document.addEventListener('keyup', onDocumentKeyUp, false);

  // 按键按下事件处理函数
  function onDocumentKeyDown(event) {
    // 设置对应按键的状态为按下
    keyState[event.code] = true;
    updateMoveDirection();
  }

  // 按键抬起事件处理函数
  function onDocumentKeyUp(event) {
    // 设置对应按键的状态为抬起
    keyState[event.code] = false;
    updateMoveDirection();
  }
  // 定义键盘控制速度(可根据需要调整)
  const moveSpeed = 0.5
  // 更新移动方向的函数
  function updateMoveDirection() {
    const direction = new THREE.Vector3(); // 用于存储相机的视线方向
    const moveDirection = new THREE.Vector3(); // 用于计算移动向量

    // 获取相机的全局前方方向
    camera.getWorldDirection(direction);
    const upVector = new THREE.Vector3(0, 1, 0); // 用于计算旋转轴
    // 根据按键状态调整移动向量
    if (keyState['KeyW']) moveDirection.add(direction);
    if (keyState['KeyS']) moveDirection.sub(direction);
    if (keyState['KeyA']) moveDirection.add(upVector.clone().cross(direction));
    if (keyState['KeyD']) moveDirection.sub(upVector.clone().cross(direction));
    // 规范化移动向量
    moveDirection.normalize();
    // 应用移动
    camera.position.add(moveDirection.multiplyScalar(moveSpeed));
  }
复制代码
相关推荐
qiyi.sky8 分钟前
JavaWeb——Vue组件库Element(3/6):常见组件:Dialog对话框、Form表单(介绍、使用、实际效果)
前端·javascript·vue.js
先生沉默先11 分钟前
3dsMax合并FBX的时候相同的节点会被合并(重命名解决),3Ds MAX创建空物体(虚拟对象或者点)
3d·3dsmax
煸橙干儿~~11 分钟前
分析JS Crash(进程崩溃)
java·前端·javascript
哪 吒13 分钟前
华为OD机试 - 几何平均值最大子数(Python/JS/C/C++ 2024 E卷 200分)
javascript·python·华为od
安冬的码畜日常20 分钟前
【D3.js in Action 3 精译_027】3.4 让 D3 数据适应屏幕(下)—— D3 分段比例尺的用法
前端·javascript·信息可视化·数据可视化·d3.js·d3比例尺·分段比例尺
l1x1n01 小时前
No.3 笔记 | Web安全基础:Web1.0 - 3.0 发展史
前端·http·html
Q_w77421 小时前
一个真实可用的登录界面!
javascript·mysql·php·html5·网站登录
昨天;明天。今天。1 小时前
案例-任务清单
前端·javascript·css
一丝晨光2 小时前
C++、Ruby和JavaScript
java·开发语言·javascript·c++·python·c·ruby
Front思2 小时前
vue使用高德地图
javascript·vue.js·ecmascript