Skip to content

倾斜(运动传感器) ​

用手机的加速度计控制游戏:左右倾斜转向、前后倾斜加减速。倾斜在 sapling2d/motion 插件里,和键盘共用动作,游戏代码只查动作。

ts
import { key, Node2D, Scene, v } from 'sapling2d'
import { motion, MotionInput, tilt } from 'sapling2d/motion'

declare module 'sapling2d' {
  interface ActionRegistry {
    steerLeft: true
    steerRight: true
  }
}

// 倾斜和键盘共用动作:浏览器里按 A / D,手机上左右倾斜(5° 以内不动,30° 满力度)
export const actions = { steerLeft: [key('KeyA'), tilt('left')], steerRight: [key('KeyD'), tilt('right')] }
export const plugins = [motion()]

class Car extends Node2D {
  override physicsProcess(dt: number) {
    // 力度 0–1:倾斜越多转得越快;游戏不关心输入来自键盘还是传感器
    this.x += this.tree.input.getAxis('steerLeft', 'steerRight') * 400 * dt
  }
}

export class Track extends Scene {
  car!: Car

  override ready() {
    this.car = this.add(new Car({ position: v(375, 1100) }))
    // iOS 浏览器要在第一次触摸时授权:prompt 期间可以提示“点击屏幕开启重力感应”
    const sensor = this.tree.get(MotionInput)
    if (sensor.permission === 'prompt') console.log('tap to enable tilt')
  }
}

// 启动参数:startGame({ main: Track, actions, plugins })

测试里用 g.inject 注入传感器数据:

ts
const x0 = g.scene.car.x
const deg = (20 * Math.PI) / 180
g.inject({ type: 'motion', x: Math.sin(deg), y: 0, z: Math.cos(deg) }) // 向左压低 20°(单位 g,设备坐标)
g.step()
expect(g.tree.input.getActionStrength('steerLeft')).toBeCloseTo(0.6) // (20° − 5°) / (30° − 5°)
g.stepSeconds(1)
expect(g.scene.car.x).toBeLessThan(x0)
expect(g.tree.get(MotionInput).permission).toBe('granted') // 无头平台当作已授权

绑定:tilt() ​

plugins: [motion()] 安装插件后,tilt(dir, { deadzone?, full? }) 把倾斜角换成 0–1 的力度:默认 5° 以内是 0,30° 是 1。

dir含义
left / right左边 / 右边压低
forward / back上边 / 下边压低

方向以竖屏持机为准。forward / back 的基线是手机平放,而人手持时本来就有几十度的倾斜,所以多数游戏只用左右。

原始值:MotionInput ​

this.tree.get(MotionInput) 提供:

成员说明
x / y / z含重力的加速度,单位 g,设备坐标:向右 +x、向上 +y、朝外 +z;已平滑(motion({ smoothing }),默认 0.2)
roll / pitch角度(度)
available有没有传感器
permissiongranted / denied / prompt / unsupported

各平台 ​

  • iOS 浏览器要在用户手势里申请权限,插件会在第一次触摸时自动申请。permission === 'prompt' 期间,显示"点击屏幕开启重力感应"之类的提示,不要在 ready() 里就假定有倾斜输入。
  • 微信小游戏用 wx.startAccelerometer,不用申请权限;切到后台时插件停掉传感器。轴向和单位以真机为准,模拟器不可信。
  • 桌面浏览器没有传感器:available 为 false,倾斜绑定一直是 0,键盘照常可用。

MIT 许可证