О чем этот пример
По умолчанию Phaser предоставляет одну основную камеру для отрисовки игрового мира. Но что, если вам нужен split-screen для многопользовательской игры, статичный интерфейс поверх основного мира или сложные эффекты с разными областями видимости? Решение — использование нескольких камер, которые можно легко настроить прямо в конфигурации сцены. Эта статья покажет, как декларативно создавать несколько камер с разными параметрами и управлять ими.
Версия Phaser: код и демо в этой статье рассчитаны на Phaser 3.90.0.
Живой запуск
Ниже встроен рабочий билд примера. Оригинальный источник: GitHub.
Исходный код
// Scene configuration
const sceneConfig = {
key: 'Example',
cameras: [
{
width: 400,
height: 300,
backgroundColor: '#ff0000'
},
{
x: 400,
y: 0,
width: 400,
height: 300,
backgroundColor: '#ff00ff'
},
{
x: 0,
y: 300,
width: 400,
height: 300,
backgroundColor: '#ffff00'
},
{
x: 400,
y: 300,
width: 400,
height: 300,
backgroundColor: '#00ff00'
}
]
};
// Scene
class Example extends Phaser.Scene
{
constructor ()
{
super(sceneConfig);
}
preload ()
{
this.load.setBaseURL('https://raw.githubusercontent.com/phaserjs/examples/master/public/');
this.load.image('mech', 'assets/pics/titan-mech.png');
}
create ()
{
this.image = this.add.image(200, 150, 'mech');
}
update ()
{
this.image.rotation += 0.01;
}
}
const config = {
type: Phaser.WEBGL,
parent: 'phaser-example',
width: 800,
height: 600,
scene: Example
};
const game = new Phaser.Game(config);
Конфигурация камер через sceneConfig
В Phaser 3 камеры можно создавать не только через this.cameras.add в методе create сцены, но и на этапе её инициализации. Это делается через специальный объект конфигурации, который передаётся в конструктор родительского класса Phaser.Scene.
Ключевой параметр — массив cameras. Каждый его элемент — это объект с настройками для отдельной камеры. В этом примере создаётся четыре камеры, делящие окно игры на четыре равные части.
const sceneConfig = {
key: 'Example',
cameras: [
{
width: 400,
height: 300,
backgroundColor: '#ff0000'
},
// ... другие камеры
]
};
class Example extends Phaser.Scene
{
constructor ()
{
super(sceneConfig); // Передаём конфиг в родительский конструктор
}
}
При таком подходе камеры создаются автоматически до вызова метода preload. Свойство key в конфиге сцены является обязательным для её идентификации в Phaser.
Настройка положения, размера и фона
Каждая камера в массиве настраивается независимо. Основные параметры:
- `x,y`: Положение *вида* (viewport) камеры на игровом холсте (рендерере). По умолчанию (0, 0).
- width, height: Размеры *вида* камеры.
- backgroundColor: Цвет фона, который будет заполнять область вида, если там нет игровых объектов.
В примере создаётся сетка 2x2. Первая камера (красный фон) занимает левый верхний квадрант (0,0, 400x300). Вторая (розовый) смещена по X на 400 пикселей и занимает правый верхний угол. Третья и четвёртая смещены по оси Y на 300 пикселей.
{
x: 400,
y: 0,
width: 400,
height: 300,
backgroundColor: '#ff00ff'
}
Важно: эти параметры задают область отрисовки на *экране*, а не область видимости внутри игрового мира. По умолчанию все камеры смотрят на одну и ту же точку мира (0,0), но их можно перемещать независимо с помощью методов camera.scrollX и camera.scrollY.
Работа с камерами в сцене
После создания через конфиг камеры становятся доступны в свойстве this.cameras (объект CameraManager). Основная (первая созданная) камера также доступна через this.cameras.main. Все камеры хранятся в коллекции this.cameras.cameras.
В методе create нашего примера изображение добавляется в сцену через this.add.image. По умолчанию игровые объекты рендерятся на *все* камеры, у которых не отключён рендеринг. Поэтому механическая картинка появляется сразу в четырёх квадрантах экрана.
create ()
{
// Этот объект будет отрисован на всех активных камерах
this.image = this.add.image(200, 150, 'mech');
}
Метод update вращает это изображение, и анимация видна во всех четырёх видах одновременно, так как они показывают один и тот же игровой объект в мире.
Практическое применение и управление
Зачем это нужно? Представьте split-screen для гонок, где каждый игрок видит свою часть трассы, или статичный HUD в отдельной камере, который не двигается при скролле основного мира.
Вы можете точечно управлять рендерингом объектов на конкретных камерах. Вот как, например, сделать объект видимым только для первой камеры:
// В методе create, после создания объекта:
this.image.setVisible(false); // Сначала скрываем для всех
this.cameras.cameras[0].visible = true; // Включаем видимость для камеры с индексом 0
// ИЛИ через менеджер, если знаем ключ камеры (если он был задан в конфиге)
// this.cameras.getCamera('Camera1').visible = true;
Камеры можно перемещать по игровому миру независимо друг от друга, задавая им разные scrollX и scrollY. Это позволяет реализовать сложные динамические виды.
Что попробовать дальше
Использование конфигурации cameras — это мощный и декларативный способ создать сложную систему отображения в самом начале жизни сцены. Вы можете разделить экран на области с разным фоном, а затем гибко управлять тем, какие объекты и куда рендерятся. Для экспериментов попробуйте
- Задать разный
zoomдля каждой камеры в конфиге - В цикле в
updateдвигать камеры с разной скоростью, создавая эффект параллакса - Назначить разным игровым объектам разные камеры для отрисовки через
setVisible
