feat(game): 创建游戏核心框架(常量、配置、状态管理、地图渲染、主场景)
This commit is contained in:
96
game/GameManager.ts
Normal file
96
game/GameManager.ts
Normal file
@@ -0,0 +1,96 @@
|
||||
import {
|
||||
INITIAL_HC,
|
||||
INITIAL_KPI,
|
||||
} from './constants'
|
||||
|
||||
type GameState = 'idle' | 'playing' | 'paused' | 'victory' | 'defeat'
|
||||
|
||||
/**
|
||||
* 游戏状态管理器(单例)
|
||||
* 负责管理 HC(人才储备)、KPI、波次状态,并通过回调事件通知 Scene
|
||||
*/
|
||||
export class GameManager {
|
||||
private static instance: GameManager
|
||||
|
||||
public hc: number = INITIAL_HC
|
||||
public kpi: number = INITIAL_KPI
|
||||
public currentWave: number = 0
|
||||
public gameState: GameState = 'idle'
|
||||
|
||||
// 事件回调(Scene 通过这些 hook 更新 HUD)
|
||||
public onHCChange: ((hc: number) => void)[] = []
|
||||
public onKPIChange: ((kpi: number) => void)[] = []
|
||||
public onGameOver: (() => void)[] = []
|
||||
public onVictory: (() => void)[] = []
|
||||
|
||||
private constructor() {}
|
||||
|
||||
static getInstance(): GameManager {
|
||||
if (!GameManager.instance) {
|
||||
GameManager.instance = new GameManager()
|
||||
}
|
||||
return GameManager.instance
|
||||
}
|
||||
|
||||
/** 重置游戏状态(新局开始时调用) */
|
||||
reset(): void {
|
||||
this.hc = INITIAL_HC
|
||||
this.kpi = INITIAL_KPI
|
||||
this.currentWave = 0
|
||||
this.gameState = 'idle'
|
||||
this.onHCChange = []
|
||||
this.onKPIChange = []
|
||||
this.onGameOver = []
|
||||
this.onVictory = []
|
||||
}
|
||||
|
||||
/**
|
||||
* 扣除 HC,余额不足时返回 false
|
||||
* @param amount 扣除数量
|
||||
*/
|
||||
spendHC(amount: number): boolean {
|
||||
if (this.hc < amount) return false
|
||||
this.hc -= amount
|
||||
this.onHCChange.forEach(cb => cb(this.hc))
|
||||
return true
|
||||
}
|
||||
|
||||
/**
|
||||
* 增加 HC
|
||||
* @param amount 增加数量
|
||||
*/
|
||||
addHC(amount: number): void {
|
||||
this.hc += amount
|
||||
this.onHCChange.forEach(cb => cb(this.hc))
|
||||
}
|
||||
|
||||
/**
|
||||
* 减少 KPI,归零时触发 GameOver
|
||||
* @param amount 减少数量
|
||||
*/
|
||||
reduceKPI(amount: number): void {
|
||||
this.kpi = Math.max(0, this.kpi - amount)
|
||||
this.onKPIChange.forEach(cb => cb(this.kpi))
|
||||
if (this.kpi <= 0 && this.gameState === 'playing') {
|
||||
this.gameState = 'defeat'
|
||||
this.onGameOver.forEach(cb => cb())
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 增加 KPI(不超过 100)
|
||||
* @param amount 增加数量
|
||||
*/
|
||||
addKPI(amount: number): void {
|
||||
this.kpi = Math.min(100, this.kpi + amount)
|
||||
this.onKPIChange.forEach(cb => cb(this.kpi))
|
||||
}
|
||||
|
||||
/** 触发胜利 */
|
||||
triggerVictory(): void {
|
||||
if (this.gameState === 'playing') {
|
||||
this.gameState = 'victory'
|
||||
this.onVictory.forEach(cb => cb())
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user