283 lines
7.4 KiB
TypeScript
283 lines
7.4 KiB
TypeScript
import { Socket } from "socket.io";
|
||
import { Player } from "./Player";
|
||
import { Json } from "sequelize/types/utils";
|
||
import { Matchmaker, createMatchmaker, PairingResult } from "./MatchMaker";
|
||
import { ALL_PLAYER_NUM } from "./GameDefine";
|
||
import { GameManager } from "./GameManager";
|
||
import { getLocalTime } from "./GetLocalTime";
|
||
|
||
|
||
type RoomPlayerInfo = {
|
||
playerName: string;
|
||
playerPrepared: boolean;
|
||
};
|
||
|
||
interface GameInfo {
|
||
playerId: string;
|
||
opponentId: string;
|
||
socketID: string;
|
||
rank: number;
|
||
character: string;
|
||
hp: number;
|
||
};
|
||
|
||
class Room
|
||
{
|
||
mPlayers:Map<string, Player> = new Map<string, Player>
|
||
mStatus:number = 0;//0:房间开启;1:所有人准备,进入fight;2:fight结束
|
||
mMatchMaker:Matchmaker = createMatchmaker(this.mPlayers);
|
||
mGameManager:GameManager = new GameManager();
|
||
mCreatedTime:Date = getLocalTime();
|
||
|
||
isRoomPrepared():boolean
|
||
{
|
||
if(this.mPlayers.size != ALL_PLAYER_NUM)
|
||
{
|
||
return false;
|
||
}
|
||
|
||
for(const value of this.mPlayers.values())
|
||
{
|
||
if(value.mPrepared == false)
|
||
{
|
||
return false;
|
||
}
|
||
}
|
||
return true;
|
||
}
|
||
|
||
setRoomPrepared()
|
||
{
|
||
this.generatePairings();
|
||
this.mStatus = 1;
|
||
}
|
||
|
||
generatePairings():PairingResult[]
|
||
{
|
||
let tempPlayers:Map<string, Player> = new Map<string, Player>;
|
||
for(const key of this.mPlayers.keys())
|
||
{
|
||
const player = this.mPlayers.get(key);
|
||
if(player && player.mHp > 0)
|
||
{
|
||
tempPlayers.set(key, player);
|
||
}
|
||
}
|
||
this.mMatchMaker.updatePlayers(tempPlayers);
|
||
let result = this.mMatchMaker.generatePairings();
|
||
for(let i=0; i<result.length; ++i)
|
||
{
|
||
let player = this.mPlayers.get(result[i].playerId);
|
||
if(player)
|
||
{
|
||
player.mCurrentEnemy = result[i].opponentId;
|
||
player.mIsResting = result[i].isResting;
|
||
}
|
||
}
|
||
return result;
|
||
}
|
||
|
||
getGameInfos():GameInfo[]
|
||
{
|
||
let gameInfo: GameInfo[] = [];
|
||
for(const player of this.mPlayers.values())
|
||
{
|
||
gameInfo.push({playerId:player.mPlayerName,
|
||
opponentId:player.mCurrentEnemy,
|
||
socketID: player.mSocketId,
|
||
rank: player.mRank,
|
||
character: player.mCharacterName,
|
||
hp: player.mHp});
|
||
}
|
||
return gameInfo;
|
||
}
|
||
|
||
getGameRoundInfos():GameInfo[]
|
||
{
|
||
let gameInfo: GameInfo[] = [];
|
||
for(const player of this.mGameManager.mGameFightPlayer.values())
|
||
{
|
||
gameInfo.push({playerId:player.mPlayerName,
|
||
opponentId:player.mCurrentEnemy,
|
||
socketID: player.mSocketId,
|
||
rank: player.mRank,
|
||
character: player.mCharacterName,
|
||
hp: player.mHp});
|
||
}
|
||
return gameInfo;
|
||
}
|
||
|
||
getGameInfo(aPlayerID:string):GameInfo|null
|
||
{
|
||
let player = this.mPlayers.get(aPlayerID);
|
||
if(player)
|
||
{
|
||
return {playerId:player.mPlayerName,opponentId:player.mCurrentEnemy,socketID:player.mSocketId,rank:player.mRank,character: player.mCharacterName, hp:player.mHp}
|
||
}
|
||
return null;
|
||
}
|
||
|
||
setGameFight(aPlayerID:string, aAttack:number, aDefender:number):boolean
|
||
{
|
||
let player = this.mPlayers.get(aPlayerID);
|
||
if(!player)
|
||
{
|
||
return false;
|
||
}
|
||
player.mAttack = aAttack;
|
||
player.mDefener = aDefender;
|
||
return this.mGameManager.setGameRoundInfo(aPlayerID, player);
|
||
}
|
||
}
|
||
|
||
export class RoomManager
|
||
{
|
||
static mInstance : RoomManager;
|
||
static getInstance(): RoomManager
|
||
{
|
||
if(this.mInstance == null)
|
||
{
|
||
this.mInstance = new RoomManager();
|
||
}
|
||
return this.mInstance;
|
||
}
|
||
|
||
mRooms = new Map<string, Room>;
|
||
|
||
join(aRoomID:string, aName:string, aSocket:Socket):[boolean, string, number | null, Player | null]
|
||
{
|
||
const room = this.mRooms.get(aRoomID);
|
||
if (!room)
|
||
{
|
||
return [false, "No room Id", null, null];
|
||
}
|
||
if(room.mPlayers.has(aName))
|
||
{
|
||
let player = room.mPlayers.get(aName);
|
||
if(player)
|
||
{
|
||
player.setPlayerSocketId(aSocket.id);
|
||
aSocket.join(aRoomID);
|
||
return [true, "", room.mStatus, player];
|
||
}
|
||
else
|
||
{
|
||
return [false, "unKnow error", null, null];
|
||
}
|
||
}
|
||
|
||
if(room.mPlayers.size < ALL_PLAYER_NUM)
|
||
{
|
||
let player = new Player(aName, aSocket.id);
|
||
aSocket.join(aRoomID);
|
||
room.mPlayers.set(aName, player);
|
||
return [true,"", 0, null];
|
||
}
|
||
|
||
return [false, "room full", null, null];
|
||
}
|
||
|
||
setPlayerInfo(roomId:string, playerId:string, strength:number, stamina:number, agile:number, cards:number[])
|
||
: boolean //返回值是是否所有玩家都准备完毕
|
||
{
|
||
let room = this.mRooms.get(roomId);
|
||
if(!room)
|
||
{
|
||
return false;
|
||
}
|
||
let player = room.mPlayers.get(playerId);
|
||
if(!player)
|
||
{
|
||
return false;
|
||
}
|
||
player.setPlayerInfo(strength, stamina, agile, cards);
|
||
if(room.isRoomPrepared() == true )
|
||
{
|
||
room.setRoomPrepared();
|
||
return true;
|
||
}
|
||
return false;
|
||
}
|
||
|
||
createRoom(aRoomID:string)
|
||
{
|
||
this.mRooms.set(aRoomID, new Room());
|
||
}
|
||
|
||
getPlayersByRoomID(aRoomID:string):RoomPlayerInfo[]
|
||
{
|
||
let room = this.mRooms.get(aRoomID);
|
||
let result:RoomPlayerInfo[] = [];
|
||
if(room?.mPlayers)
|
||
{
|
||
for(const value of room.mPlayers.values())
|
||
{
|
||
result.push({playerName:value.mPlayerName,playerPrepared:value.mPrepared});
|
||
}
|
||
}
|
||
return result;
|
||
}
|
||
|
||
getGameInfos(aRoomID:string):GameInfo[]
|
||
{
|
||
let room = this.mRooms.get(aRoomID);
|
||
if(room)
|
||
{
|
||
return room.getGameInfos();
|
||
}
|
||
return [];
|
||
}
|
||
|
||
getGameInfo(aRoomID:string, aPlayerID:string):GameInfo|null
|
||
{
|
||
let room = this.mRooms.get(aRoomID);
|
||
if(room)
|
||
{
|
||
return room.getGameInfo(aPlayerID);
|
||
}
|
||
return null;
|
||
}
|
||
|
||
getGameRoundInfos(aRoomID:string, aPlayerID:string):GameInfo[]
|
||
{
|
||
let room = this.mRooms.get(aRoomID);
|
||
if(room)
|
||
{
|
||
return room.getGameRoundInfos();
|
||
}
|
||
return [];
|
||
}
|
||
|
||
//返回值是否所有人都准备完毕
|
||
setGameFight(aRoomID:string, aPlayerID:string, aAttack:number, aDefender:number):boolean
|
||
{
|
||
let room = this.mRooms.get(aRoomID);
|
||
if(!room)
|
||
{
|
||
return false;
|
||
}
|
||
|
||
let result = room.setGameFight(aPlayerID, aAttack, aDefender);
|
||
if(result)
|
||
{
|
||
room.generatePairings();
|
||
}
|
||
|
||
return result;
|
||
}
|
||
|
||
clearGameRoundPlayer(aRoomID:string)
|
||
{
|
||
let room = this.mRooms.get(aRoomID);
|
||
if(!room)
|
||
{
|
||
return;
|
||
}
|
||
room.mGameManager.clearGameRoundPlayer();
|
||
}
|
||
|
||
isRoomExist(aRoomID:string):boolean
|
||
{
|
||
return this.mRooms.has(aRoomID);
|
||
}
|
||
} |