This commit is contained in:
k8w 2021-12-28 15:23:18 +08:00
parent 0f89b080cd
commit 52618125e1
4 changed files with 81 additions and 16 deletions

View File

@ -12,6 +12,7 @@
"devDependencies": { "devDependencies": {
"@types/mocha": "^8.2.3", "@types/mocha": "^8.2.3",
"@types/node": "^15.14.9", "@types/node": "^15.14.9",
"@types/seedrandom": "^3.0.1",
"mocha": "^9.1.3", "mocha": "^9.1.3",
"onchange": "^7.1.0", "onchange": "^7.1.0",
"ts-node": "^10.4.0", "ts-node": "^10.4.0",
@ -19,6 +20,7 @@
"typescript": "^4.5.4" "typescript": "^4.5.4"
}, },
"dependencies": { "dependencies": {
"seedrandom": "^3.0.5",
"tsrpc": "^3.1.4" "tsrpc": "^3.1.4"
} }
} }

View File

@ -1,7 +1,8 @@
import seedrandom from "seedrandom";
import { gameConfig } from "./gameConfig"; import { gameConfig } from "./gameConfig";
import { GameSystemEvent } from "./GameSystemEvent"; import { GameSystemEvent } from "./GameSystemEvent";
import { GameSystemInput } from "./GameSystemInput"; import { GameSystemInput } from "./GameSystemInput";
import { GameSystemState } from "./GameSystemState"; import { EnemyState, EnemyType, GameSystemState } from "./GameSystemState";
/** /**
* *
@ -9,7 +10,17 @@ import { GameSystemState } from "./GameSystemState";
export class GameSystem { export class GameSystem {
// 当前状态 // 当前状态
state: GameSystemState; private _state!: GameSystemState;
get state(): Readonly<GameSystemState> {
return this._state;
}
set state(state: GameSystemState) {
this._state = state;
this._seedRandom = seedrandom(state.random.seed, state.random.state);
}
// 伪随机数发生器
private _seedRandom!: ReturnType<seedrandom>;
constructor(state: GameSystemState) { constructor(state: GameSystemState) {
this.state = state; this.state = state;
@ -89,7 +100,7 @@ export class GameSystem {
this.state.enemies.forEach(enemy => { this.state.enemies.forEach(enemy => {
// 更新敌机位置 // 更新敌机位置
const enemyTime = this.state.now - enemy.init.time; const enemyTime = this.state.now - enemy.init.time;
enemy.pos.y = enemy.init.pos.y - gameConfig.enemy.speed * enemyTime; enemy.pos.y = enemy.init.pos.y - gameConfig.enemy.speed[enemy.type] * enemyTime;
// 更新敌机子弹位置 // 更新敌机子弹位置
enemy.bullets.forEach(bullet => { enemy.bullets.forEach(bullet => {
@ -119,14 +130,36 @@ export class GameSystem {
} }
private _createEnemies() { private _createEnemies() {
// 前 10 秒 if (this.state.now < this.state.lastCreateEnemyTime + gameConfig.enemy.bornY) {
// 每 1 秒创建一个敌机 return;
}
// 10~20秒 let time = this.state.now - (this.state.now % gameConfig.enemy.bornGapTime);
// 每3秒一个组合然后每秒一个敌机 let pos = { x: this._random() * 750 - 375, y: gameConfig.enemy.bornY };
let enemy: EnemyState = {
id: this.state.nextId.enemy++,
// 敌机类型
type: this._random() > 0.5 ? EnemyType.E1 : EnemyType.E2,
pos: { ...pos },
init: {
time: time,
pos: { ...pos },
},
bullets: [],
// 初次创建敌机,按 bulletDelayTime 倒推 lastBulletTime
lastBulletTime: time + gameConfig.enemy.bulletDelayTime - gameConfig.enemy.bulletGapTime,
nextId: {
bullet: 0
}
}
// 20秒以后 this.state.enemies.push(enemy);
// 每 2 秒一个组合(组合1 / 组合2 / xxx) }
private _random(): number {
let rand = this._seedRandom();
this.state.random.state = this._seedRandom.state();
return rand;
} }
// 简易的事件侦听器 // 简易的事件侦听器

View File

@ -1,11 +1,19 @@
import { uint } from "tsrpc"; import { uint } from "tsrpc";
// 坐标系X-Y 原点在左下角 // 坐标系X-Y 原点在中间下方
/*
[ ] [ ] [ ]
[ ] [ ] [ ]
y
[ ] [x] [ ] x
*/
export interface GameSystemState { export interface GameSystemState {
// 游戏时间 // 游戏时间
now: number, now: number,
// 场景状态
players: PlayerState[], players: PlayerState[],
enemies: EnemyState[], enemies: EnemyState[],
fightIcons: FightIconState[], fightIcons: FightIconState[],
@ -15,11 +23,18 @@ export interface GameSystemState {
enemy: uint, enemy: uint,
fightIcon: uint fightIcon: uint
}, },
// 上次创建敌机的时间 // 上次创建敌机的时间
lastCreateEnemyTime: number, lastCreateEnemyTime: number,
randomSeed: number,
// 伪随机数发生器状态
random: {
seed: string,
state: object
}
} }
// 玩家 // 玩家
export interface PlayerState { export interface PlayerState {
id: uint, id: uint,
@ -52,12 +67,12 @@ export type PlayerBulletType = 'M' | 'H' | 'S';
// 敌机 // 敌机
export interface EnemyState { export interface EnemyState {
id: uint, id: uint,
type: uint, // 敌机类型
type: EnemyType,
pos: { x: number, y: number }, pos: { x: number, y: number },
init: { init: {
time: number, time: number,
pos: { x: number, y: number }, pos: { x: number, y: number },
speed: { y: number }
} }
bullets: { bullets: {
id: uint, id: uint,
@ -76,6 +91,11 @@ export interface EnemyState {
} }
} }
export enum EnemyType {
E1,
E2
};
// 子弹图标 // 子弹图标
export interface FightIconState { export interface FightIconState {
id: uint, id: uint,

View File

@ -1,13 +1,23 @@
import { EnemyType } from "./GameSystemState";
export const gameConfig = { export const gameConfig = {
syncRate: 10, syncRate: 10,
enemy: { enemy: {
speed: 10,
bulletSpeed: 20, bulletSpeed: 20,
// 第一次发射子弹的延迟时间 // 第一次发射子弹的延迟时间
bulletDelayTime: 1500, bulletDelayTime: 1500,
// 每次发射子弹的间隔 // 每次发射子弹的间隔
bulletGapTime: 500 bulletGapTime: 500,
// 出现位置Y轴
bornY: 1800,
// 敌机出现时间间隔(毫秒)
bornGapTime: 1000,
// 敌机速度
speed: {
[EnemyType.E1]: 10,
[EnemyType.E2]: 20,
}
}, },
player: { player: {