О чем этот пример
Анимация — это душа игрового мира, и Phaser предлагает мощный инструмент для её создания: систему твинов. Часто игровому объекту нужно выполнить не одно, а последовательность движений — плавно проехать по маршруту, сделать комбо-прыжок или нарисовать сложную траекторию. Ручное управление несколькими анимациями быстро становится громоздким. В этой статье мы разберём метод `tweens.chain()`, который позволяет создавать цепочки анимаций, где каждый следующий твин начинается после завершения предыдущего. Это делает код чище, логику — понятнее, а анимации — бесшовными.
Версия Phaser: код и демо в этой статье рассчитаны на Phaser 3.90.0.
Живой запуск
Ниже встроен рабочий билд примера. Оригинальный источник: GitHub.
Исходный код
class Example extends Phaser.Scene
{
constructor()
{
super();
}
preload ()
{
this.load.setBaseURL('https://raw.githubusercontent.com/phaserjs/examples/master/public/');
this.load.image('block', 'assets/sprites/block.png');
}
create ()
{
const image = this.add.image(100, 100, 'block');
this.text = this.add.text(16, 16).setFontSize(16).setColor('#ffffff');
this.tween = this.tweens.chain({
targets: image,
persist: true,
tweens: [
{
x: 600,
ease: 'Linear',
duration: 1000,
},
{
y: 500,
ease: 'Linear',
duration: 500
},
{
x: 100,
ease: 'Linear',
duration: 1000
},
{
y: 100,
ease: 'Linear',
duration: 500
},
]
});
}
update ()
{
const t = this.tween;
this.text.setText([
`Duration: ${t.currentTween.duration}`,
`Start Delay: ${t.currentTween.startDelay}`,
`Elapsed: ${t.currentTween.elapsed}`,
`Progress: ${t.currentTween.progress}`,
`State: ${t.state}`
]);
}
}
const config = {
type: Phaser.AUTO,
width: 800,
height: 600,
backgroundColor: '#2d2d2d',
parent: 'phaser-example',
scene: Example
};
const game = new Phaser.Game(config);
Что такое цепочка твинов и зачем она нужна
Цепочка твинов (tween chain) — это последовательность анимаций, применённых к одному или нескольким целям (targets). Ключевое отличие от запуска нескольких независимых твинов в том, что они выполняются строго друг за другом, образуя единый поток. Это идеально для:
* Создания патрульных маршрутов для NPC. * Реализации сложных эффектов (например, объект увеличивается, затем вращается и меняет цвет). * Построения сценариев движения, где важна последовательность.
Метод this.tweens.chain() принимает объект конфигурации, который определяет цели и массив (tweens) с описанием каждого шага анимации.
Разбираем конфигурацию цепочки
В примере мы создаём цепочку для спрайта image. Обратите внимание на параметр persist: true. Он указывает системе твинов не уничтожать данные анимации после её завершения, что критически важно для работы отладочной информации в методе update().
Каждый элемент массива tweens — это конфиг для отдельного твина. Здесь цепочка описывает прямоугольный маршрут: вправо, вниз, влево, вверх.
this.tween = this.tweens.chain({
targets: image,
persist: true, // Сохраняем твин для отладки
tweens: [
{ x: 600, ease: 'Linear', duration: 1000 },
{ y: 500, ease: 'Linear', duration: 500 },
{ x: 100, ease: 'Linear', duration: 1000 },
{ y: 100, ease: 'Linear', duration: 500 },
]
});
Каждый твин в цепочке — это самостоятельная анимация со своими свойствами (`x,y), длительностью (duration) и функцией сглаживания (ease`). Система автоматически запускает следующий твин, когда текущий завершён.
Мониторинг состояния цепочки в реальном времени
Одна из сильных сторон примера — демонстрация отладки. В методе update() мы в реальном времени выводим ключевые параметры текущего активного твина в цепочке. Это возможно благодаря тому, что метод chain() возвращает объект TweenChain, который содержит ссылку на текущий выполняемый твин (currentTween).
update ()
{
const t = this.tween;
this.text.setText([
`Duration: ${t.currentTween.duration}`,
`Start Delay: ${t.currentTween.startDelay}`,
`Elapsed: ${t.currentTween.elapsed}`,
`Progress: ${t.currentTween.progress}`,
`State: ${t.state}`
]);
}
* currentTween.duration / elapsed / progress: показывают длительность, прошедшее время и прогресс (от 0 до 1) именно того твина, который сейчас играет.
* t.state: отображает общее состояние всей цепочки (например, PLAYING, PAUSED).
Такой подход незаменим при тонкой настройке времени и отладке сложных анимационных сценариев.
Что попробовать дальше
Метод tweens.chain() — это элегантное решение для создания последовательных, управляемых анимаций. Он избавляет от необходимости вручную отслеживать события завершения твинов и запускать новые, инкапсулируя всю логику последовательности в одном месте.
**Идеи для экспериментов:**
1. Добавьте разные функции ease (например, 'Bounce', 'Back') в каждый шаг цепочки, чтобы движение стало более "живым".
2. Создайте цепочку, которая меняет не только позицию (`x,y), но и масштаб (scale), угол поворота (angle) и прозрачность (alpha`) объекта.
3. Реализуйте систему патрулирования для врага, зациклив цепочку с помощью loop: -1 в конфигурации основного цепочного твина.
4. Используйте цепочку для построения визуальной траектории снаряда с учетом гравитации (последовательные изменения по `y`).
