О чем этот пример
Движение объектов по заданным траекториям — одна из ключевых механик в играх. Использование системы Path Follower в Phaser позволяет создавать сложные, плавные и повторяющиеся пути для спрайтов без написания сложной логики вручную. Этот подход идеально подходит для создания патрулирующих врагов, летящих снарядов, платформ-лифтеров или декоративных анимированных элементов. В статье мы разберем пример, где спрайт движется по составному пути, состоящему из сплайнов, линий, эллипсов и кривых Безье.
Версия Phaser: код и демо в этой статье рассчитаны на Phaser 3.90.0.
Живой запуск
Ниже встроен рабочий билд примера. Оригинальный источник: GitHub.
Исходный код
class Example extends Phaser.Scene
{
preload ()
{
this.load.setBaseURL('https://raw.githubusercontent.com/phaserjs/examples/master/public/');
this.load.image('lemming', 'assets/sprites/lemming.png');
}
create ()
{
const path = new Phaser.Curves.Path(50, 500);
path.splineTo([ 164, 446, 274, 542, 412, 457, 522, 541, 664, 464 ]);
path.lineTo(700, 300);
path.lineTo(600, 350);
path.ellipseTo(200, 100, 100, 250, false, 0);
path.cubicBezierTo(222, 119, 308, 107, 208, 368);
path.ellipseTo(60, 60, 0, 360, true);
const graphics = this.add.graphics();
graphics.lineStyle(1, 0xffffff, 1);
path.draw(graphics, 128);
const lemming = this.add.follower(path, 50, 500, 'lemming');
lemming.startFollow({
duration: 10000,
yoyo: true,
repeat: -1,
rotateToPath: true,
verticalAdjust: true
});
}
}
const config = {
type: Phaser.AUTO,
width: 800,
height: 600,
backgroundColor: '#2d2d2d',
parent: 'phaser-example',
scene: Example
};
const game = new Phaser.Game(config);
Создание и определение пути (Path)
В Phaser путь (Phaser.Curves.Path) представляет собой последовательность соединенных кривых. Вы создаете путь, указывая начальную точку, а затем добавляете к нему различные сегменты.
В нашем примере путь начинается в точке (50, 500). Метод splineTo создает плавную кривую (сплайн), проходящую через массив контрольных точек. Затем lineTo добавляет прямые отрезки. Методы ellipseTo и cubicBezierTo позволяют рисовать эллипсы и кубические кривые Безье соответственно.
Для визуализации пути в целях отладки мы создаем объект Graphics и рисуем на нем наш путь с помощью метода draw.
const path = new Phaser.Curves.Path(50, 500);
path.splineTo([ 164, 446, 274, 542, 412, 457, 522, 541, 664, 464 ]);
path.lineTo(700, 300);
path.lineTo(600, 350);
path.ellipseTo(200, 100, 100, 250, false, 0);
path.cubicBezierTo(222, 119, 308, 107, 208, 368);
path.ellipseTo(60, 60, 0, 360, true);
const graphics = this.add.graphics();
graphics.lineStyle(1, 0xffffff, 1);
path.draw(graphics, 128);
Настройка следящего объекта (Follower)
Чтобы заставить спрайт следовать по созданному пути, используется объект Follower. Он создается через this.add.follower(), куда передаются сам путь, начальные координаты (которые должны совпадать с началом пути) и ключ текстуры.
const lemming = this.add.follower(path, 50, 500, 'lemming');
После создания объекта необходимо запустить анимацию следования, вызвав метод startFollow(). Этот метод принимает объект конфигурации, который определяет поведение движения.
lemming.startFollow({
duration: 10000,
yoyo: true,
repeat: -1,
rotateToPath: true,
verticalAdjust: true
});
- duration: Время в миллисекундах, за которое объект пройдет весь путь от начала до конца.
- yoyo: Если true, объект, дойдя до конца пути, развернется и пойдет обратно.
- repeat: Количество повторений. Значение -1 означает бесконечное повторение.
- rotateToPath: Автоматически поворачивает спрайт так, чтобы его передняя часть была направлена по касательной к траектории движения. Критически важно для реалистичного движения машин, самолетов или персонажей.
- verticalAdjust: Небольшая коррекция позиции спрайта по вертикали для более точного совмещения с линией пути.
Конфигурация игры и сцены
Для запуска примера необходимо создать стандартную конфигурацию игры Phaser (Phaser.Game). В ней указывается тип рендерера, размеры холста, цвет фона и корневой класс сцены.
Ключевой элемент — класс Example, расширяющий Phaser.Scene. В нем реализованы два основных метода жизненного цикла:
1. preload(): Здесь загружаются необходимые ассеты (в нашем случае — изображение спрайта 'lemming'). Базовый URL упрощает загрузку из репозитория с примерами.
2. create(): В этом методе, выполняемом один раз после загрузки ресурсов, происходит основная логика: создание пути, его отрисовка и настройка следящего объекта.
const config = {
type: Phaser.AUTO,
width: 800,
height: 600,
backgroundColor: '#2d2d2d',
parent: 'phaser-example',
scene: Example
};
const game = new Phaser.Game(config);
Что попробовать дальше
Система Path Follower в Phaser предоставляет мощный и гибкий инструмент для анимации движения по сложным траекториям. Всего несколькими строками кода можно создать циклическое, плавное и визуально привлекательное перемещение объектов.
**Идеи для экспериментов:**
1. Измените параметры ellipseTo и cubicBezierTo, чтобы создавать более замысловатые петли и виражи.
2. Попробуйте создать несколько объектов-follower на одном пути с разной скоростью (duration) или задержкой перед стартом.
3. Используйте событие 'complete' у объекта lemming, чтобы запускать определенные действия (например, атаку или смену анимации) в момент достижения конца пути.
4. Сделайте путь динамическим: модифицируйте контрольные точки пути path.curves[i].points во время выполнения игры в ответ на действия игрока.
