О чем этот пример

При создании уровней в редакторах вроде Tiled можно применять к тайлам горизонтальное и вертикальное отражение. Это позволяет разнообразить окружение, используя один и тот же набор изображений. Однако при импорте карты в Phaser важно убедиться, что все трансформации отображаются корректно. Данный пример показывает, как провести визуальный тест, сравнив рендеринг tilemap в Phaser с оригинальным скриншотом из Tiled. Это полезно для отладки и гарантии, что ваш игровой мир выглядит именно так, как задумано.

Версия 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('kenney_redux_64x64', 'assets/tilemaps/tiles/kenney_redux_64x64.png');
        this.load.image('flipped-tiles-screenshot', 'assets/tilemaps/visual-tests/flipped-tiles-screenshot.png');
        this.load.tilemapTiledJSON('map', 'assets/tilemaps/maps/flipped-tiles.json');
    }

    create ()
    {
        // Visual test to make sure tiles flip properly - should match the given screenshot from Tiled

        this.add.text(10, 10, 'Tilemap Rendering:', {
            fontSize: '18px',
            padding: { x: 10, y: 5 },
            fill: '#000000',
            backgroundColor: '#ffffff'
        });

        const map = this.make.tilemap({ key: 'map'});
        const tileset = map.addTilesetImage('kenney_redux_64x64');
        const layer = map.createLayer(0, tileset, 0, 50);

        this.add.text(310, 10, 'Tiled Screenshot of Map:', {
            fontSize: '18px',
            padding: { x: 10, y: 5 },
            fill: '#000000',
            backgroundColor: '#ffffff'
        });

        const image = this.add.image(300, 40, 'flipped-tiles-screenshot');
        image.setOrigin(0);
        image.setScale(0.65);
    }
}

const config = {
    type: Phaser.AUTO,
    width: 800,
    height: 600,
    backgroundColor: '#312136',
    parent: 'phaser-example',
    pixelArt: true,
    scene: Example
};

const game = new Phaser.Game(config);

Настройка загрузки ресурсов

В методе preload загружаются все необходимые ресурсы для примера. Обратите внимание, что используется this.load.setBaseURL, чтобы задать базовый URL для всех последующих загрузок. Это удобно, если ваши ресурсы хранятся в одном месте.

this.load.setBaseURL('https://raw.githubusercontent.com/phaserjs/examples/master/public/');
this.load.image('kenney_redux_64x64', 'assets/tilemaps/tiles/kenney_redux_64x64.png');
this.load.image('flipped-tiles-screenshot', 'assets/tilemaps/visual-tests/flipped-tiles-screenshot.png');
this.load.tilemapTiledJSON('map', 'assets/tilemaps/maps/flipped-tiles.json');

Загружаются три ключевых ресурса: набор тайлов (kenney_redux_64x64), скриншот исходной карты из Tiled (flipped-tiles-screenshot) и сама карта в формате JSON (map), экспортированная из Tiled. Карта JSON уже содержит информацию о том, какие тайлы перевернуты.

Создание tilemap и слоя

В методе create сначала создается текстовый заголовок для визуального разделения. Затем происходит основная работа с картой.

const map = this.make.tilemap({ key: 'map'});
const tileset = map.addTilesetImage('kenney_redux_64x64');
const layer = map.createLayer(0, tileset, 0, 50);

1. this.make.tilemap создает объект Tilemap из загруженных данных JSON по ключу 'map'. 2. map.addTilesetImage связывает загруженное изображение тайлов ('kenney_redux_64x64') с набором тайлов, описанным в карте. Имя набора должно совпадать с именем в Tiled. 3. map.createLayer создает и отображает слой с индексом 0. Последние два аргумента (0, 50) задают позицию отрисовки слоя на экране (X, Y). Phaser автоматически применяет все трансформации тайлов (отражения), указанные в JSON-файле карты.

Добавление эталонного скриншота для сравнения

Чтобы наглядно сравнить результат рендеринга Phaser с ожидаемым видом из редактора, на сцену добавляется скриншот, сделанный в Tiled.

const image = this.add.image(300, 40, 'flipped-tiles-screenshot');
image.setOrigin(0);
image.setScale(0.65);

Скриншот позиционируется с помощью this.add.image. Метод setOrigin(0) устанавливает точку привязки изображения в его левый верхний угол, что упрощает выравнивание. setScale(0.65) уменьшает скриншот, чтобы он поместился на экране рядом с отрендеренной картой. Разместив их рядом, можно быстро оценить, корректно ли Phaser обработал перевернутые тайлы.

Конфигурация игры и важный параметр pixelArt

Конфигурация игры содержит важный для работы с пиксельной графикой параметр.

const config = {
    type: Phaser.AUTO,
    width: 800,
    height: 600,
    backgroundColor: '#312136',
    parent: 'phaser-example',
    pixelArt: true,
    scene: Example
};

Установка pixelArt: true отключает сглаживание (anti-aliasing) для всех текстур при масштабировании. Это критически важно, если вы используете пиксель-арт тайлы, как в данном примере. Без этого флага четкие края пикселей могут стать размытыми, и визуальное сравнение с эталоном будет некорректным.

Что попробовать дальше

Этот пример демонстрирует простой, но эффективный метод визуальной проверки корректности рендеринга tilemap, особенно при использовании продвинутых свойств тайлов вроде отражения. Для экспериментов попробуйте изменить параметры в createLayer (например, позицию или индекс слоя), отключить pixelArt в конфиге, чтобы увидеть разницу, или создать свою карту в Tiled с различными комбинациями перевернутых тайлов и импортировать её.