当前位置:首页 > JavaScript

js实现人物行走

2026-02-03 07:10:54JavaScript

实现基础动画循环

使用requestAnimationFrame创建平滑动画循环,通过时间差计算确保帧率稳定。定义一个游戏循环函数,在每次屏幕刷新时更新角色位置和渲染状态。

let lastTime = 0;
function gameLoop(timestamp) {
    const deltaTime = timestamp - lastTime;
    lastTime = timestamp;

    updatePosition(deltaTime);
    renderCharacter();

    requestAnimationFrame(gameLoop);
}
requestAnimationFrame(gameLoop);

处理键盘输入

通过addEventListener监听键盘事件,使用对象存储按键状态。创建包含方向键映射的对象,实时跟踪WASD或方向键的按下/释放状态。

const keys = {};
document.addEventListener('keydown', (e) => {
    keys[e.key] = true;
});
document.addEventListener('keyup', (e) => {
    keys[e.key] = false;
});

// 方向键映射示例
const directionMap = {
    'ArrowUp': 'up',
    'ArrowDown': 'down',
    'ArrowLeft': 'left',
    'ArrowRight': 'right'
};

角色移动逻辑

根据按键状态计算移动向量,考虑对角线移动的归一化处理。定义移动速度和加速度参数,实现更自然的运动效果。

const character = {
    x: 0,
    y: 0,
    speed: 100, // 像素/秒
    moving: false
};

function updatePosition(deltaTime) {
    let moveX = 0;
    let moveY = 0;

    if (keys['ArrowUp']) moveY -= 1;
    if (keys['ArrowDown']) moveY += 1;
    if (keys['ArrowLeft']) moveX -= 1;
    if (keys['ArrowRight']) moveX += 1;

    // 对角线移动归一化
    if (moveX !== 0 && moveY !== 0) {
        moveX *= 0.7071;
        moveY *= 0.7071;
    }

    character.x += moveX * character.speed * (deltaTime / 1000);
    character.y += moveY * character.speed * (deltaTime / 1000);
    character.moving = (moveX !== 0 || moveY !== 0);
}

精灵动画控制

使用精灵表实现行走动画,通过计算帧索引实现动画播放。定义动画帧率和当前帧索引,根据移动状态切换不同动画序列。

const sprite = {
    frameWidth: 32,
    frameHeight: 48,
    currentFrame: 0,
    frameCount: 4,
    frameDuration: 100, // 毫秒
    lastFrameTime: 0,
    row: 0 // 精灵表行号(0:下,1:左,2:右,3:上)
};

function updateAnimation(deltaTime) {
    if (!character.moving) {
        sprite.currentFrame = 0;
        return;
    }

    sprite.lastFrameTime += deltaTime;
    if (sprite.lastFrameTime >= sprite.frameDuration) {
        sprite.currentFrame = (sprite.currentFrame + 1) % sprite.frameCount;
        sprite.lastFrameTime = 0;
    }

    // 根据移动方向设置精灵行
    if (keys['ArrowUp']) sprite.row = 3;
    else if (keys['ArrowDown']) sprite.row = 0;
    else if (keys['ArrowLeft']) sprite.row = 1;
    else if (keys['ArrowRight']) sprite.row = 2;
}

渲染角色

使用Canvas API绘制精灵动画,计算正确的精灵图裁剪区域。实现双缓冲技术避免画面闪烁,处理不同方向的镜像翻转。

const canvas = document.getElementById('gameCanvas');
const ctx = canvas.getContext('2d');
const spriteSheet = new Image();
spriteSheet.src = 'character.png';

function renderCharacter() {
    ctx.clearRect(0, 0, canvas.width, canvas.height);

    if (!spriteSheet.complete) return;

    const sx = sprite.currentFrame * sprite.frameWidth;
    const sy = sprite.row * sprite.frameHeight;

    ctx.save();
    ctx.translate(character.x, character.y);
    if (sprite.row === 1) { // 向左移动时水平翻转
        ctx.scale(-1, 1);
        ctx.drawImage(spriteSheet, sx, sy, sprite.frameWidth, sprite.frameHeight, 
                      -sprite.frameWidth, 0, sprite.frameWidth, sprite.frameHeight);
    } else {
        ctx.drawImage(spriteSheet, sx, sy, sprite.frameWidth, sprite.frameHeight, 
                      0, 0, sprite.frameWidth, sprite.frameHeight);
    }
    ctx.restore();
}

边界检测

添加场景边界限制,防止角色移出可视区域。计算碰撞体积,实现简单的碰撞检测系统。

function checkBoundaries() {
    character.x = Math.max(0, Math.min(canvas.width - sprite.frameWidth, character.x));
    character.y = Math.max(0, Math.min(canvas.height - sprite.frameHeight, character.y));
}

// 在updatePosition函数末尾调用
checkBoundaries();

性能优化

使用对象池管理游戏对象,减少内存分配。实现视口裁剪,只渲染可见区域的元素。

function optimizeRendering() {
    // 计算可见区域
    const viewportLeft = Math.max(0, character.x - canvas.width/2);
    const viewportTop = Math.max(0, character.y - canvas.height/2);

    // 只渲染位于视口内的对象
    // ...
}

移动端支持

添加触摸控制支持,创建虚拟摇杆界面。实现手势识别处理滑动操作。

js实现人物行走

const touchArea = document.getElementById('touchArea');
let touchStartX = 0;
let touchStartY = 0;

touchArea.addEventListener('touchstart', (e) => {
    touchStartX = e.touches[0].clientX;
    touchStartY = e.touches[0].clientY;
});

touchArea.addEventListener('touchmove', (e) => {
    const touchX = e.touches[0].clientX;
    const touchY = e.touches[0].clientY;

    // 根据滑动距离和方向设置移动状态
    // ...
});

标签: 人物js
分享给朋友:

相关文章

js实现验证码

js实现验证码

实现验证码的JavaScript方法 生成随机验证码 使用Math.random()生成随机字符串,结合数字和字母: function generateCaptcha() { const cha…

js实现继承

js实现继承

原型链继承 通过将子类的原型指向父类的实例实现继承。子类实例可以访问父类原型上的属性和方法。 function Parent() { this.name = 'parent'; } Parent…

js实现打印

js实现打印

使用window.print()方法实现打印 在JavaScript中,可以通过调用window.print()方法直接触发浏览器的打印功能。这会打开系统的打印对话框,用户可以选择打印机和设置打印选项…

js实现全选

js实现全选

实现全选功能的方法 在JavaScript中实现全选功能通常涉及监听全选复选框的点击事件,并根据其状态控制其他复选框的选中状态。以下是几种常见的实现方式: 基础DOM操作实现 通过获取所有目标复选框…

js 进度条的实现

js 进度条的实现

使用 HTML 和 CSS 创建基础进度条 HTML 结构可以简单使用一个 div 元素作为容器,内部嵌套另一个 div 表示进度: <div class="progress-containe…

js实现路由

js实现路由

js实现路由的方法 在JavaScript中实现路由功能可以通过多种方式完成,以下是几种常见的方法: 使用原生JavaScript实现路由 通过监听window.onhashchange事件来实现基…