用Swoole來寫個聯機對戰遊戲呀!(二)單機遊戲架構

寫程式的趙童鞋發表於2019-04-23

遊戲邏輯開發進度:□□□□□□□□□□□□

本章結束開發進度:■■■■□□□□□□□□

開發環境

教程需要PHP-7.x版本支援,由於不是面向基礎小白,PHP環境需要童鞋們自行安裝配置,以下是一些有可能有幫助的資料:

引入Composer

在合適的位置新建一個資料夾HideAndSeek作為我們的專案根目錄。

為了後續開發的方便,我們需要為我們的專案引入composer的自動載入機制,並在專案根目錄執行以下命令:

composer init
複製程式碼
  • 小提示:沒有安裝composer的童鞋需要自行安裝喔:pkg.phpcomposer.com/#how-to-ins…
  • 啟用國內映象地址,下載速度更快。
  • 國內映象一:composer config -g repo.packagist composer https://packagist.phpcomposer.com
  • 國內映象二:composer config -g repo.packagist composer https://packagist.laravel-china.org

經過幾次回車之後,composer就會為我們生成一個composer.json檔案,需要在這個檔案中增加以下程式碼:

"autoload": {
    "psr-4": {
        "App\\": "app"
    }
},
複製程式碼

再執行一次composer命令:

composer install
複製程式碼

composer就會為我們建立vendor資料夾,裡面會有一個autoload.php檔案,這個檔案就是用來實現類自動載入機制。

建立專案結構

下一步就是編寫遊戲的邏輯,實現一個單機版的捉迷藏。

在上面建立的資料夾HideAndSeek中新建一個test.php檔案

HideAndSeek
└─test.php
複製程式碼

為什麼要新建這個test.php呢?因為我們現在對整個專案的架構毫無頭緒,所以需要將這個遊戲邏輯拆分成幾個步驟,並且將邏輯預先寫在test.php檔案中。

趙童鞋設想的遊戲邏輯是這樣的:

  1. 每個玩家要有一個ID,用來區別玩家。
  2. 要有一個遊戲控制器,用來建立玩家、執行移動邏輯、判斷遊戲是否結束。
  3. 使用遊戲控制器建立玩家,遊戲開始。
  4. 使用遊戲控制器控制某個玩家進行移動。

test.php檔案:

$redId = "red_player";
$blueId = "blue_player";
//建立遊戲控制器
$game = new Game();
//新增玩家
$game->createPlayer($redId, 6, 1);
//新增玩家
$game->createPlayer($blueId, 6, 10);
//移動座標
$game->playerMove($redId, 'up');
複製程式碼

現在就很明顯了,我們首要任務就是先實現這樣一個遊戲控制器。

HideAndSeek資料夾中建立app資料夾,app資料夾用來存放我們專案的各種類檔案。並在app資料夾中建立Manager資料夾用來存放所有管理者類的類檔案,在Manager資料夾中建立Game遊戲控制器類。

為了composer能夠自動載入類檔案,需要在Game類編寫名稱空間程式碼:namespace App\Manager,細心的童鞋已經發現了,我們上面在composer.json檔案中新增程式碼時,就有提到App這個詞,不瞭解自動載入機制的童鞋可以自行搜尋一下composer psr-4

<?php
namespace App\Manager;
class Game
{
}
複製程式碼

我們現在要思考一下游戲還需要哪些實體類,我們捉迷藏遊戲有玩家,有地圖,所以遊戲還需要兩個實體類:一個是玩家類,另一個是地圖類,沒錯,這就是物件導向程式設計,而不是面向運氣程式設計。

app資料夾下新建Model資料夾,用來存放各種遊戲實體類,並在其中新建Player類和Map類:

<?php
namespace App\Model;
class Player
{
}
複製程式碼
<?php
namespace App\Model;
class Map
{
}
複製程式碼

完善各類程式碼

現在我們需要思考一下,這三個類各自的屬性和方法需要有哪些。

Map類

我們先從最簡單的Map類開始:

  1. Map物件應該在建立的時候可以指定長和寬,並生成一個地圖。
  2. Map物件中應該有一個陣列,用來儲存完整的地圖資料,我們假設這個陣列中,0是牆,1是路。
  3. Map類中需要有一個方法來獲取地圖資料。

由於生成一個地圖的演算法有點複雜,我們現在的重點只在於編寫遊戲邏輯,所以地圖資料可以先寫死。

<?php
namespace App\Model;
class Map
{
    private $width;
    private $height;

    private $map = [
        [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
        [0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0],
        [0, 1, 0, 1, 1, 1, 1, 1, 1, 1, 0, 0],
        [0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 0, 0],
        [0, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 0],
        [0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0],
        [0, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0],
        [0, 1, 1, 0, 0, 1, 0, 1, 1, 1, 1, 0],
        [0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0],
        [0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 1, 0],
        [0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0],
        [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
    ];

    public function __construct($width, $height)
    {
        $this->width = $width;
        $this->height = $height;
    }
    
    public function getMapData()
    {
        return $this->map;
    }
}
複製程式碼

Player類

第二個輪到我們的Player類:

  1. Player物件應該有一個自己的唯一ID。
  2. Player物件需要有自己的座標,用來標識他在地圖的位置。
  3. Player物件需要有自己的型別,分為尋找者躲藏者
  4. Player類中需要有四個方向常量用來控制當前座標,分別是 右。
<?php
namespace App\Model;
class Player
{
    const UP = 'up';
    const DOWN = 'down';
    const LEFT = 'left';
    const RIGHT = 'right';

    const PLAYER_TYPE_SEEK = 1;
    const PLAYER_TYPE_HIDE = 2;

    private $id;
    private $type = self::PLAYER_TYPE_SEEK;
    private $x;
    private $y;

    public function __construct($id, $x, $y)
    {
        $this->id = $id;
        $this->x = $x;
        $this->y = $y;
    }

    public function setType($type)
    {
        $this->type = $type;
    }

    public function getId()
    {
        return $this->id;
    }
}
複製程式碼

Game類

最後輪到我們的遊戲控制器Game類啦~

  1. 新建一個Game物件時需要生成一個地圖並且儲存地圖資料。
  2. Game中需要一個陣列儲存兩個玩家資料。
  3. Game中需要實現createPlayer()方法用來新增玩家。
  4. Game中需要實現playerMove()方法操作玩家移動。
<?php
namespace App\Manager;

use App\Model\Map;

class Game
{
    private $gameMap = [];
    private $players = [];

    public function __construct()
    {
        $this->gameMap = new Map(12, 12);
    }

    public function createPlayer($playerId, $x, $y)
    {
    }

    public function playerMove($playerId, $direction)
    {
    }
}
複製程式碼

童鞋們先嚐試實現一下createPlayer方法和playerMove方法應該怎麼實現,我們下一章再來揭祕。

當前目錄結構:

HideAndSeek
├── app
│   ├── Manager
│   │   └── Game.php
│   └── Model
│       ├── Map.php
│       └── Player.php
├── composer.json
├── test.php
└── vendor
    ├── autoload.php
    └── composer
複製程式碼

用Swoole來寫個聯機對戰遊戲呀!(二)單機遊戲架構

相關文章