О чем этот пример
Детектирование конкретной отпущенной кнопки мыши — частый запрос в играх, будь то выпуск снаряда при отпускании ЛКМ или отмена действия через ПКМ. Часто разработчики проверяют только факт клика, но не то, какая именно кнопка была отпущена. Встроенные методы Phaser `pointer.leftButtonReleased()` и подобные позволяют легко и точно обрабатывать такие события. Эта статья покажет, как отслеживать отпускание любой кнопки мыши — от основной до дополнительных (вперёд/назад) — и использовать это для игровой механики.
Версия Phaser: код и демо в этой статье рассчитаны на Phaser 3.90.0.
Живой запуск
Ниже встроен рабочий билд примера. Оригинальный источник: GitHub.
Исходный код
class Example extends Phaser.Scene
{
text2;
text1;
preload ()
{
this.load.setBaseURL('https://raw.githubusercontent.com/phaserjs/examples/master/public/');
this.load.image('logo', 'assets/sprites/phaser.png');
this.load.image('asuna', 'assets/sprites/asuna_by_vali233.png');
this.load.image('disk', 'assets/sprites/oz_pov_melting_disk.png');
this.load.image('tree', 'assets/sprites/palm-tree-left.png');
}
create ()
{
this.text1 = this.add.text(10, 10, '', { fill: '#00ff00' });
this.text2 = this.add.text(500, 10, '', { fill: '#00ff00' });
this.input.mouse.disableContextMenu();
this.input.on('pointerup', pointer =>
{
if (pointer.leftButtonReleased())
{
this.text2.setText('Left Button was released');
}
else if (pointer.rightButtonReleased())
{
this.text2.setText('Right Button was released');
}
else if (pointer.middleButtonReleased())
{
this.text2.setText('Middle Button was released');
}
else if (pointer.backButtonReleased())
{
this.text2.setText('Back Button was released');
}
else if (pointer.forwardButtonReleased())
{
this.text2.setText('Forward Button was released');
}
});
}
update ()
{
const pointer = this.input.activePointer;
this.text1.setText([
`x: ${pointer.worldX}`,
`y: ${pointer.worldY}`,
`isDown: ${pointer.isDown}`
]);
}
}
const config = {
width: 800,
height: 600,
type: Phaser.AUTO,
parent: 'phaser-example',
scene: Example
};
const game = new Phaser.Game(config);
Подготовка сцены и настройка ввода
В первую очередь нужно настроить сцену и загрузить ресурсы. Важный шаг — отключение стандартного контекстного меню браузера, которое появляется при клике правой кнопкой мыши. Это необходимо, чтобы игра полностью контролировала ввод.
this.input.mouse.disableContextMenu();
Слушатель события pointerup
Основная логика обработки размещается в обработчике события 'pointerup'. Это событие срабатывает, когда любая кнопка указателя (мыши или касания) отпускается. Внутри обработчика мы получаем объект pointer, который содержит информацию о событии.
this.input.on('pointerup', pointer => {
// Логика проверки кнопок здесь
});
Определение отпущенной кнопки
Объект pointer предоставляет набор булевых методов для точного определения, какая кнопка была отпущена именно в этом событии. Их следует вызывать только внутри обработчика 'pointerup'.
if (pointer.leftButtonReleased())
{
this.text2.setText('Left Button was released');
}
else if (pointer.rightButtonReleased())
{
this.text2.setText('Right Button was released');
}
else if (pointer.middleButtonReleased())
{
this.text2.setText('Middle Button was released');
}
else if (pointer.backButtonReleased())
{
this.text2.setText('Back Button was released');
}
else if (pointer.forwardButtonReleased())
{
this.text2.setText('Forward Button was released');
}
Каждый метод (например, leftButtonReleased()) возвращает true только если соответствующая кнопка была отпущена в момент этого конкретного события pointerup. Это позволяет различать действия для разных кнопок.
Отслеживание состояния указателя в реальном времени
Помимо обработки событий, полезно в реальном времени отслеживать общее состояние указателя — его координаты и нажата ли какая-либо кнопка. Для этого используется метод update и свойство this.input.activePointer.
update ()
{
const pointer = this.input.activePointer;
this.text1.setText([
`x: ${pointer.worldX}`,
`y: ${pointer.worldY}`,
`isDown: ${pointer.isDown}`
]);
}
pointer.worldX и pointer.worldY дают координаты в игровом мире, а pointer.isDown показывает, нажата ли в данный момент любая кнопка.
Что попробовать дальше
Использование методов pointer.leftButtonReleased() и их аналогов — самый чистый и надёжный способ обработки отпускания конкретных кнопок мыши в Phaser. Это открывает путь к созданию сложных механик ввода. Попробуйте реализовать зарядку выстрела: сила выстрела увеличивается, пока зажата ЛКМ, и рассчитывается в момент её отпускания. Или создайте контекстное меню игры, которое появляется при отпускании ПКМ, — теперь у вас есть точный инструмент для этого.
