JS + Phaser пишем игру с Дино (часть 4) 🦖
В прошлой части мы с вами добавили противников для нашего Дино, а так же разобрались с тем, как делать респаун объектов по своему желанию, если вы это пропустили, то советую вернуться к части 3.
Код, который уже готов живет тут.
Противников мы с вами добавили в предыдущей части, а сегодня займемся тем, чтобы эти противники могли нанести нам урон...
А именно научимся обрабатывать коллизии и определять конец нашей игры)
Начнем отслеживать коллизии
И так, для начала нам нужно как-то определить, что Дино столкнулся с другими объектами, для этого в конструкторе добавим строчку с инициализацией функции, которая будет за это отвечать:
create() {
// Остальной код функции
this.initAnims();
// Добавим еще одну функцию илициализатов
this.initColliders();
this.createControll();
this.initStartTrigger();
}Теперь давайте начнем создавать объявленную функцию:
initColliders() {
this.physics.add.collider(this.dino, this.obsticles, () => { // 1
this.physics.pause(); // 2
this.isGameRunning = false; // 3
this.anims.pauseAll(); // 4
this.dino.setTexture('dino-hurt'); // 5
this.respawnTime = 0; // 6
this.gameSpeed = 10; // 7
}, null, this);
}collider- функция, которая позволяет нам добавить функцию обработчик на ситуации коллизии объектов.- Для начала при столкновении мы с вами остановим всю физику в игре
- Скажем что сейчас игра не идет
- Остановим все анимации, которые у нас сейчас играют
- Навесим на динозавра погибающего спрайта
- Откатим време респауна
- И откатим скорость игры к дефолтному значению
Немного оптимизации
После того как препятствия пропадают из нашей области видимости обработчик этой функции на них сохраняется и код продолжает жить в памяти, из-за того что мы никак ее не высвобождаем. Давайте исправим это!
Для этого нам нужно добавить убийство этих объектов в нашу функцию update():
update(time, delta) {
// Остальной код функции
this.obsticles.getChildren().forEach(obsticle => {
// Если препятствие вышло за границы
if (obsticle.getBounds().right < 0) {
// Метод для вызова деструктора
obsticle.destroy();
}
});
}Добавим перезапуск игры
После того как произошла коллизия нам бы как-то игру перезапустить, для этого давайте в конструкторе создадим еще несколько объектов:
create() {
// Остальной код функции
this.gameOverScreen = this.add.container(width / 2, height / 2 - 50);
this.gameOverText = this.add.image(0, 0, 'game-over');
this.restart = this.add.image(0, 80, 'restart').setInteractive();
this.gameOverScreen.add([
this.gameOverText, this.restart
]);
}Метод setInteractive() - дает нам возможность потом взаимодействовать с объектом, а в нашем случае - обрабатывать нажатия.
Если открыть браузер, то мы сразу увидем наш экран для конца игры:
Это не совсем то что мы хотим, поэтому давайте на момент начала игры спрячем этот экран, установив ему .setAlpha(0):
create() {
// Остальной код функции
this.gameOverScreen = this.add.container(width / 2, height / 2 - 50).setAlpha(0);
this.gameOverText = this.add.image(0, 0, 'game-over');
this.restart = this.add.image(0, 80, 'restart').setInteractive();
this.gameOverScreen.add([
this.gameOverText, this.restart
]);
}А вот когда игра заканчивается - в функции обработки коллизии, нам нужно наоборот показать этот экран:
initColliders() {
this.physics.add.collider(this.dino, this.obsticles, () => {
this.physics.pause();
this.isGameRunning = false;
this.anims.pauseAll();
this.dino.setTexture('dino-hurt');
this.respawnTime = 0;
this.gameSpeed = 20;
// Показываем экран
this.gameOverScreen.setAlpha(1);
}, null, this);
}Сейчас у нас выходит следующее:
Обрабатываем нажатие на кнопку
Ну что же, для полноценного рестарта не хватает только перезапуска по кнопке, поэтому давайте добавим этот обработчик в функции createControll():
createControll() {
// Остальной код функции
this.restart.on('pointerdown', () => { // 1
this.dino.setVelocityY(0); // 2
this.dino.body.height = 92; // 3
this.dino.body.offset.y = 0; // 4
this.physics.resume(); // 5
this.obsticles.clear(true, true); // 6
this.isGameRunning = true; // 7
this.gameOverScreen.setAlpha(0); // 8
this.anims.resumeAll(); // 9
});
}- Функция обработчик нажатия на кнопку
- Если наш Дино прыгал - вернем его на землю
- Если он пригибался - вернем исходную высоту
- Так же нужно просто откатить к состоянию, которое у нас было на начало игры
- Возобновим всю физику в игре
- Уберем всех врагов со сцены
- Запустим игру
- Спрячем экран конца игры
- Возобновим анимацию
На этом я закончу четвертую часть из цикла статей по созданию игры с Дино, надеюсь вам было интересно и вы попробовали сами с нуля создать свою игру!
Вы можете найти код для этого урока тут