О чем этот пример
В игровой разработке часто требуется хранить и отслеживать дополнительную информацию об объектах, например, уровень персонажа или количество золота. Phaser предоставляет удобную систему Data Manager и события `setdata` и `changedata`. В этой статье мы разберем, как привязать пользовательские данные к спрайту и реагировать на их изменение, что позволит легко синхронировать игровую логику с визуальным представлением.
Версия 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('gem', 'assets/sprites/gem.png');
}
create ()
{
const text = this.add.text(350, 250, '', { font: '16px Courier', fill: '#00ff00' });
const text2 = this.add.text(30, 30, '', { font: '16px Courier', fill: '#00ff00' });
const list = [ 'Gem Data:', '' ];
const gem = this.add.image(300, 300, 'gem');
// Store some data about this Gem:
gem.setDataEnabled();
// Whenever a data value is first set it will dispatch a setdata event
gem.on('setdata', function (gameObject, key, value) {
list.push(key);
text2.setText(list);
});
gem.data.set('name', 'Red Gem Stone');
gem.data.set('level', 2);
gem.data.set('owner', 'Link');
// Whenever a data value is updated it will dispatch a changedata event
gem.on('changedata', function (gameObject, key, value) {
text.setText([
'Name: ' + gem.data.get('name'),
'Level: ' + gem.data.get('level'),
'Value: ' + gem.data.get('gold') + ' gold',
'Owner: ' + gem.data.get('owner')
]);
});
// Change the 'value' property when the mouse is clicked
this.input.on('pointerdown', function () {
const gold = gem.data.get('gold');
if (!gold)
{
// Set the value, this will emit the `setdata` and `changedata` events
gem.data.set('gold', 50);
text.setText([
'Name: ' + gem.data.get('name'),
'Level: ' + gem.data.get('level'),
'Value: ' + gem.data.get('gold') + ' gold',
'Owner: ' + gem.data.get('owner')
]);
}
else
{
// Set the value, this will call the 'after' callback
gem.data.set('gold', gold + 50);
}
});
}
}
const config = {
type: Phaser.AUTO,
parent: 'phaser-example',
width: 800,
height: 600,
scene: Example
};
const game = new Phaser.Game(config);
Включение системы данных для объекта
Прежде чем объект сможет хранить пользовательские данные, для него необходимо активировать Data Manager. Это делается методом setDataEnabled().
gem.setDataEnabled();
После этого вызова объект gem получает свойство .data, через которое можно устанавливать и получать значения. Метод подготавливает объект к работе с системой событий данных.
Событие `setdata` при первой установке значения
Событие setdata срабатывает в момент, когда вы в первый раз присваиваете значение конкретному ключу. Это полезно для логирования или инициализации связанных систем.
gem.on('setdata', function (gameObject, key, value) {
list.push(key);
text2.setText(list);
});
В примере обработчик добавляет имя нового ключа (key) в массив list и обновляет текст на экране. Так мы видим, какие данные были добавлены в объект.
Инициализация данных и событие `changedata`
После включения системы можно установить начальные значения с помощью метода .data.set(). Событие changedata срабатывает каждый раз, когда значение существующего ключа изменяется.
gem.data.set('name', 'Red Gem Stone');
gem.data.set('level', 2);
gem.data.set('owner', 'Link');
gem.on('changedata', function (gameObject, key, value) {
text.setText([
'Name: ' + gem.data.get('name'),
'Level: ' + gem.data.get('level'),
'Value: ' + gem.data.get('gold') + ' gold',
'Owner: ' + gem.data.get('owner')
]);
});
Обработчик changedata обновляет основной текст на экране, отображая актуальные данные объекта. Обратите внимание, что событие не сработает при первой установке ключа gold, так как для него сначала вызовется setdata.
Обработка клика для изменения данных
Логика изменения данных часто привязана к действиям игрока. В примере клик мыши увеличивает значение ключа gold.
this.input.on('pointerdown', function () {
const gold = gem.data.get('gold');
if (!gold)
{
gem.data.set('gold', 50);
}
else
{
gem.data.set('gold', gold + 50);
}
});
При первом клике ключ gold создается (сработает setdata), а при последующих — изменяется (сработает changedata). Метод .data.get() безопасно возвращает значение, даже если ключа еще не существует.
Что попробовать дальше
Система данных Phaser — это мощный инструмент для связывания игровой логики с объектами. Вы можете хранить в ней здоровье, инвентарь, статусы эффектов. Поэкспериментируйте: создайте систему квестов, где завершение задачи меняет данные NPC, или реализуйте индикатор, который автоматически обновляется при изменении значения health у персонажа.
