GameApi.canPlaceBuilding(playerName, buildingName, tile)

| Chrono Divide | 9 Reads

以下是 GameApi 類別對外介面中與建築放置相關的部分,可在套件 @chronodivide/game-api 的型別宣告檔看到:

320      #private;
321      mapApi: MapApi;
322      rulesApi: RulesApi;
323      isPlayerDefeated(playerName: string): boolean;
324      areAlliedPlayers(p1Name: string, p2Name: string): boolean;
325      canPlaceBuilding(playerName: string, buildingName: string, tile: Tile): boolean;
326      getBuildingPlacementData(objName: string): BuildingPlacementData;
327      getPlayers(): string[];

canPlaceBuilding 的核心實作藏在打包後的 index.js。雖然檔案被壓縮成單行,但從截取的片段可以看出邏輯:

alliances.areAllied(i,e)}canPlaceBuilding(e,t,i){var s=Mp(this,Lp,"f").getPlayerByName(e);
if(!s)throw new Error(`Player "${e}" doesn't exist`);
return Mp(this,Lp,"f").getConstructionWorker(s).canPlaceAt(t,i,{normalizedTile:!0})}

流程大致如下:

  1. 依名稱取得玩家物件,若找不到則丟出錯誤。

  2. 透過該玩家的 ConstructionWorker 判斷指定建築物能否放置在給定的格子。

  3. canPlaceAt 會考量地形、相鄰建築等條件,並以 { normalizedTile: true } 方式處理座標。

專案裡在計算建築位置時就使用了此方法,僅在找到可放置的格子時才回傳:

for (let tileDistance of tileDistances) {
    if (tileDistance.tile &&
        game.canPlaceBuilding(playerData.name, technoRules.name, tileDistance.tile)) {
        return tileDistance.tile;
    }
}

簡易範例

以下 TypeScript 範例展示如何在自訂 Bot 中利用 canPlaceBuilding 判斷建築位置:

import { cdapi, Bot, GameApi, Tile } from "@chronodivide/game-api";

class BuilderBot extends Bot {
    onGameStart(game: GameApi) {
        const playerName = this.name;          // 取得自己的名稱
        const building = "GAPOWR";             // 例如 Allied Power Plant
        const target: Tile = { rx: 64, ry: 60 }; // 要嘗試放置的地塊

        const ok = game.canPlaceBuilding(playerName, building, target);
        console.log(`Can place ${building} at (${target.rx},${target.ry}) : ${ok}`);
    }
}

async function main() {
    await cdapi.init(process.env.MIX_DIR!);
    await cdapi.createGame({
        agents: [new BuilderBot("BotA", "Americans")],
        mapName: "mp03t4.map",
        shortGame: true,
        online: false,
    });
}

main().catch(console.error);

onGameStart 裡呼叫 canPlaceBuilding 後,若回傳 true,即可進一步下指令建造;若為 false,應換其他格子或重新計算位置。

透過 canPlaceBuilding,Bot 得以在建築前快速驗證地形限制,避免無效的建築指令。以上就是此方法的主要運作方式與使用範例。

 

→返回《@chronodivide/game-api 使用教學與完整 API 對照表》

This article was last edited at