Input
Опрос клавиатуры. Input отвечает на один вопрос — зажата ли сейчас эта клавиша? — и ты
спрашиваешь его каждый кадр внутри setLoop. Событий клавиш нет (никаких keydown/keyup-слушателей);
для тапов и перетаскиваний по объектам используй события указателя.
Обзор
setLoop(dt => {
if (Input.key('ArrowRight')) player.x += 200 * dt
if (Input.key('ArrowLeft')) player.x -= 200 * dt
})Опрос
Input.key(code: string): boolean // true, пока клавиша зажатаcode — строка в стиле KeyboardEvent.code — это физическая клавиша, а не введённый символ:
'ArrowRight', 'KeyW', 'Space', 'Enter', 'ShiftLeft'. WASD — это 'KeyW'/'KeyA'/
'KeyS'/'KeyD' независимо от раскладки.
опрос, а не события — умножай перемещение на dt (секунды), чтобы скорость не зависела от частоты
кадров.
«Нажата в этом кадре» — детект фронта
Input.key срабатывает по уровню (true каждый кадр, пока клавиша зажата). Для действий, которые
должны срабатывать раз на нажатие (прыжок, выстрел), держи карту wasDown и защёлкивай её в
конце кадра:
const wasDown: Record<string, boolean> = {}
const pressed = (code: string) => Input.key(code) && !wasDown[code]
setLoop(dt => {
if (pressed('Space')) player.jump() // срабатывает раз на нажатие
if (Input.key('ArrowRight')) player.x += 200 * dt // срабатывает каждый кадр, пока зажато
wasDown['Space'] = Input.key('Space') // защёлкнуть в конце кадра
})Защёлкивай каждую клавишу, для которой ловишь фронт — по одной строке на клавишу в конце цикла.
Подводные камни
// ✗ проверка по уровню для одноразового действия — прыгает каждый кадр, пока зажат Space
if (Input.key('Space')) player.jump()
// ✓ лови фронт по рецепту с wasDown выше
if (pressed('Space')) player.jump()
// ✗ символьные коды — зависят от раскладки и не то, что ждёт Input.key
Input.key('w')
// ✓ физические коды клавиш
Input.key('KeyW')Смотрите также
- События указателя и жесты — тапы касанием/мышью и трекинг перетаскивания.
- Соглашения —
setLoopиdtв секундах.