游戏结束判断

游戏逻辑开发进度:■■■■■■■■□□□□

本章结束开发进度:■■■■■■■■■■■■

上一章的答案

在我们的$mapData数组中,0就是墙,1就是路,canMoveToDirection()方法主要就是获取方向,计算得出目标坐标,检测一下目标坐标能不能走,所以当数组中是0的时候就返回false,否则返回true

Game类:

  1. <?php
  2. ...
  3. class Game
  4. {
  5. ...
  6. private function canMoveToDirection($player, $direction)
  7. {
  8. $x = $player->getX();
  9. $y = $player->getY();
  10. $moveCoor = $this->getMoveCoor($x, $y, $direction);
  11. $mapData = $this->gameMap->getMapData();
  12. if (!$mapData[$moveCoor[0]][$moveCoor[1]]) {
  13. return false;
  14. }
  15. return true;
  16. }
  17. private function getMoveCoor($x, $y, $direction)
  18. {
  19. switch ($direction) {
  20. case Player::UP:
  21. return [--$x, $y];
  22. case Player::DOWN:
  23. return [++$x, $y];
  24. case Player::LEFT:
  25. return [$x, --$y];
  26. case Player::RIGHT:
  27. return [$x, ++$y];
  28. }
  29. return [$x, $y];
  30. }
  31. }

增加canMoveToDirection()方法后再次运行test.php文件输出地图数据:

4 游戏结束判断 - 图1

可以看到,即使经过了三次的up操作,寻找者都没有再跑到墙上面去。

游戏结束判断

我们的游戏逻辑开发已经接近尾声了,目前剩下的就是游戏结束时的判断,我们需要在Game类中增加isGameOver()方法,用来判断游戏是否结束。

做题时间

  1. Game类中的$players数组保存了玩家的数据。
  2. 两个玩家坐标叠一块就结束啦~

Game类:

  1. <?php
  2. ...
  3. class Game
  4. {
  5. ...
  6. public function isGameOver()
  7. {
  8. $result = false;
  9. $x = -1;
  10. $y = -1;
  11. $players = array_values($this->players);
  12. /* @var Player $player */
  13. foreach ($players as $key => $player) {
  14. if ($key == 0) {
  15. $x = $player->getX();
  16. $y = $player->getY();
  17. } elseif ($x == $player->getX() && $y == $player->getY()) {
  18. $result = true;
  19. }
  20. }
  21. return $result;
  22. }
  23. }

到这里为止,我们的游戏主体逻辑已经开发完毕了,但不能我说开发完就开发完的嘛,我们必须要实践一下,测试一下整体逻辑有没有问题。这时候又到test.php文件登场了,请童鞋们在test.php文件中,新增代码逻辑让两个电脑对战一次。

做题时间

  1. 让双方玩家随机行走。
  2. 实时打印游戏地图数据。
  3. 当游戏结束时停止游戏。

提示:每次打印完毕使用`usleep()`方法停止一下,否则运算过快可能看不到游戏过程哦。

Player类:

  1. <?php
  2. ...
  3. class Player
  4. {
  5. ...
  6. const DIRECTION = [self::UP, self::DOWN, self::LEFT, self::RIGHT];
  7. }

为了方便随机选择位置,我们需要在Player类中新增一个常量DIRECTION

test.php

  1. <?php
  2. ...
  3. for ($i = 0; $i <= 300; $i++) {
  4. $direct = mt_rand(0, 3);
  5. $game->playerMove($redId, Player::DIRECTION[$direct]);
  6. if ($game->isGameOver()) {
  7. $game->printGameMap();
  8. echo "game_over" . PHP_EOL;
  9. return;
  10. }
  11. $direct = mt_rand(0, 3);
  12. $game->playerMove($blueId, Player::DIRECTION[$direct]);
  13. if ($game->isGameOver()) {
  14. $game->printGameMap();
  15. echo "game_over" . PHP_EOL;
  16. return;
  17. }
  18. //打印移动后战局
  19. echo PHP_EOL . PHP_EOL . PHP_EOL . PHP_EOL . PHP_EOL . PHP_EOL . PHP_EOL . PHP_EOL . PHP_EOL . PHP_EOL;
  20. $game->printGameMap();
  21. usleep(200000);
  22. }

运行test.php文件就会出现以下输出啦:

4 游戏结束判断 - 图2

游戏效果看上去挺不错的吧?

我们的游戏逻辑开发就到这里了,后面的章节将会简单介绍SwooleVueWebSocket。然后就开始接入SwooleVue,开始编写网络对战部分。

本章对应Github Commit第四章结束

当前目录结构:

  1. HideAndSeek
  2. ├── app
  3. ├── Manager
  4. └── Game.php
  5. └── Model
  6. ├── Map.php
  7. └── Player.php
  8. ├── composer.json
  9. ├── test.php
  10. └── vendor
  11. ├── autoload.php
  12. └── composer