2022-12-04 22:10:30 +08:00
|
|
|
import { ApiMsgEnum, EntityTypeEnum, IClientInput, InputTypeEnum, IState, toFixed } from '../Common'
|
2022-12-01 22:26:41 +08:00
|
|
|
import type Player from './Player'
|
|
|
|
import PlayerManager from './PlayerManager'
|
|
|
|
import RoomManager from './RoomManager'
|
|
|
|
|
|
|
|
export default class Room {
|
|
|
|
id: number
|
|
|
|
players: Set<Player> = new Set()
|
2022-12-04 22:10:30 +08:00
|
|
|
lastSyncTime?: number
|
2022-12-06 23:10:03 +08:00
|
|
|
timers: NodeJS.Timer[] = []
|
2022-12-04 22:10:30 +08:00
|
|
|
|
|
|
|
private inputs: Array<IClientInput> = []
|
2022-12-01 22:26:41 +08:00
|
|
|
|
|
|
|
constructor(rid: number) {
|
|
|
|
this.id = rid
|
|
|
|
}
|
|
|
|
|
2022-12-03 20:06:57 +08:00
|
|
|
|
2022-12-01 22:26:41 +08:00
|
|
|
join(uid: number) {
|
|
|
|
const player = PlayerManager.Instance.getPlayerById(uid)
|
|
|
|
if (player) {
|
|
|
|
player.rid = this.id
|
|
|
|
this.players.add(player)
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
leave(uid: number) {
|
|
|
|
const player = PlayerManager.Instance.getPlayerById(uid)
|
|
|
|
if (player) {
|
|
|
|
player.rid = -1
|
|
|
|
this.players.delete(player)
|
|
|
|
if (!this.players.size) {
|
2022-12-06 23:10:03 +08:00
|
|
|
this.timers.forEach(t => clearInterval(t))
|
2022-12-01 22:26:41 +08:00
|
|
|
RoomManager.Instance.closeRoom(this.id)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
sync() {
|
|
|
|
for (const player of this.players) {
|
2022-12-03 20:06:57 +08:00
|
|
|
player.connection.sendMsg(ApiMsgEnum.MsgRoom, {
|
|
|
|
room: RoomManager.Instance.getRoomView(this)
|
|
|
|
})
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
start() {
|
|
|
|
const state: IState = {
|
|
|
|
players: [...this.players].map((player, index) => ({
|
|
|
|
id: player.id,
|
|
|
|
nickname: player.nickname,
|
|
|
|
position: {
|
|
|
|
x: -150 + index * 300,
|
|
|
|
y: -150 + index * 300,
|
|
|
|
},
|
|
|
|
direction: {
|
|
|
|
x: 1,
|
|
|
|
y: 0
|
|
|
|
},
|
|
|
|
hp: 100,
|
2022-12-06 23:10:03 +08:00
|
|
|
type: EntityTypeEnum.Actor2,
|
|
|
|
weaponType: EntityTypeEnum.Weapon2,
|
|
|
|
bulletType: EntityTypeEnum.Bullet2,
|
2022-12-03 20:06:57 +08:00
|
|
|
})),
|
|
|
|
bullets: [],
|
|
|
|
nextBulletId: 1
|
|
|
|
}
|
|
|
|
|
|
|
|
for (const player of this.players) {
|
|
|
|
player.connection.sendMsg(ApiMsgEnum.MsgGameStart, {
|
|
|
|
state
|
|
|
|
})
|
|
|
|
}
|
|
|
|
this.listenPlayer()
|
2022-12-06 23:10:03 +08:00
|
|
|
let t1 = setInterval(() => {
|
2022-12-03 21:28:38 +08:00
|
|
|
this.syncInput()
|
2022-12-04 22:10:30 +08:00
|
|
|
}, 100)
|
2022-12-06 23:10:03 +08:00
|
|
|
let t2 = setInterval(() => {
|
2022-12-04 22:10:30 +08:00
|
|
|
this.timePast()
|
|
|
|
}, 16)
|
2022-12-06 23:10:03 +08:00
|
|
|
this.timers = [t1, t2]
|
2022-12-03 20:06:57 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
listenPlayer() {
|
|
|
|
for (const player of this.players) {
|
2022-12-04 22:10:30 +08:00
|
|
|
player.connection.listenMsg(ApiMsgEnum.MsgClientSync, (input) => {
|
2022-12-03 21:28:38 +08:00
|
|
|
this.inputs.push(input)
|
|
|
|
})
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
syncInput() {
|
|
|
|
const inputs = this.inputs
|
|
|
|
this.inputs = []
|
2022-12-04 22:10:30 +08:00
|
|
|
|
|
|
|
|
2022-12-03 21:28:38 +08:00
|
|
|
for (const player of this.players) {
|
2022-12-04 22:10:30 +08:00
|
|
|
player.connection.sendMsg(ApiMsgEnum.MsgServerSync, inputs)
|
2022-12-01 22:26:41 +08:00
|
|
|
}
|
|
|
|
}
|
2022-12-04 22:10:30 +08:00
|
|
|
|
|
|
|
timePast() {
|
|
|
|
let now = process.uptime();
|
|
|
|
const dt = now - (this.lastSyncTime ?? now)
|
|
|
|
this.inputs.push({
|
|
|
|
type: InputTypeEnum.TimePast,
|
|
|
|
dt: toFixed(dt)
|
|
|
|
})
|
|
|
|
this.lastSyncTime = now;
|
|
|
|
}
|
2022-12-01 22:26:41 +08:00
|
|
|
}
|