О чем этот пример
При создании игр часто возникает необходимость заставить спрайт плавно следовать по заданному пути, будь то полёт снаряда, движение патрульного или траектория платформы. Phaser 3 предоставляет для этого мощный инструмент — Follower. Однако, при включении автоматического поворота (`rotateToPath`) спрайт может быть изначально сориентирован не так, как требуется. Параметр `rotationOffset` решает эту проблему, позволяя скорректировать начальный и последующий угол объекта относительно пути. Эта статья научит вас тонко управлять ориентацией объектов, движущихся по кривым, что критически важно для визуальной согласованности геймплея.
Версия 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 curve = new Phaser.Curves.Line(new Phaser.Math.Vector2(100, 100), new Phaser.Math.Vector2(600, 400));
const graphics = this.add.graphics();
graphics.lineStyle(1, 0xffffff, 0.5);
curve.draw(graphics);
const lemming = this.add.follower(curve, 100, 100, 'lemming');
lemming.startFollow({
duration: 5000,
yoyo: true,
repeat: -1,
rotateToPath: true,
rotationOffset: 90
});
}
}
const config = {
type: Phaser.AUTO,
width: 800,
height: 600,
backgroundColor: '#2d2d2d',
parent: 'phaser-example',
scene: Example
};
const game = new Phaser.Game(config);
Создание сцены и базовой кривой
Вся логика примера содержится в методе create сцены. Первым делом создаётся объект кривой — в данном случае это прямая линия (Phaser.Curves.Line), заданная двумя точками в мировых координатах.
const curve = new Phaser.Curves.Line(new Phaser.Math.Vector2(100, 100), new Phaser.Math.Vector2(600, 400));
Затем создаётся объект Graphics и настраивается его стиль для отрисовки линии. После этого сама кривая отрисовывается на холсте Graphics. Это необязательный, но очень полезный шаг для визуализации пути в целях отладки.
const graphics = this.add.graphics();
graphics.lineStyle(1, 0xffffff, 0.5);
curve.draw(graphics);
Инициализация Follower и ключевые параметры
Спрайт-последователь создаётся с помощью метода this.add.follower(). В него передаются сама кривая, начальные координаты (которые будут переопределены кривой) и ключ текстуры.
const lemming = this.add.follower(curve, 100, 100, 'lemming');
Запуск движения осуществляется методом startFollow(), который принимает объект конфигурации. Разберём его основные свойства:
- duration: Время в миллисекундах, за которое объект пройдёт от начала до конца кривой.
- yoyo: Если true, объект, достигнув конца пути, развернётся и пойдёт обратно.
- repeat: Количество повторений (-1 для бесконечного цикла).
- rotateToPath: Самая важная настройка. При значении true спрайт будет автоматически вращаться, чтобы его "передняя" часть (положительное направление оси Y) была направлена по касательной к пути.
lemming.startFollow({
duration: 5000,
yoyo: true,
repeat: -1,
rotateToPath: true,
rotationOffset: 90
});
Магия rotationOffset: корректировка угла
Параметр rotationOffset — это решение проблемы неверной начальной ориентации. По умолчанию, когда rotateToPath включён, Phaser считает, что "лицо" вашего спрайта смотрит вверх (в сторону положительной оси Y). Если же на спрайте, как в нашем примере с леммингом, персонаж нарисован смотрящим вправо, его направление не совпадёт с направлением пути.
rotationOffset позволяет добавить фиксированное смещение к вычисленному углу поворота. Значение указывается в градусах.
rotationOffset: 90
Установив смещение в 90 градусов, мы по сути говорим движку: "Поверни вычисленный угол ещё на четверть круга по часовой стрелке". Если спрайт изначально смотрит вправо (0 градусов в системе координат Phaser), то после применения смещения он будет корректно ориентирован вдоль пути. Без этого параметра лемминг двигался бы боком.
Важно: это смещение применяется постоянно на всём протяжении пути, обеспечивая корректную ориентацию как при движении вперёд, так и при использовании опции yoyo.
Полная конфигурация игры
Инициализация самого игрового экземпляра Phaser.Game происходит в конце кода. Конфигурационный объект задаёт основные параметры: тип рендерера, размеры холста, цвет фона, родительский HTML-элемент и стартовую сцену.
const config = {
type: Phaser.AUTO,
width: 800,
height: 600,
backgroundColor: '#2d2d2d',
parent: 'phaser-example',
scene: Example
};
const game = new Phaser.Game(config);
Эта базовая структура конфига является стандартной для большинства проектов на Phaser 3. Ключевой момент — передача класса нашей сцены (Example) в свойство scene.
Что попробовать дальше
Параметр rotationOffset в методе startFollow() — это небольшой, но крайне важный инструмент для тонкой настройки визуализации движения объектов по пути. Он позволяет согласовать "встроенную" ориентацию спрайта в вашем арт-ассете с требованиями игровой логики, не прибегая к ручному вращению текстуры в графическом редакторе.
**Идеи для экспериментов:**
1. Попробуйте изменить значение rotationOffset на -90 или 180 и понаблюдайте за поведением спрайта.
2. Замените Phaser.Curves.Line на более сложную кривую, например, Phaser.Curves.Spline, и убедитесь, что смещение угла работает корректно на всём её протяжении.
3. Создайте цепочку из нескольких последователей (followers) с разными значениями rotationOffset, чтобы сформировать строй или патруль, где каждый объект смотрит в своём направлении относительно пути.
