mirror of
https://github.com/demostf/demo.js
synced 2026-06-04 00:54:14 +02:00
lint fixes
This commit is contained in:
parent
00ef5499c6
commit
0aad1e874b
78 changed files with 879 additions and 851 deletions
102
package-lock.json
generated
102
package-lock.json
generated
|
|
@ -484,14 +484,6 @@
|
||||||
"requires": {
|
"requires": {
|
||||||
"balanced-match": "1.0.0",
|
"balanced-match": "1.0.0",
|
||||||
"concat-map": "0.0.1"
|
"concat-map": "0.0.1"
|
||||||
},
|
|
||||||
"dependencies": {
|
|
||||||
"concat-map": {
|
|
||||||
"version": "0.0.1",
|
|
||||||
"resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz",
|
|
||||||
"integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=",
|
|
||||||
"dev": true
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"clone": {
|
"clone": {
|
||||||
|
|
@ -520,6 +512,12 @@
|
||||||
"integrity": "sha1-FopHAXVran9RoSzgyXv6KMCE7WM=",
|
"integrity": "sha1-FopHAXVran9RoSzgyXv6KMCE7WM=",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
|
"concat-map": {
|
||||||
|
"version": "0.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz",
|
||||||
|
"integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
"core-util-is": {
|
"core-util-is": {
|
||||||
"version": "1.0.2",
|
"version": "1.0.2",
|
||||||
"resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz",
|
"resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz",
|
||||||
|
|
@ -532,6 +530,12 @@
|
||||||
"integrity": "sha512-MKPHZDMB0o6yHyDryUOScqZibp914ksXwAMYMTHj6KO8UeKsRYNJD3oNCKjTqZon+V488P7N/HzXF8t7ZR95ww==",
|
"integrity": "sha512-MKPHZDMB0o6yHyDryUOScqZibp914ksXwAMYMTHj6KO8UeKsRYNJD3oNCKjTqZon+V488P7N/HzXF8t7ZR95ww==",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
|
"fs.realpath": {
|
||||||
|
"version": "1.0.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz",
|
||||||
|
"integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
"glob": {
|
"glob": {
|
||||||
"version": "7.1.2",
|
"version": "7.1.2",
|
||||||
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
"resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
|
||||||
|
|
@ -544,51 +548,6 @@
|
||||||
"minimatch": "3.0.4",
|
"minimatch": "3.0.4",
|
||||||
"once": "1.4.0",
|
"once": "1.4.0",
|
||||||
"path-is-absolute": "1.0.1"
|
"path-is-absolute": "1.0.1"
|
||||||
},
|
|
||||||
"dependencies": {
|
|
||||||
"fs.realpath": {
|
|
||||||
"version": "1.0.0",
|
|
||||||
"resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz",
|
|
||||||
"integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=",
|
|
||||||
"dev": true
|
|
||||||
},
|
|
||||||
"inflight": {
|
|
||||||
"version": "1.0.6",
|
|
||||||
"resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz",
|
|
||||||
"integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=",
|
|
||||||
"dev": true,
|
|
||||||
"requires": {
|
|
||||||
"once": "1.4.0",
|
|
||||||
"wrappy": "1.0.2"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"inherits": {
|
|
||||||
"version": "2.0.3",
|
|
||||||
"resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz",
|
|
||||||
"integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=",
|
|
||||||
"dev": true
|
|
||||||
},
|
|
||||||
"once": {
|
|
||||||
"version": "1.4.0",
|
|
||||||
"resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz",
|
|
||||||
"integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=",
|
|
||||||
"dev": true,
|
|
||||||
"requires": {
|
|
||||||
"wrappy": "1.0.2"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"path-is-absolute": {
|
|
||||||
"version": "1.0.1",
|
|
||||||
"resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz",
|
|
||||||
"integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=",
|
|
||||||
"dev": true
|
|
||||||
},
|
|
||||||
"wrappy": {
|
|
||||||
"version": "1.0.2",
|
|
||||||
"resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz",
|
|
||||||
"integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=",
|
|
||||||
"dev": true
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"has-flag": {
|
"has-flag": {
|
||||||
|
|
@ -612,6 +571,22 @@
|
||||||
"parse-passwd": "1.0.0"
|
"parse-passwd": "1.0.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"inflight": {
|
||||||
|
"version": "1.0.6",
|
||||||
|
"resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz",
|
||||||
|
"integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=",
|
||||||
|
"dev": true,
|
||||||
|
"requires": {
|
||||||
|
"once": "1.4.0",
|
||||||
|
"wrappy": "1.0.2"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"inherits": {
|
||||||
|
"version": "2.0.3",
|
||||||
|
"resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz",
|
||||||
|
"integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
"isarray": {
|
"isarray": {
|
||||||
"version": "1.0.0",
|
"version": "1.0.0",
|
||||||
"resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz",
|
"resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz",
|
||||||
|
|
@ -929,12 +904,27 @@
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"once": {
|
||||||
|
"version": "1.4.0",
|
||||||
|
"resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz",
|
||||||
|
"integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=",
|
||||||
|
"dev": true,
|
||||||
|
"requires": {
|
||||||
|
"wrappy": "1.0.2"
|
||||||
|
}
|
||||||
|
},
|
||||||
"parse-passwd": {
|
"parse-passwd": {
|
||||||
"version": "1.0.0",
|
"version": "1.0.0",
|
||||||
"resolved": "https://registry.npmjs.org/parse-passwd/-/parse-passwd-1.0.0.tgz",
|
"resolved": "https://registry.npmjs.org/parse-passwd/-/parse-passwd-1.0.0.tgz",
|
||||||
"integrity": "sha1-bVuTSkVpk7I9N/QKOC1vFmao5cY=",
|
"integrity": "sha1-bVuTSkVpk7I9N/QKOC1vFmao5cY=",
|
||||||
"dev": true
|
"dev": true
|
||||||
},
|
},
|
||||||
|
"path-is-absolute": {
|
||||||
|
"version": "1.0.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz",
|
||||||
|
"integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
"path-parse": {
|
"path-parse": {
|
||||||
"version": "1.0.5",
|
"version": "1.0.5",
|
||||||
"resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.5.tgz",
|
"resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.5.tgz",
|
||||||
|
|
@ -1209,6 +1199,12 @@
|
||||||
"homedir-polyfill": "1.0.1"
|
"homedir-polyfill": "1.0.1"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"wrappy": {
|
||||||
|
"version": "1.0.2",
|
||||||
|
"resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz",
|
||||||
|
"integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=",
|
||||||
|
"dev": true
|
||||||
|
},
|
||||||
"yn": {
|
"yn": {
|
||||||
"version": "2.0.0",
|
"version": "2.0.0",
|
||||||
"resolved": "https://registry.npmjs.org/yn/-/yn-2.0.0.tgz",
|
"resolved": "https://registry.npmjs.org/yn/-/yn-2.0.0.tgz",
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,7 @@
|
||||||
import {Parser} from './Parser';
|
|
||||||
import {Match} from './Data/Match';
|
|
||||||
import {EventEmitter} from 'events';
|
import {EventEmitter} from 'events';
|
||||||
import {Header} from './Data/Header';
|
import {Header} from './Data/Header';
|
||||||
|
import {Match} from './Data/Match';
|
||||||
|
import {Parser} from './Parser';
|
||||||
|
|
||||||
export class Analyser extends EventEmitter {
|
export class Analyser extends EventEmitter {
|
||||||
private parser: Parser;
|
private parser: Parser;
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
export interface Chat {
|
export interface Chat {
|
||||||
kind: string,
|
kind: string;
|
||||||
from: string,
|
from: string;
|
||||||
text: string,
|
text: string;
|
||||||
tick: number,
|
tick: number;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -18,7 +18,7 @@ export enum GameEventValueType {
|
||||||
SHORT = 4,
|
SHORT = 4,
|
||||||
BYTE = 5,
|
BYTE = 5,
|
||||||
BOOLEAN = 6,
|
BOOLEAN = 6,
|
||||||
LOCAL = 7,
|
LOCAL = 7
|
||||||
}
|
}
|
||||||
|
|
||||||
export type GameEventValue = string | number | boolean;
|
export type GameEventValue = string | number | boolean;
|
||||||
|
|
|
||||||
|
|
@ -3528,7 +3528,7 @@ export type GameEvent = ServerSpawnEvent |
|
||||||
|
|
||||||
export type GameEventType = GameEvent['name'];
|
export type GameEventType = GameEvent['name'];
|
||||||
|
|
||||||
export type GameEventTypeMap = {
|
export interface GameEventTypeMap {
|
||||||
server_spawn: ServerSpawnEvent;
|
server_spawn: ServerSpawnEvent;
|
||||||
server_changelevel_failed: ServerChangelevelFailedEvent;
|
server_changelevel_failed: ServerChangelevelFailedEvent;
|
||||||
server_shutdown: ServerShutdownEvent;
|
server_shutdown: ServerShutdownEvent;
|
||||||
|
|
@ -3905,7 +3905,7 @@ export type GameEventTypeMap = {
|
||||||
replay_endrecord: ReplayEndRecordEvent;
|
replay_endrecord: ReplayEndRecordEvent;
|
||||||
replay_replaysavailable: ReplayReplaysAvailableEvent;
|
replay_replaysavailable: ReplayReplaysAvailableEvent;
|
||||||
replay_servererror: ReplayServerErrorEvent;
|
replay_servererror: ReplayServerErrorEvent;
|
||||||
};
|
}
|
||||||
|
|
||||||
export type GameEventTypeId = number;
|
export type GameEventTypeId = number;
|
||||||
|
|
||||||
|
|
@ -4285,6 +4285,5 @@ export const GameEventTypeIdMap: Map<GameEventType, GameEventTypeId> = new Map<G
|
||||||
['replay_sessioninfo', 372],
|
['replay_sessioninfo', 372],
|
||||||
['replay_endrecord', 373],
|
['replay_endrecord', 373],
|
||||||
['replay_replaysavailable', 374],
|
['replay_replaysavailable', 374],
|
||||||
['replay_servererror', 375],
|
['replay_servererror', 375]
|
||||||
]);
|
]);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -3,19 +3,19 @@ import {handleGameEvent} from '../PacketHandler/GameEvent';
|
||||||
import {handlePacketEntities} from '../PacketHandler/PacketEntities';
|
import {handlePacketEntities} from '../PacketHandler/PacketEntities';
|
||||||
import {handleSayText2} from '../PacketHandler/SayText2';
|
import {handleSayText2} from '../PacketHandler/SayText2';
|
||||||
import {Building} from './Building';
|
import {Building} from './Building';
|
||||||
|
import {Chat} from './Chat';
|
||||||
import {Death} from './Death';
|
import {Death} from './Death';
|
||||||
|
import {Packet} from './Packet';
|
||||||
import {EntityId, PacketEntity} from './PacketEntity';
|
import {EntityId, PacketEntity} from './PacketEntity';
|
||||||
|
import {ParserState} from './ParserState';
|
||||||
import {Player} from './Player';
|
import {Player} from './Player';
|
||||||
import {PlayerResource} from './PlayerResource';
|
import {PlayerResource} from './PlayerResource';
|
||||||
|
import {Round} from './Round';
|
||||||
|
import {StringTableEntry} from './StringTable';
|
||||||
import {Team, TeamNumber} from './Team';
|
import {Team, TeamNumber} from './Team';
|
||||||
import {UserInfo} from './UserInfo';
|
import {UserInfo} from './UserInfo';
|
||||||
import {Weapon} from './Weapon';
|
import {Weapon} from './Weapon';
|
||||||
import {World} from './World';
|
import {World} from './World';
|
||||||
import {Round} from './Round';
|
|
||||||
import {Chat} from './Chat';
|
|
||||||
import {Packet} from './Packet';
|
|
||||||
import {ParserState} from './ParserState';
|
|
||||||
import {StringTableEntry} from './StringTable';
|
|
||||||
|
|
||||||
export class Match {
|
export class Match {
|
||||||
public tick: number = 0;
|
public tick: number = 0;
|
||||||
|
|
@ -27,7 +27,7 @@ export class Match {
|
||||||
public intervalPerTick: number = 0;
|
public intervalPerTick: number = 0;
|
||||||
public world: World = {
|
public world: World = {
|
||||||
boundaryMin: {x: 0, y: 0, z: 0},
|
boundaryMin: {x: 0, y: 0, z: 0},
|
||||||
boundaryMax: {x: 0, y: 0, z: 0},
|
boundaryMax: {x: 0, y: 0, z: 0}
|
||||||
};
|
};
|
||||||
public playerEntityMap: Map<EntityId, Player> = new Map();
|
public playerEntityMap: Map<EntityId, Player> = new Map();
|
||||||
public weaponMap: Map<EntityId, Weapon> = new Map();
|
public weaponMap: Map<EntityId, Weapon> = new Map();
|
||||||
|
|
@ -49,7 +49,7 @@ export class Match {
|
||||||
classes: user.classes,
|
classes: user.classes,
|
||||||
name: user.name,
|
name: user.name,
|
||||||
steamId: user.steamId,
|
steamId: user.steamId,
|
||||||
userId: user.userId,
|
userId: user.userId
|
||||||
};
|
};
|
||||||
if (user.team) {
|
if (user.team) {
|
||||||
users[key].team = user.team;
|
users[key].team = user.team;
|
||||||
|
|
@ -62,7 +62,7 @@ export class Match {
|
||||||
deaths: this.deaths,
|
deaths: this.deaths,
|
||||||
rounds: this.rounds,
|
rounds: this.rounds,
|
||||||
startTick: this.startTick,
|
startTick: this.startTick,
|
||||||
intervalPerTick: this.intervalPerTick,
|
intervalPerTick: this.intervalPerTick
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -94,6 +94,38 @@ export class Match {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public getUserInfo(userId: number): UserInfo {
|
||||||
|
// no clue why it does this
|
||||||
|
// only seems to be the case with per user ready
|
||||||
|
while (userId > 256) {
|
||||||
|
userId -= 256;
|
||||||
|
}
|
||||||
|
const user = this.users.get(userId);
|
||||||
|
if (!user) {
|
||||||
|
|
||||||
|
const newUser = {
|
||||||
|
name: '',
|
||||||
|
userId,
|
||||||
|
steamId: '',
|
||||||
|
classes: {},
|
||||||
|
entityId: 0,
|
||||||
|
team: ''
|
||||||
|
};
|
||||||
|
this.users.set(userId, newUser);
|
||||||
|
return newUser;
|
||||||
|
}
|
||||||
|
return user;
|
||||||
|
}
|
||||||
|
|
||||||
|
public getUserInfoForEntity(entity: PacketEntity): UserInfo | null {
|
||||||
|
for (const user of this.users.values()) {
|
||||||
|
if (user && user.entityId === entity.entityIndex) {
|
||||||
|
return user;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return this.calculateUserInfoByEntityId(entity.entityIndex);
|
||||||
|
}
|
||||||
|
|
||||||
private calculateUserInfo() {
|
private calculateUserInfo() {
|
||||||
for (const [text, extraData] of this.parserState.userInfoEntries.entries()) {
|
for (const [text, extraData] of this.parserState.userInfoEntries.entries()) {
|
||||||
this.calculateUserInfoFromEntry(text, extraData);
|
this.calculateUserInfoFromEntry(text, extraData);
|
||||||
|
|
@ -127,36 +159,4 @@ export class Match {
|
||||||
throw new Error();
|
throw new Error();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public getUserInfo(userId: number): UserInfo {
|
|
||||||
// no clue why it does this
|
|
||||||
// only seems to be the case with per user ready
|
|
||||||
while (userId > 256) {
|
|
||||||
userId -= 256;
|
|
||||||
}
|
|
||||||
const user = this.users.get(userId);
|
|
||||||
if (!user) {
|
|
||||||
|
|
||||||
const newUser = {
|
|
||||||
name: '',
|
|
||||||
userId,
|
|
||||||
steamId: '',
|
|
||||||
classes: {},
|
|
||||||
entityId: 0,
|
|
||||||
team: '',
|
|
||||||
};
|
|
||||||
this.users.set(userId, newUser);
|
|
||||||
return newUser;
|
|
||||||
}
|
|
||||||
return user;
|
|
||||||
}
|
|
||||||
|
|
||||||
public getUserInfoForEntity(entity: PacketEntity): UserInfo | null {
|
|
||||||
for (const user of this.users.values()) {
|
|
||||||
if (user && user.entityId === entity.entityIndex) {
|
|
||||||
return user;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return this.calculateUserInfoByEntityId(entity.entityIndex);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,9 +1,9 @@
|
||||||
import {Packet} from './Packet';
|
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {ServerClass} from './ServerClass';
|
import {Packet} from './Packet';
|
||||||
import {SendTable} from './SendTable';
|
|
||||||
import {StringTable} from './StringTable';
|
|
||||||
import {ParserState} from './ParserState';
|
import {ParserState} from './ParserState';
|
||||||
|
import {SendTable} from './SendTable';
|
||||||
|
import {ServerClass} from './ServerClass';
|
||||||
|
import {StringTable} from './StringTable';
|
||||||
import {Vector} from './Vector';
|
import {Vector} from './Vector';
|
||||||
|
|
||||||
export enum MessageType {
|
export enum MessageType {
|
||||||
|
|
@ -14,7 +14,7 @@ export enum MessageType {
|
||||||
UserCmd = 5,
|
UserCmd = 5,
|
||||||
DataTables = 6,
|
DataTables = 6,
|
||||||
Stop = 7,
|
Stop = 7,
|
||||||
StringTables = 8,
|
StringTables = 8
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface BaseMessage {
|
export interface BaseMessage {
|
||||||
|
|
@ -33,8 +33,7 @@ export interface PacketMessage extends BaseMessage {
|
||||||
flags: number;
|
flags: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface SigonMessage extends PacketMessage {
|
export type SigonMessage = PacketMessage;
|
||||||
}
|
|
||||||
|
|
||||||
export interface SyncTickMessage extends BaseMessage {
|
export interface SyncTickMessage extends BaseMessage {
|
||||||
type: MessageType.SyncTick;
|
type: MessageType.SyncTick;
|
||||||
|
|
@ -53,7 +52,7 @@ export interface UserCmdMessage extends BaseMessage {
|
||||||
export interface DataTablesMessage extends BaseMessage {
|
export interface DataTablesMessage extends BaseMessage {
|
||||||
type: MessageType.DataTables;
|
type: MessageType.DataTables;
|
||||||
tables: SendTable[];
|
tables: SendTable[];
|
||||||
serverClasses: ServerClass[]
|
serverClasses: ServerClass[];
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface StopMessage extends BaseMessage {
|
export interface StopMessage extends BaseMessage {
|
||||||
|
|
@ -62,7 +61,7 @@ export interface StopMessage extends BaseMessage {
|
||||||
|
|
||||||
export interface StringTablesMessage extends BaseMessage {
|
export interface StringTablesMessage extends BaseMessage {
|
||||||
type: MessageType.StringTables;
|
type: MessageType.StringTables;
|
||||||
tables: StringTable[]
|
tables: StringTable[];
|
||||||
}
|
}
|
||||||
|
|
||||||
export type Message = SigonMessage |
|
export type Message = SigonMessage |
|
||||||
|
|
|
||||||
|
|
@ -1,48 +1,45 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {GameEventDefinition} from './GameEvent';
|
import {GameEventDefinition} from './GameEvent';
|
||||||
|
import {GameEvent, GameEventType} from './GameEventTypes';
|
||||||
import {EntityId, PacketEntity} from './PacketEntity';
|
import {EntityId, PacketEntity} from './PacketEntity';
|
||||||
import {SendTable} from './SendTable';
|
import {SendTable} from './SendTable';
|
||||||
import {ServerClass} from './ServerClass';
|
import {ServerClass} from './ServerClass';
|
||||||
import {StringTable, StringTableEntry} from './StringTable';
|
import {StringTable, StringTableEntry} from './StringTable';
|
||||||
import {Vector} from './Vector';
|
|
||||||
import {GameEvent, GameEventType} from './GameEventTypes';
|
|
||||||
import {
|
import {
|
||||||
BreakModelPumpkinPacket, ResetHUDPacket, TextMessagePacket, TrainPacket, UnknownUserMessagePacket,
|
BreakModelPumpkinPacket, ResetHUDPacket, SayText2Packet, TextMessagePacket, TrainPacket,
|
||||||
UserMessagePacket, UserMessageType,
|
UnknownUserMessagePacket, UserMessagePacket,
|
||||||
UserMessageTypeMap, VoiceSubtitlePacket, SayText2Packet
|
UserMessageType, UserMessageTypeMap, VoiceSubtitlePacket
|
||||||
} from './UserMessage';
|
} from './UserMessage';
|
||||||
|
import {Vector} from './Vector';
|
||||||
|
|
||||||
export interface BasePacket {
|
export interface StringTablePacket {
|
||||||
}
|
|
||||||
|
|
||||||
export interface StringTablePacket extends BasePacket {
|
|
||||||
packetType: 'stringTable';
|
packetType: 'stringTable';
|
||||||
tables: StringTable[];
|
tables: StringTable[];
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface CreateStringTablePacket extends BasePacket {
|
export interface CreateStringTablePacket {
|
||||||
packetType: 'createStringTable';
|
packetType: 'createStringTable';
|
||||||
table: StringTable;
|
table: StringTable;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface UpdateStringTablePacket extends BasePacket {
|
export interface UpdateStringTablePacket {
|
||||||
packetType: 'updateStringTable';
|
packetType: 'updateStringTable';
|
||||||
entries: StringTableEntry[];
|
entries: StringTableEntry[];
|
||||||
tableId: number;
|
tableId: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface ConsoleCmdPacket extends BasePacket {
|
export interface ConsoleCmdPacket {
|
||||||
packetType: 'consoleCmd';
|
packetType: 'consoleCmd';
|
||||||
command: string;
|
command: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface DataTablePacket extends BasePacket {
|
export interface DataTablePacket {
|
||||||
packetType: 'dataTable';
|
packetType: 'dataTable';
|
||||||
tables: SendTable[];
|
tables: SendTable[];
|
||||||
serverClasses: ServerClass[];
|
serverClasses: ServerClass[];
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface BSPDecalPacket extends BasePacket {
|
export interface BSPDecalPacket {
|
||||||
packetType: 'bspDecal';
|
packetType: 'bspDecal';
|
||||||
position: Vector;
|
position: Vector;
|
||||||
textureIndex: number;
|
textureIndex: number;
|
||||||
|
|
@ -51,35 +48,35 @@ export interface BSPDecalPacket extends BasePacket {
|
||||||
lowPriority: boolean;
|
lowPriority: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface ClassInfoPacket extends BasePacket {
|
export interface ClassInfoPacket {
|
||||||
packetType: 'classInfo';
|
packetType: 'classInfo';
|
||||||
number: number;
|
number: number;
|
||||||
create: boolean;
|
create: boolean;
|
||||||
entries: {
|
entries: Array<{
|
||||||
classId: number;
|
classId: number;
|
||||||
className: string;
|
className: string;
|
||||||
dataTableName: string;
|
dataTableName: string;
|
||||||
}[];
|
}>;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface EntityMessagePacket extends BasePacket {
|
export interface EntityMessagePacket {
|
||||||
packetType: 'entityMessage';
|
packetType: 'entityMessage';
|
||||||
classId: number;
|
classId: number;
|
||||||
length: number;
|
length: number;
|
||||||
data: string;
|
data: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface GameEventPacket extends BasePacket {
|
export interface GameEventPacket {
|
||||||
packetType: 'gameEvent';
|
packetType: 'gameEvent';
|
||||||
event: GameEvent;
|
event: GameEvent;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface GameEventListPacket extends BasePacket {
|
export interface GameEventListPacket {
|
||||||
packetType: 'gameEventList';
|
packetType: 'gameEventList';
|
||||||
eventList: Map<number, GameEventDefinition<GameEvent['name']>>;
|
eventList: Map<number, GameEventDefinition<GameEvent['name']>>;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface PacketEntitiesPacket extends BasePacket {
|
export interface PacketEntitiesPacket {
|
||||||
packetType: 'packetEntities';
|
packetType: 'packetEntities';
|
||||||
entities: PacketEntity[];
|
entities: PacketEntity[];
|
||||||
removedEntities: EntityId[];
|
removedEntities: EntityId[];
|
||||||
|
|
@ -89,7 +86,7 @@ export interface PacketEntitiesPacket extends BasePacket {
|
||||||
updatedBaseLine: boolean;
|
updatedBaseLine: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface ParseSoundsPacket extends BasePacket {
|
export interface ParseSoundsPacket {
|
||||||
packetType: 'parseSounds';
|
packetType: 'parseSounds';
|
||||||
reliable: boolean;
|
reliable: boolean;
|
||||||
num: number;
|
num: number;
|
||||||
|
|
@ -97,24 +94,24 @@ export interface ParseSoundsPacket extends BasePacket {
|
||||||
data: BitStream;
|
data: BitStream;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface SetConVarPacket extends BasePacket {
|
export interface SetConVarPacket {
|
||||||
packetType: 'setConVar';
|
packetType: 'setConVar';
|
||||||
vars: Map<string, string>;
|
vars: Map<string, string>;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface TempEntitiesPacket extends BasePacket {
|
export interface TempEntitiesPacket {
|
||||||
packetType: 'tempEntities';
|
packetType: 'tempEntities';
|
||||||
entities: PacketEntity[];
|
entities: PacketEntity[];
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface VoiceInitPacket extends BasePacket {
|
export interface VoiceInitPacket {
|
||||||
packetType: 'voiceInit';
|
packetType: 'voiceInit';
|
||||||
codec: string;
|
codec: string;
|
||||||
quality: number;
|
quality: number;
|
||||||
extraData: number;
|
extraData: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface VoiceDataPacket extends BasePacket {
|
export interface VoiceDataPacket {
|
||||||
packetType: 'voiceData';
|
packetType: 'voiceData';
|
||||||
client: number;
|
client: number;
|
||||||
proximity: number;
|
proximity: number;
|
||||||
|
|
@ -122,54 +119,54 @@ export interface VoiceDataPacket extends BasePacket {
|
||||||
data: BitStream;
|
data: BitStream;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface MenuPacket extends BasePacket {
|
export interface MenuPacket {
|
||||||
packetType: 'menu';
|
packetType: 'menu';
|
||||||
type: number;
|
type: number;
|
||||||
length: number;
|
length: number;
|
||||||
data: BitStream;
|
data: BitStream;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface CmdKeyValuesPacket extends BasePacket {
|
export interface CmdKeyValuesPacket {
|
||||||
packetType: 'cmdKeyValues';
|
packetType: 'cmdKeyValues';
|
||||||
length: number;
|
length: number;
|
||||||
data: BitStream;
|
data: BitStream;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface VoidPacket extends BasePacket {
|
export interface VoidPacket {
|
||||||
packetType: 'void';
|
packetType: 'void';
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface FilePacket extends BasePacket {
|
export interface FilePacket {
|
||||||
packetType: 'file';
|
packetType: 'file';
|
||||||
transferId: number;
|
transferId: number;
|
||||||
fileName: string;
|
fileName: string;
|
||||||
requested: boolean;
|
requested: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface NetTickPacket extends BasePacket {
|
export interface NetTickPacket {
|
||||||
packetType: 'netTick';
|
packetType: 'netTick';
|
||||||
tick: number;
|
tick: number;
|
||||||
frameTime: number;
|
frameTime: number;
|
||||||
stdDev: number;
|
stdDev: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface StringCmdPacket extends BasePacket {
|
export interface StringCmdPacket {
|
||||||
packetType: 'stringCmd';
|
packetType: 'stringCmd';
|
||||||
command: string;
|
command: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface SigOnStatePacket extends BasePacket {
|
export interface SigOnStatePacket {
|
||||||
packetType: 'sigOnState';
|
packetType: 'sigOnState';
|
||||||
state: number;
|
state: number;
|
||||||
count: number;
|
count: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface PrintPacket extends BasePacket {
|
export interface PrintPacket {
|
||||||
packetType: 'print';
|
packetType: 'print';
|
||||||
value: string;
|
value: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface ServerInfoPacket extends BasePacket {
|
export interface ServerInfoPacket {
|
||||||
packetType: 'serverInfo';
|
packetType: 'serverInfo';
|
||||||
version: number;
|
version: number;
|
||||||
serverCount: number;
|
serverCount: number;
|
||||||
|
|
@ -188,17 +185,17 @@ export interface ServerInfoPacket extends BasePacket {
|
||||||
replay: boolean;
|
replay: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface SetPausePacket extends BasePacket {
|
export interface SetPausePacket {
|
||||||
packetType: 'setPause';
|
packetType: 'setPause';
|
||||||
paused: boolean;
|
paused: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface SetViewPacket extends BasePacket {
|
export interface SetViewPacket {
|
||||||
packetType: 'setView';
|
packetType: 'setView';
|
||||||
index: number;
|
index: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface FixAnglePacket extends BasePacket {
|
export interface FixAnglePacket {
|
||||||
packetType: 'fixAngle';
|
packetType: 'fixAngle';
|
||||||
relative: boolean;
|
relative: boolean;
|
||||||
x: number;
|
x: number;
|
||||||
|
|
@ -206,12 +203,12 @@ export interface FixAnglePacket extends BasePacket {
|
||||||
z: number;
|
z: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface PreFetchPacket extends BasePacket {
|
export interface PreFetchPacket {
|
||||||
packetType: 'preFetch';
|
packetType: 'preFetch';
|
||||||
index: number;
|
index: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface GetCvarValuePacket extends BasePacket {
|
export interface GetCvarValuePacket {
|
||||||
packetType: 'getCvarValue';
|
packetType: 'getCvarValue';
|
||||||
cookie: number;
|
cookie: number;
|
||||||
value: string;
|
value: string;
|
||||||
|
|
@ -312,5 +309,5 @@ export enum PacketTypeId {
|
||||||
menu = 29,
|
menu = 29,
|
||||||
gameEventList = 30,
|
gameEventList = 30,
|
||||||
getCvarValue = 31,
|
getCvarValue = 31,
|
||||||
cmdKeyValues = 32,
|
cmdKeyValues = 32
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -6,12 +6,21 @@ export enum PVS {
|
||||||
PRESERVE = 0,
|
PRESERVE = 0,
|
||||||
ENTER = 1,
|
ENTER = 1,
|
||||||
LEAVE = 2,
|
LEAVE = 2,
|
||||||
DELETE = 4,
|
DELETE = 4
|
||||||
}
|
}
|
||||||
|
|
||||||
export type EntityId = number;
|
export type EntityId = number;
|
||||||
|
|
||||||
export class PacketEntity {
|
export class PacketEntity {
|
||||||
|
public static getPropByFullName(props: SendProp[], fullName: string): SendProp | null {
|
||||||
|
for (const prop of props) {
|
||||||
|
if (prop.definition.fullName === fullName) {
|
||||||
|
return prop;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
public serverClass: ServerClass;
|
public serverClass: ServerClass;
|
||||||
public entityIndex: EntityId;
|
public entityIndex: EntityId;
|
||||||
public props: SendProp[];
|
public props: SendProp[];
|
||||||
|
|
@ -28,15 +37,6 @@ export class PacketEntity {
|
||||||
this.pvs = pvs;
|
this.pvs = pvs;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static getPropByFullName(props: SendProp[], fullName: string): SendProp | null {
|
|
||||||
for (const prop of props) {
|
|
||||||
if (prop.definition.fullName === fullName) {
|
|
||||||
return prop;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
public getPropByDefinition(definition: SendPropDefinition) {
|
public getPropByDefinition(definition: SendPropDefinition) {
|
||||||
return PacketEntity.getPropByFullName(this.props, definition.fullName);
|
return PacketEntity.getPropByFullName(this.props, definition.fullName);
|
||||||
}
|
}
|
||||||
|
|
@ -75,7 +75,7 @@ export class PacketEntity {
|
||||||
}
|
}
|
||||||
|
|
||||||
public diffFromBaseLine(baselineProps: SendProp[]): SendProp[] {
|
public diffFromBaseLine(baselineProps: SendProp[]): SendProp[] {
|
||||||
return this.props.filter(prop => {
|
return this.props.filter((prop) => {
|
||||||
const baseProp = PacketEntity.getPropByFullName(baselineProps, prop.definition.fullName);
|
const baseProp = PacketEntity.getPropByFullName(baselineProps, prop.definition.fullName);
|
||||||
return (!baseProp || prop.value !== baseProp.value);
|
return (!baseProp || prop.value !== baseProp.value);
|
||||||
});
|
});
|
||||||
|
|
|
||||||
|
|
@ -1,19 +1,19 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {GameEventDefinition} from './GameEvent';
|
import {handleGameEventList} from '../PacketHandler/GameEventList';
|
||||||
import {EntityId} from './PacketEntity';
|
import {handlePacketEntitiesForState} from '../PacketHandler/PacketEntities';
|
||||||
import {SendTable, SendTableName} from './SendTable';
|
|
||||||
import {ServerClass, ServerClassId} from './ServerClass';
|
|
||||||
import {StringTable} from './StringTable';
|
|
||||||
import {GameEventType} from './GameEventTypes';
|
|
||||||
import {SendProp} from './SendProp';
|
|
||||||
import {Packet, PacketTypeId} from './Packet';
|
|
||||||
import {
|
import {
|
||||||
handleStringTable, handleStringTables, handleStringTableUpdate,
|
handleStringTable, handleStringTables, handleStringTableUpdate,
|
||||||
handleTable
|
handleTable
|
||||||
} from '../PacketHandler/StringTable';
|
} from '../PacketHandler/StringTable';
|
||||||
import {handleGameEventList} from '../PacketHandler/GameEventList';
|
import {GameEventDefinition} from './GameEvent';
|
||||||
|
import {GameEventType} from './GameEventTypes';
|
||||||
import {DataTablesMessage, Message, MessageType, StringTablesMessage} from './Message';
|
import {DataTablesMessage, Message, MessageType, StringTablesMessage} from './Message';
|
||||||
import {handlePacketEntitiesForState} from '../PacketHandler/PacketEntities';
|
import {Packet, PacketTypeId} from './Packet';
|
||||||
|
import {EntityId} from './PacketEntity';
|
||||||
|
import {SendProp} from './SendProp';
|
||||||
|
import {SendTable, SendTableName} from './SendTable';
|
||||||
|
import {ServerClass, ServerClassId} from './ServerClass';
|
||||||
|
import {StringTable} from './StringTable';
|
||||||
|
|
||||||
export class ParserState {
|
export class ParserState {
|
||||||
public version: number = 0;
|
public version: number = 0;
|
||||||
|
|
@ -62,6 +62,14 @@ export class ParserState {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public getStringTable(name: string): StringTable | null {
|
||||||
|
const table = this.stringTables.find((stringTable) => stringTable.name === name);
|
||||||
|
if (!table) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
return table;
|
||||||
|
}
|
||||||
|
|
||||||
private handleDataTableMessage(message: DataTablesMessage) {
|
private handleDataTableMessage(message: DataTablesMessage) {
|
||||||
for (const table of message.tables) {
|
for (const table of message.tables) {
|
||||||
this.sendTables.set(table.name, table);
|
this.sendTables.set(table.name, table);
|
||||||
|
|
@ -74,14 +82,6 @@ export class ParserState {
|
||||||
handleTable(table, this);
|
handleTable(table, this);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public getStringTable(name: string): StringTable | null {
|
|
||||||
const table = this.stringTables.find(table => table.name === name);
|
|
||||||
if (!table) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
return table;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export function getClassBits(state: ParserState) {
|
export function getClassBits(state: ParserState) {
|
||||||
|
|
|
||||||
|
|
@ -1,15 +1,15 @@
|
||||||
import {Match} from './Match';
|
import {Match} from './Match';
|
||||||
|
import {EntityId} from './PacketEntity';
|
||||||
import {PlayerCondition} from './PlayerCondition';
|
import {PlayerCondition} from './PlayerCondition';
|
||||||
import {UserInfo} from './UserInfo';
|
import {UserInfo} from './UserInfo';
|
||||||
import {Vector} from './Vector';
|
import {Vector} from './Vector';
|
||||||
import {Weapon} from './Weapon';
|
import {Weapon} from './Weapon';
|
||||||
import {EntityId} from './PacketEntity';
|
|
||||||
|
|
||||||
export enum LifeState {
|
export enum LifeState {
|
||||||
ALIVE = 0,
|
ALIVE = 0,
|
||||||
DYING = 1,
|
DYING = 1,
|
||||||
DEATH = 2,
|
DEATH = 2,
|
||||||
RESPAWNABLE = 3,
|
RESPAWNABLE = 3
|
||||||
}
|
}
|
||||||
|
|
||||||
export class Player {
|
export class Player {
|
||||||
|
|
@ -33,8 +33,8 @@ export class Player {
|
||||||
|
|
||||||
get weapons(): Weapon[] {
|
get weapons(): Weapon[] {
|
||||||
return this.weaponIds
|
return this.weaponIds
|
||||||
.map(id => this.match.outerMap.get(id) as EntityId)
|
.map((id) => this.match.outerMap.get(id) as EntityId)
|
||||||
.filter(entityId => entityId > 0)
|
.filter((entityId) => entityId > 0)
|
||||||
.map(entityId => this.match.weaponMap.get(entityId) as Weapon);
|
.map((entityId) => this.match.weaponMap.get(entityId) as Weapon);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -77,5 +77,5 @@ export enum PlayerCondition {
|
||||||
TF_COND_HALLOWEEN_TINY = (1 << 75),
|
TF_COND_HALLOWEEN_TINY = (1 << 75),
|
||||||
TF_COND_HALLOWEEN_IN_HELL = (1 << 76),
|
TF_COND_HALLOWEEN_IN_HELL = (1 << 76),
|
||||||
TF_COND_HALLOWEEN_GHOST_MODE = (1 << 77),
|
TF_COND_HALLOWEEN_GHOST_MODE = (1 << 77),
|
||||||
TF_COND_MINICRITBOOSTED_ON_KILL = (1 << 78),
|
TF_COND_MINICRITBOOSTED_ON_KILL = (1 << 78)
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,5 @@
|
||||||
export interface Round {
|
export interface Round {
|
||||||
winner: 'red' | 'blue',
|
winner: 'red' | 'blue';
|
||||||
length: number;
|
length: number;
|
||||||
end_tick: number;
|
end_tick: number;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,21 @@
|
||||||
import {SendTable} from './SendTable';
|
import {SendTable} from './SendTable';
|
||||||
|
|
||||||
export class SendPropDefinition {
|
export class SendPropDefinition {
|
||||||
|
public static formatFlags(flags: number) {
|
||||||
|
const names: string[] = [];
|
||||||
|
for (const name in SendPropFlag) {
|
||||||
|
if ((SendPropFlag as object).hasOwnProperty(name)) {
|
||||||
|
const flagValue = SendPropFlag[name] as SendPropFlag | string;
|
||||||
|
if (typeof flagValue === 'number') {
|
||||||
|
if (flags & flagValue) {
|
||||||
|
names.push(name);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return names;
|
||||||
|
}
|
||||||
|
|
||||||
public type: SendPropType;
|
public type: SendPropType;
|
||||||
public name: string;
|
public name: string;
|
||||||
public flags: number;
|
public flags: number;
|
||||||
|
|
@ -41,7 +56,7 @@ export class SendPropDefinition {
|
||||||
name: this.name,
|
name: this.name,
|
||||||
type: SendPropType[this.type],
|
type: SendPropType[this.type],
|
||||||
flags: this.flags,
|
flags: this.flags,
|
||||||
bitCount: this.bitCount,
|
bitCount: this.bitCount
|
||||||
};
|
};
|
||||||
if (this.type === SendPropType.DPT_Float) {
|
if (this.type === SendPropType.DPT_Float) {
|
||||||
data.lowValue = this.lowValue;
|
data.lowValue = this.lowValue;
|
||||||
|
|
@ -61,19 +76,6 @@ export class SendPropDefinition {
|
||||||
get allFlags() {
|
get allFlags() {
|
||||||
return SendPropDefinition.formatFlags(this.flags);
|
return SendPropDefinition.formatFlags(this.flags);
|
||||||
}
|
}
|
||||||
|
|
||||||
static formatFlags(flags: number) {
|
|
||||||
let names: string[] = [];
|
|
||||||
for (const name in SendPropFlag) {
|
|
||||||
const flagValue = <SendPropFlag | string>SendPropFlag[name];
|
|
||||||
if (typeof flagValue === 'number') {
|
|
||||||
if (flags & flagValue) {
|
|
||||||
names.push(name);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return names;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export enum SendPropType {
|
export enum SendPropType {
|
||||||
|
|
@ -84,7 +86,7 @@ export enum SendPropType {
|
||||||
DPT_String,
|
DPT_String,
|
||||||
DPT_Array,
|
DPT_Array,
|
||||||
DPT_DataTable,
|
DPT_DataTable,
|
||||||
DPT_NUMSendPropTypes,
|
DPT_NUMSendPropTypes
|
||||||
}
|
}
|
||||||
|
|
||||||
export enum SendPropFlag {
|
export enum SendPropFlag {
|
||||||
|
|
@ -111,5 +113,5 @@ export enum SendPropFlag {
|
||||||
SPROP_COORD_MP_LOWPRECISION = (1 << 14), // Like SPROP_COORD, but special handling for multiplayer games
|
SPROP_COORD_MP_LOWPRECISION = (1 << 14), // Like SPROP_COORD, but special handling for multiplayer games
|
||||||
// where the fractional component only gets a 3 bits instead of 5
|
// where the fractional component only gets a 3 bits instead of 5
|
||||||
SPROP_COORD_MP_INTEGRAL = (1 << 15), // SPROP_COORD_MP, but coordinates are rounded to integral boundaries
|
SPROP_COORD_MP_INTEGRAL = (1 << 15), // SPROP_COORD_MP, but coordinates are rounded to integral boundaries
|
||||||
SPROP_VARINT = (1 << 5),
|
SPROP_VARINT = (1 << 5)
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -2,7 +2,7 @@ export enum TeamNumber {
|
||||||
UNASGINED = 0,
|
UNASGINED = 0,
|
||||||
SPECTATOR = 1,
|
SPECTATOR = 1,
|
||||||
RED = 2,
|
RED = 2,
|
||||||
BLU = 3,
|
BLU = 3
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface Team {
|
export interface Team {
|
||||||
|
|
|
||||||
|
|
@ -1,4 +1,3 @@
|
||||||
import {BasePacket} from './Packet';
|
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
|
|
||||||
export enum UserMessageType {
|
export enum UserMessageType {
|
||||||
|
|
@ -59,14 +58,14 @@ export enum UserMessageType {
|
||||||
HapPunch = 54,
|
HapPunch = 54,
|
||||||
HapSetDrag = 55,
|
HapSetDrag = 55,
|
||||||
HapSet = 56,
|
HapSet = 56,
|
||||||
HapMeleeContact = 57,
|
HapMeleeContact = 57
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface BaseDataUserPacket extends BasePacket {
|
export interface BaseDataUserPacket {
|
||||||
data: number;
|
data: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface SayText2Packet extends BasePacket {
|
export interface SayText2Packet {
|
||||||
packetType: 'sayText2';
|
packetType: 'sayText2';
|
||||||
client: number;
|
client: number;
|
||||||
raw: number;
|
raw: number;
|
||||||
|
|
@ -82,7 +81,7 @@ export enum HudTextLocation {
|
||||||
HUD_PRINTCENTER = 4
|
HUD_PRINTCENTER = 4
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface TextMessagePacket extends BasePacket {
|
export interface TextMessagePacket {
|
||||||
packetType: 'textMsg';
|
packetType: 'textMsg';
|
||||||
destType: HudTextLocation;
|
destType: HudTextLocation;
|
||||||
text: string;
|
text: string;
|
||||||
|
|
@ -96,14 +95,14 @@ export interface TrainPacket extends BaseDataUserPacket {
|
||||||
packetType: 'train';
|
packetType: 'train';
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface VoiceSubtitlePacket extends BasePacket {
|
export interface VoiceSubtitlePacket {
|
||||||
packetType: 'voiceSubtitle';
|
packetType: 'voiceSubtitle';
|
||||||
client: number;
|
client: number;
|
||||||
menu: number;
|
menu: number;
|
||||||
item: number;
|
item: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface ShakePacket extends BasePacket {
|
export interface ShakePacket {
|
||||||
packetType: 'shake';
|
packetType: 'shake';
|
||||||
command: number;
|
command: number;
|
||||||
amplitude: number;
|
amplitude: number;
|
||||||
|
|
@ -111,7 +110,7 @@ export interface ShakePacket extends BasePacket {
|
||||||
duration: number;
|
duration: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface UnknownUserMessageBasePacket extends BasePacket {
|
export interface UnknownUserMessageBasePacket {
|
||||||
data: BitStream;
|
data: BitStream;
|
||||||
type: number;
|
type: number;
|
||||||
}
|
}
|
||||||
|
|
@ -136,7 +135,7 @@ export type UserMessagePacket = SayText2Packet
|
||||||
| BreakModelPumpkinPacket
|
| BreakModelPumpkinPacket
|
||||||
| ShakePacket;
|
| ShakePacket;
|
||||||
|
|
||||||
export type UserMessageTypeMap = {
|
export interface UserMessageTypeMap {
|
||||||
sayText2: SayText2Packet;
|
sayText2: SayText2Packet;
|
||||||
textMsg: TextMessagePacket;
|
textMsg: TextMessagePacket;
|
||||||
unknownUserMessage: GenericUnknownUserMessagePacket;
|
unknownUserMessage: GenericUnknownUserMessagePacket;
|
||||||
|
|
@ -147,7 +146,8 @@ export type UserMessageTypeMap = {
|
||||||
shake: ShakePacket;
|
shake: ShakePacket;
|
||||||
}
|
}
|
||||||
|
|
||||||
export const UserMessagePacketTypeMap: Map<UserMessagePacket['packetType'], UserMessageType> = new Map<UserMessagePacket['packetType'], UserMessageType>([
|
export const UserMessagePacketTypeMap: Map<UserMessagePacket['packetType'], UserMessageType> =
|
||||||
|
new Map<UserMessagePacket['packetType'], UserMessageType>([
|
||||||
['sayText2', UserMessageType.SayText2],
|
['sayText2', UserMessageType.SayText2],
|
||||||
['textMsg', UserMessageType.TextMsg],
|
['textMsg', UserMessageType.TextMsg],
|
||||||
['train', UserMessageType.Train],
|
['train', UserMessageType.Train],
|
||||||
|
|
@ -155,4 +155,4 @@ export const UserMessagePacketTypeMap: Map<UserMessagePacket['packetType'], User
|
||||||
['breakModelPumpkin', UserMessageType.BreakModel_Pumpkin],
|
['breakModelPumpkin', UserMessageType.BreakModel_Pumpkin],
|
||||||
['resetHUD', UserMessageType.ResetHUD],
|
['resetHUD', UserMessageType.ResetHUD],
|
||||||
['shake', UserMessageType.Shake]
|
['shake', UserMessageType.Shake]
|
||||||
]);
|
]);
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,7 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {Parser} from './Parser';
|
|
||||||
import {PacketTypeId} from './Data/Packet';
|
|
||||||
import {Analyser} from './Analyser';
|
import {Analyser} from './Analyser';
|
||||||
|
import {PacketTypeId} from './Data/Packet';
|
||||||
|
import {Parser} from './Parser';
|
||||||
|
|
||||||
export class Demo {
|
export class Demo {
|
||||||
public static fromNodeBuffer(nodeBuffer) {
|
public static fromNodeBuffer(nodeBuffer) {
|
||||||
|
|
@ -26,7 +26,7 @@ export class Demo {
|
||||||
const skippedPackets = fastMode ? [
|
const skippedPackets = fastMode ? [
|
||||||
PacketTypeId.packetEntities,
|
PacketTypeId.packetEntities,
|
||||||
PacketTypeId.tempEntities,
|
PacketTypeId.tempEntities,
|
||||||
PacketTypeId.entityMessage,
|
PacketTypeId.entityMessage
|
||||||
] : [];
|
] : [];
|
||||||
this.parser = new Parser(this.stream, skippedPackets);
|
this.parser = new Parser(this.stream, skippedPackets);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,23 +1,5 @@
|
||||||
import {BitStream, BitView} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
|
import {DynamicBitView} from './DynamicBitView';
|
||||||
class DynamicBitView extends BitView {
|
|
||||||
protected _view: Uint8Array;
|
|
||||||
|
|
||||||
setBits(offset: number, value: number, bits: number) {
|
|
||||||
const available = (this.byteLength * 8 - offset);
|
|
||||||
|
|
||||||
if (bits > available) {
|
|
||||||
this.grow();
|
|
||||||
}
|
|
||||||
return super.setBits(offset, value, bits);
|
|
||||||
}
|
|
||||||
|
|
||||||
grow() {
|
|
||||||
const newView = new Uint8Array(this.byteLength * 2);
|
|
||||||
newView.set(this._view);
|
|
||||||
this._view = newView;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
export class DynamicBitStream extends BitStream {
|
export class DynamicBitStream extends BitStream {
|
||||||
constructor(initialByteSize: number = 16 * 1024) {
|
constructor(initialByteSize: number = 16 * 1024) {
|
||||||
|
|
|
||||||
21
src/DynamicBitView.ts
Normal file
21
src/DynamicBitView.ts
Normal file
|
|
@ -0,0 +1,21 @@
|
||||||
|
import {BitView} from 'bit-buffer';
|
||||||
|
|
||||||
|
export class DynamicBitView extends BitView {
|
||||||
|
// tslint:disable-next-line
|
||||||
|
protected _view: Uint8Array;
|
||||||
|
|
||||||
|
public setBits(offset: number, value: number, bits: number) {
|
||||||
|
const available = (this.byteLength * 8 - offset);
|
||||||
|
|
||||||
|
if (bits > available) {
|
||||||
|
this.grow();
|
||||||
|
}
|
||||||
|
return super.setBits(offset, value, bits);
|
||||||
|
}
|
||||||
|
|
||||||
|
public grow() {
|
||||||
|
const newView = new Uint8Array(this.byteLength * 2);
|
||||||
|
newView.set(this._view);
|
||||||
|
this._view = newView;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -1,8 +1,8 @@
|
||||||
import {Match} from '../Data/Match';
|
|
||||||
import {GameEventPacket} from '../Data/Packet';
|
|
||||||
import {
|
import {
|
||||||
ObjectDestroyedEvent, PlayerDeathEvent, PlayerSpawnEvent, TeamPlayRoundStartEvent, TeamPlayRoundWinEvent
|
ObjectDestroyedEvent, PlayerDeathEvent, PlayerSpawnEvent, TeamPlayRoundStartEvent, TeamPlayRoundWinEvent
|
||||||
} from '../Data/GameEventTypes';
|
} from '../Data/GameEventTypes';
|
||||||
|
import {Match} from '../Data/Match';
|
||||||
|
import {GameEventPacket} from '../Data/Packet';
|
||||||
|
|
||||||
export function handleGameEvent(packet: GameEventPacket, match: Match) {
|
export function handleGameEvent(packet: GameEventPacket, match: Match) {
|
||||||
switch (packet.event.name) {
|
switch (packet.event.name) {
|
||||||
|
|
@ -42,7 +42,7 @@ function handlePlayerDeath(event: PlayerDeathEvent, match: Match) {
|
||||||
assister,
|
assister,
|
||||||
victim: values.userid,
|
victim: values.userid,
|
||||||
weapon: values.weapon,
|
weapon: values.weapon,
|
||||||
tick: match.tick,
|
tick: match.tick
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -52,7 +52,7 @@ function handleRoundWin(event: TeamPlayRoundWinEvent, match: Match) {
|
||||||
match.rounds.push({
|
match.rounds.push({
|
||||||
winner: values.team === 2 ? 'red' : 'blue',
|
winner: values.team === 2 ? 'red' : 'blue',
|
||||||
length: values.round_time,
|
length: values.round_time,
|
||||||
end_tick: match.tick,
|
end_tick: match.tick
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -2,12 +2,12 @@ import {Building, Dispenser, Sentry, Teleporter} from '../Data/Building';
|
||||||
import {Match} from '../Data/Match';
|
import {Match} from '../Data/Match';
|
||||||
import {PacketEntitiesPacket} from '../Data/Packet';
|
import {PacketEntitiesPacket} from '../Data/Packet';
|
||||||
import {PacketEntity, PVS} from '../Data/PacketEntity';
|
import {PacketEntity, PVS} from '../Data/PacketEntity';
|
||||||
|
import {ParserState} from '../Data/ParserState';
|
||||||
import {LifeState, Player} from '../Data/Player';
|
import {LifeState, Player} from '../Data/Player';
|
||||||
import {SendProp} from '../Data/SendProp';
|
import {SendProp} from '../Data/SendProp';
|
||||||
|
import {TeamNumber} from '../Data/Team';
|
||||||
import {Vector} from '../Data/Vector';
|
import {Vector} from '../Data/Vector';
|
||||||
import {CWeaponMedigun, Weapon} from '../Data/Weapon';
|
import {CWeaponMedigun, Weapon} from '../Data/Weapon';
|
||||||
import {TeamNumber} from '../Data/Team';
|
|
||||||
import {ParserState} from '../Data/ParserState';
|
|
||||||
|
|
||||||
export function handlePacketEntities(packet: PacketEntitiesPacket, match: Match) {
|
export function handlePacketEntities(packet: PacketEntitiesPacket, match: Match) {
|
||||||
for (const entity of packet.entities) {
|
for (const entity of packet.entities) {
|
||||||
|
|
@ -47,7 +47,7 @@ function handleEntity(entity: PacketEntity, match: Match) {
|
||||||
if (!match.weaponMap.has(entity.entityIndex)) {
|
if (!match.weaponMap.has(entity.entityIndex)) {
|
||||||
match.weaponMap.set(entity.entityIndex, {
|
match.weaponMap.set(entity.entityIndex, {
|
||||||
className: entity.serverClass.name,
|
className: entity.serverClass.name,
|
||||||
owner: prop.value as number,
|
owner: prop.value as number
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -176,7 +176,7 @@ function handleEntity(entity: PacketEntity, match: Match) {
|
||||||
score: entity.getProperty('DT_Team', 'm_iScore').value as number,
|
score: entity.getProperty('DT_Team', 'm_iScore').value as number,
|
||||||
roundsWon: entity.getProperty('DT_Team', 'm_iRoundsWon').value as number,
|
roundsWon: entity.getProperty('DT_Team', 'm_iRoundsWon').value as number,
|
||||||
players: entity.getProperty('DT_Team', '"player_array"').value as number[],
|
players: entity.getProperty('DT_Team', '"player_array"').value as number[],
|
||||||
teamNumber: teamId,
|
teamNumber: teamId
|
||||||
};
|
};
|
||||||
match.teams.set(teamId, team);
|
match.teams.set(teamId, team);
|
||||||
match.teamEntityMap.set(entity.entityIndex, team);
|
match.teamEntityMap.set(entity.entityIndex, team);
|
||||||
|
|
@ -225,7 +225,7 @@ function handleEntity(entity: PacketEntity, match: Match) {
|
||||||
shieldLevel: 0,
|
shieldLevel: 0,
|
||||||
isMini: false,
|
isMini: false,
|
||||||
team: 0,
|
team: 0,
|
||||||
angle: 0,
|
angle: 0
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
const sentry = match.buildings.get(entity.entityIndex) as Sentry;
|
const sentry = match.buildings.get(entity.entityIndex) as Sentry;
|
||||||
|
|
@ -274,7 +274,7 @@ function handleEntity(entity: PacketEntity, match: Match) {
|
||||||
team: 0,
|
team: 0,
|
||||||
healing: [],
|
healing: [],
|
||||||
metal: 0,
|
metal: 0,
|
||||||
angle: 0,
|
angle: 0
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
const dispenser = match.buildings.get(entity.entityIndex) as Dispenser;
|
const dispenser = match.buildings.get(entity.entityIndex) as Dispenser;
|
||||||
|
|
@ -312,7 +312,7 @@ function handleEntity(entity: PacketEntity, match: Match) {
|
||||||
rechargeDuration: 0,
|
rechargeDuration: 0,
|
||||||
timesUsed: 0,
|
timesUsed: 0,
|
||||||
angle: 0,
|
angle: 0,
|
||||||
yawToExit: 0,
|
yawToExit: 0
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
const teleporter = match.buildings.get(entity.entityIndex) as Teleporter;
|
const teleporter = match.buildings.get(entity.entityIndex) as Teleporter;
|
||||||
|
|
@ -372,7 +372,7 @@ function handleEntity(entity: PacketEntity, match: Match) {
|
||||||
score: 0,
|
score: 0,
|
||||||
team: 0,
|
team: 0,
|
||||||
totalScore: 0,
|
totalScore: 0,
|
||||||
damage: 0,
|
damage: 0
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
const playerResource = match.playerResources[playerId];
|
const playerResource = match.playerResources[playerId];
|
||||||
|
|
|
||||||
|
|
@ -6,6 +6,6 @@ export function handleSayText2(packet: SayText2Packet, match: Match) {
|
||||||
kind: packet.kind,
|
kind: packet.kind,
|
||||||
from: packet.from,
|
from: packet.from,
|
||||||
text: packet.text,
|
text: packet.text,
|
||||||
tick: match.tick,
|
tick: match.tick
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
import {CreateStringTablePacket, StringTablePacket, UpdateStringTablePacket} from '../Data/Packet';
|
import {CreateStringTablePacket, StringTablePacket, UpdateStringTablePacket} from '../Data/Packet';
|
||||||
import {StringTable, StringTableEntry} from '../Data/StringTable';
|
|
||||||
import {ParserState} from '../Data/ParserState';
|
import {ParserState} from '../Data/ParserState';
|
||||||
|
import {StringTable, StringTableEntry} from '../Data/StringTable';
|
||||||
|
|
||||||
export function handleStringTable(packet: CreateStringTablePacket, state: ParserState) {
|
export function handleStringTable(packet: CreateStringTablePacket, state: ParserState) {
|
||||||
handleTable(packet.table, state);
|
handleTable(packet.table, state);
|
||||||
|
|
@ -17,7 +17,6 @@ export function handleStringTableUpdate(packet: UpdateStringTablePacket, state:
|
||||||
handleStringTableEntries(updatedTable.name, packet.entries, state);
|
handleStringTableEntries(updatedTable.name, packet.entries, state);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
export function handleTable(table: StringTable, state: ParserState) {
|
export function handleTable(table: StringTable, state: ParserState) {
|
||||||
if (!state.getStringTable(table.name)) {
|
if (!state.getStringTable(table.name)) {
|
||||||
state.stringTables.push(table);
|
state.stringTables.push(table);
|
||||||
|
|
|
||||||
|
|
@ -1,14 +1,14 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {Header} from './Data/Header';
|
import {Header} from './Data/Header';
|
||||||
|
import {Message, MessageHandler, MessageType, PacketMessage} from './Data/Message';
|
||||||
|
import {Packet, PacketTypeId} from './Data/Packet';
|
||||||
|
import {ParserState} from './Data/ParserState';
|
||||||
import {ConsoleCmdHandler} from './Parser/Message/ConsoleCmd';
|
import {ConsoleCmdHandler} from './Parser/Message/ConsoleCmd';
|
||||||
import {DataTableHandler} from './Parser/Message/DataTable';
|
import {DataTableHandler} from './Parser/Message/DataTable';
|
||||||
import {PacketMessageHandler} from './Parser/Message/Packet';
|
import {PacketMessageHandler} from './Parser/Message/Packet';
|
||||||
import {StringTableHandler} from './Parser/Message/StringTable';
|
import {StringTableHandler} from './Parser/Message/StringTable';
|
||||||
import {UserCmdHandler} from './Parser/Message/UserCmd';
|
|
||||||
import {Packet, PacketTypeId} from './Data/Packet';
|
|
||||||
import {Message, MessageHandler, MessageType, PacketMessage} from './Data/Message';
|
|
||||||
import {ParserState} from './Data/ParserState';
|
|
||||||
import {SyncTickHandler} from './Parser/Message/SyncTick';
|
import {SyncTickHandler} from './Parser/Message/SyncTick';
|
||||||
|
import {UserCmdHandler} from './Parser/Message/UserCmd';
|
||||||
|
|
||||||
const messageHandlers: Map<MessageType, MessageHandler<Message>> = new Map<MessageType, MessageHandler<Message>>([
|
const messageHandlers: Map<MessageType, MessageHandler<Message>> = new Map<MessageType, MessageHandler<Message>>([
|
||||||
[MessageType.Sigon, PacketMessageHandler],
|
[MessageType.Sigon, PacketMessageHandler],
|
||||||
|
|
@ -47,7 +47,7 @@ export class Parser {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private * getMessages(): Iterable<Message> {
|
protected * getMessages(): Iterable<Message> {
|
||||||
while (true) {
|
while (true) {
|
||||||
const message = this.readMessage(this.stream, this.parserState);
|
const message = this.readMessage(this.stream, this.parserState);
|
||||||
if (message) {
|
if (message) {
|
||||||
|
|
@ -78,7 +78,7 @@ export class Parser {
|
||||||
duration: stream.readFloat32(),
|
duration: stream.readFloat32(),
|
||||||
ticks: stream.readInt32(),
|
ticks: stream.readInt32(),
|
||||||
frames: stream.readInt32(),
|
frames: stream.readInt32(),
|
||||||
sigon: stream.readInt32(),
|
sigon: stream.readInt32()
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -2,8 +2,8 @@ import {BitStream} from 'bit-buffer';
|
||||||
import {SendProp} from '../Data/SendProp';
|
import {SendProp} from '../Data/SendProp';
|
||||||
import {SendTable} from '../Data/SendTable';
|
import {SendTable} from '../Data/SendTable';
|
||||||
import {readBitVar, writeBitVar} from './readBitVar';
|
import {readBitVar, writeBitVar} from './readBitVar';
|
||||||
import {SendPropParser} from './SendPropParser';
|
|
||||||
import {SendPropEncoder} from './SendPropEncoder';
|
import {SendPropEncoder} from './SendPropEncoder';
|
||||||
|
import {SendPropParser} from './SendPropParser';
|
||||||
|
|
||||||
export function getEntityUpdate(sendTable: SendTable, stream: BitStream): SendProp[] {
|
export function getEntityUpdate(sendTable: SendTable, stream: BitStream): SendProp[] {
|
||||||
let index = -1;
|
let index = -1;
|
||||||
|
|
@ -29,13 +29,15 @@ export function encodeEntityUpdate(props: SendProp[], sendTable: SendTable, stre
|
||||||
let lastIndex = -1;
|
let lastIndex = -1;
|
||||||
for (const prop of props) {
|
for (const prop of props) {
|
||||||
stream.writeBoolean(true);
|
stream.writeBoolean(true);
|
||||||
const index = allProps.findIndex(propDef => propDef.fullName === prop.definition.fullName);
|
const index = allProps.findIndex((propDef) => propDef.fullName === prop.definition.fullName);
|
||||||
if (index === -1) {
|
if (index === -1) {
|
||||||
throw new Error(`Unknown definition for property ${prop.definition.fullName} in ${sendTable.name}`);
|
throw new Error(`Unknown definition for property ${prop.definition.fullName} in ${sendTable.name}`);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (index < lastIndex) {
|
if (index < lastIndex) {
|
||||||
throw new Error(`Property index not incremental while encoding ${prop.definition.fullName} after ${allProps[lastIndex].fullName} in ${sendTable.name} (current: ${index}, last: ${lastIndex})`);
|
throw new Error(`Property index not incremental while encoding` +
|
||||||
|
`${prop.definition.fullName} after ${allProps[lastIndex].fullName}` +
|
||||||
|
`in ${sendTable.name} (current: ${index}, last: ${lastIndex})`);
|
||||||
}
|
}
|
||||||
writeFieldIndex(index, stream, lastIndex);
|
writeFieldIndex(index, stream, lastIndex);
|
||||||
lastIndex = index;
|
lastIndex = index;
|
||||||
|
|
|
||||||
|
|
@ -1,14 +1,14 @@
|
||||||
|
import {BitStream} from 'bit-buffer';
|
||||||
|
import {TextEncoder} from 'text-encoding-shim';
|
||||||
|
import {ConsoleCmdMessage, MessageHandler, MessageType} from '../../Data/Message';
|
||||||
import {ConsoleCmdPacket} from '../../Data/Packet';
|
import {ConsoleCmdPacket} from '../../Data/Packet';
|
||||||
import {Parser} from './Parser';
|
import {Parser} from './Parser';
|
||||||
import {BitStream} from 'bit-buffer';
|
|
||||||
import {ConsoleCmdMessage, MessageHandler, MessageType} from '../../Data/Message';
|
|
||||||
import {TextEncoder} from 'text-encoding-shim';
|
|
||||||
|
|
||||||
export class ConsoleCmd extends Parser {
|
export class ConsoleCmd extends Parser {
|
||||||
public parse(): ConsoleCmdPacket[] {
|
public parse(): ConsoleCmdPacket[] {
|
||||||
return [{
|
return [{
|
||||||
packetType: 'consoleCmd',
|
packetType: 'consoleCmd',
|
||||||
command: this.stream.readUTF8String(),
|
command: this.stream.readUTF8String()
|
||||||
}];
|
}];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,8 +1,8 @@
|
||||||
|
import {BitStream} from 'bit-buffer';
|
||||||
|
import {DataTablesMessage, MessageHandler, MessageType} from '../../Data/Message';
|
||||||
import {SendPropDefinition, SendPropFlag, SendPropType} from '../../Data/SendPropDefinition';
|
import {SendPropDefinition, SendPropFlag, SendPropType} from '../../Data/SendPropDefinition';
|
||||||
import {SendTable} from '../../Data/SendTable';
|
import {SendTable} from '../../Data/SendTable';
|
||||||
import {ServerClass} from '../../Data/ServerClass';
|
import {ServerClass} from '../../Data/ServerClass';
|
||||||
import {DataTablesMessage, MessageHandler, MessageType} from '../../Data/Message';
|
|
||||||
import {BitStream} from 'bit-buffer';
|
|
||||||
|
|
||||||
export const DataTableHandler: MessageHandler<DataTablesMessage> = {
|
export const DataTableHandler: MessageHandler<DataTablesMessage> = {
|
||||||
parseMessage: (stream: BitStream) => {
|
parseMessage: (stream: BitStream) => {
|
||||||
|
|
@ -129,7 +129,7 @@ export const DataTableHandler: MessageHandler<DataTablesMessage> = {
|
||||||
tick,
|
tick,
|
||||||
rawData: messageStream,
|
rawData: messageStream,
|
||||||
tables,
|
tables,
|
||||||
serverClasses,
|
serverClasses
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
encodeMessage: (message, stream) => {
|
encodeMessage: (message, stream) => {
|
||||||
|
|
|
||||||
|
|
@ -1,4 +1,3 @@
|
||||||
import {make} from '../Packet/ParserGenerator';
|
|
||||||
import {EncodeBSPDecal, ParseBSPDecal} from '../Packet/BSPDecal';
|
import {EncodeBSPDecal, ParseBSPDecal} from '../Packet/BSPDecal';
|
||||||
import {EncodeClassInfo, ParseClassInfo} from '../Packet/ClassInfo';
|
import {EncodeClassInfo, ParseClassInfo} from '../Packet/ClassInfo';
|
||||||
import {EncodeCreateStringTable, ParseCreateStringTable} from '../Packet/CreateStringTable';
|
import {EncodeCreateStringTable, ParseCreateStringTable} from '../Packet/CreateStringTable';
|
||||||
|
|
@ -6,6 +5,7 @@ import {EncodeGameEvent, ParseGameEvent} from '../Packet/GameEvent';
|
||||||
import {EncodeGameEventList, ParseGameEventList} from '../Packet/GameEventList';
|
import {EncodeGameEventList, ParseGameEventList} from '../Packet/GameEventList';
|
||||||
import {EncodePacketEntities, ParsePacketEntities} from '../Packet/PacketEntities';
|
import {EncodePacketEntities, ParsePacketEntities} from '../Packet/PacketEntities';
|
||||||
import {PacketHandler} from '../Packet/Parser';
|
import {PacketHandler} from '../Packet/Parser';
|
||||||
|
import {make} from '../Packet/ParserGenerator';
|
||||||
import {EncodeParseSounds, ParseParseSounds} from '../Packet/ParseSounds';
|
import {EncodeParseSounds, ParseParseSounds} from '../Packet/ParseSounds';
|
||||||
import {EncodeSetConVar, ParseSetConVar} from '../Packet/SetConVar';
|
import {EncodeSetConVar, ParseSetConVar} from '../Packet/SetConVar';
|
||||||
import {EncodeTempEntities, ParseTempEntities} from '../Packet/TempEntities';
|
import {EncodeTempEntities, ParseTempEntities} from '../Packet/TempEntities';
|
||||||
|
|
@ -14,9 +14,9 @@ import {EncodeUserMessage, ParseUserMessage} from '../Packet/UserMessage';
|
||||||
import {EncodeVoiceData, ParseVoiceData} from '../Packet/VoiceData';
|
import {EncodeVoiceData, ParseVoiceData} from '../Packet/VoiceData';
|
||||||
import {EncodeVoiceInit, ParseVoiceInit} from '../Packet/VoiceInit';
|
import {EncodeVoiceInit, ParseVoiceInit} from '../Packet/VoiceInit';
|
||||||
|
|
||||||
import {Packet as IPacket, PacketTypeId} from '../../Data/Packet';
|
|
||||||
import {MessageHandler, MessageType, PacketMessage} from '../../Data/Message';
|
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
|
import {MessageHandler, MessageType, PacketMessage} from '../../Data/Message';
|
||||||
|
import {Packet as IPacket, PacketTypeId} from '../../Data/Packet';
|
||||||
import {ParserState} from '../../Data/ParserState';
|
import {ParserState} from '../../Data/ParserState';
|
||||||
import {Vector} from '../../Data/Vector';
|
import {Vector} from '../../Data/Vector';
|
||||||
|
|
||||||
|
|
@ -79,7 +79,7 @@ const handlers: PacketHandlerMap = new Map<PacketTypeId, PacketHandler<IPacket>>
|
||||||
[PacketTypeId.getCvarValue,
|
[PacketTypeId.getCvarValue,
|
||||||
make('getCvarValue', 'cookie{32}value{s}')],
|
make('getCvarValue', 'cookie{32}value{s}')],
|
||||||
[PacketTypeId.cmdKeyValues,
|
[PacketTypeId.cmdKeyValues,
|
||||||
make('cmdKeyValues', 'length{32}data{$length}')],
|
make('cmdKeyValues', 'length{32}data{$length}')]
|
||||||
]);
|
]);
|
||||||
|
|
||||||
export const PacketMessageHandler: MessageHandler<PacketMessage> = {
|
export const PacketMessageHandler: MessageHandler<PacketMessage> = {
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {Packet, PacketTypeId} from '../../Data/Packet';
|
|
||||||
import {MessageType} from '../../Data/Message';
|
import {MessageType} from '../../Data/Message';
|
||||||
|
import {Packet, PacketTypeId} from '../../Data/Packet';
|
||||||
import {ParserState} from '../../Data/ParserState';
|
import {ParserState} from '../../Data/ParserState';
|
||||||
|
|
||||||
export abstract class Parser {
|
export abstract class Parser {
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
import {StringTable as StringTableObject, StringTableEntry} from '../../Data/StringTable';
|
|
||||||
import {MessageHandler, MessageType, StringTablesMessage} from '../../Data/Message';
|
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
|
import {MessageHandler, MessageType, StringTablesMessage} from '../../Data/Message';
|
||||||
|
import {StringTable as StringTableObject, StringTableEntry} from '../../Data/StringTable';
|
||||||
|
|
||||||
export const StringTableHandler: MessageHandler<StringTablesMessage> = {
|
export const StringTableHandler: MessageHandler<StringTablesMessage> = {
|
||||||
parseMessage: (stream: BitStream) => {
|
parseMessage: (stream: BitStream) => {
|
||||||
|
|
@ -18,7 +18,7 @@ export const StringTableHandler: MessageHandler<StringTablesMessage> = {
|
||||||
const entryCount = messageStream.readUint16();
|
const entryCount = messageStream.readUint16();
|
||||||
for (let j = 0; j < entryCount; j++) {
|
for (let j = 0; j < entryCount; j++) {
|
||||||
const entry: StringTableEntry = {
|
const entry: StringTableEntry = {
|
||||||
text: messageStream.readUTF8String(),
|
text: messageStream.readUTF8String()
|
||||||
};
|
};
|
||||||
if (messageStream.readBoolean()) {
|
if (messageStream.readBoolean()) {
|
||||||
const extraDataLength = messageStream.readUint16();
|
const extraDataLength = messageStream.readUint16();
|
||||||
|
|
@ -40,7 +40,7 @@ export const StringTableHandler: MessageHandler<StringTablesMessage> = {
|
||||||
const table: StringTableObject = {
|
const table: StringTableObject = {
|
||||||
entries,
|
entries,
|
||||||
name: tableName,
|
name: tableName,
|
||||||
maxEntries: entryCount,
|
maxEntries: entryCount
|
||||||
};
|
};
|
||||||
|
|
||||||
if (messageStream.readBoolean()) {
|
if (messageStream.readBoolean()) {
|
||||||
|
|
@ -57,7 +57,7 @@ export const StringTableHandler: MessageHandler<StringTablesMessage> = {
|
||||||
type: MessageType.StringTables,
|
type: MessageType.StringTables,
|
||||||
tick,
|
tick,
|
||||||
rawData: messageStream,
|
rawData: messageStream,
|
||||||
tables,
|
tables
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
encodeMessage: (message, stream) => {
|
encodeMessage: (message, stream) => {
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,5 @@
|
||||||
import {MessageHandler, MessageType, SyncTickMessage} from '../../Data/Message';
|
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
|
import {MessageHandler, MessageType, SyncTickMessage} from '../../Data/Message';
|
||||||
|
|
||||||
export const SyncTickHandler: MessageHandler<SyncTickMessage> = {
|
export const SyncTickHandler: MessageHandler<SyncTickMessage> = {
|
||||||
parseMessage: (stream: BitStream) => {
|
parseMessage: (stream: BitStream) => {
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,5 @@
|
||||||
import {MessageHandler, MessageType, UserCmdMessage} from '../../Data/Message';
|
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
|
import {MessageHandler, MessageType, UserCmdMessage} from '../../Data/Message';
|
||||||
|
|
||||||
export const UserCmdHandler: MessageHandler<UserCmdMessage> = {
|
export const UserCmdHandler: MessageHandler<UserCmdMessage> = {
|
||||||
parseMessage: (stream: BitStream) => {
|
parseMessage: (stream: BitStream) => {
|
||||||
|
|
|
||||||
|
|
@ -1,8 +1,8 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {BSPDecalPacket} from '../../Data/Packet';
|
import {BSPDecalPacket} from '../../Data/Packet';
|
||||||
import {Vector} from '../../Data/Vector';
|
import {Vector} from '../../Data/Vector';
|
||||||
import {SendPropParser} from '../SendPropParser';
|
|
||||||
import {SendPropEncoder} from '../SendPropEncoder';
|
import {SendPropEncoder} from '../SendPropEncoder';
|
||||||
|
import {SendPropParser} from '../SendPropParser';
|
||||||
|
|
||||||
export function getVecCoord(stream: BitStream): Vector {
|
export function getVecCoord(stream: BitStream): Vector {
|
||||||
const hasX = stream.readBoolean();
|
const hasX = stream.readBoolean();
|
||||||
|
|
@ -12,7 +12,7 @@ export function getVecCoord(stream: BitStream): Vector {
|
||||||
return {
|
return {
|
||||||
x: hasX ? SendPropParser.readBitCoord(stream) : 0,
|
x: hasX ? SendPropParser.readBitCoord(stream) : 0,
|
||||||
y: hasY ? SendPropParser.readBitCoord(stream) : 0,
|
y: hasY ? SendPropParser.readBitCoord(stream) : 0,
|
||||||
z: hasZ ? SendPropParser.readBitCoord(stream) : 0,
|
z: hasZ ? SendPropParser.readBitCoord(stream) : 0
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -49,7 +49,7 @@ export function ParseBSPDecal(stream: BitStream): BSPDecalPacket { // 21: ParseB
|
||||||
textureIndex,
|
textureIndex,
|
||||||
entIndex,
|
entIndex,
|
||||||
modelIndex,
|
modelIndex,
|
||||||
lowPriority,
|
lowPriority
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -2,22 +2,21 @@ import {BitStream} from 'bit-buffer';
|
||||||
import {ClassInfoPacket} from '../../Data/Packet';
|
import {ClassInfoPacket} from '../../Data/Packet';
|
||||||
import {logBase2} from '../../Math';
|
import {logBase2} from '../../Math';
|
||||||
|
|
||||||
|
|
||||||
export function ParseClassInfo(stream: BitStream): ClassInfoPacket { // 10: classInfo
|
export function ParseClassInfo(stream: BitStream): ClassInfoPacket { // 10: classInfo
|
||||||
const count = stream.readUint16();
|
const count = stream.readUint16();
|
||||||
const create = stream.readBoolean();
|
const create = stream.readBoolean();
|
||||||
const entries: {
|
const entries: Array<{
|
||||||
classId: number;
|
classId: number;
|
||||||
className: string;
|
className: string;
|
||||||
dataTableName: string;
|
dataTableName: string;
|
||||||
}[] = [];
|
}> = [];
|
||||||
if (!create) {
|
if (!create) {
|
||||||
const bits = logBase2(count) + 1;
|
const bits = logBase2(count) + 1;
|
||||||
for (let i = 0; i < count; i++) {
|
for (let i = 0; i < count; i++) {
|
||||||
const entry = {
|
const entry = {
|
||||||
classId: stream.readBits(bits),
|
classId: stream.readBits(bits),
|
||||||
className: stream.readASCIIString(),
|
className: stream.readASCIIString(),
|
||||||
dataTableName: stream.readASCIIString(),
|
dataTableName: stream.readASCIIString()
|
||||||
};
|
};
|
||||||
entries.push(entry);
|
entries.push(entry);
|
||||||
}
|
}
|
||||||
|
|
@ -26,7 +25,7 @@ export function ParseClassInfo(stream: BitStream): ClassInfoPacket { // 10: clas
|
||||||
packetType: 'classInfo',
|
packetType: 'classInfo',
|
||||||
number: count,
|
number: count,
|
||||||
create,
|
create,
|
||||||
entries,
|
entries
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -53,14 +53,14 @@ export function ParseCreateStringTable(stream: BitStream): CreateStringTablePack
|
||||||
entries: [],
|
entries: [],
|
||||||
maxEntries,
|
maxEntries,
|
||||||
fixedUserDataSize: userDataSize,
|
fixedUserDataSize: userDataSize,
|
||||||
fixedUserDataSizeBits: userDataSizeBits,
|
fixedUserDataSizeBits: userDataSizeBits
|
||||||
};
|
};
|
||||||
|
|
||||||
table.entries = parseStringTableEntries(data, table, entityCount);
|
table.entries = parseStringTableEntries(data, table, entityCount);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
packetType: 'createStringTable',
|
packetType: 'createStringTable',
|
||||||
table: table,
|
table
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,7 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {
|
import {
|
||||||
GameEventDefinition, GameEventEntry,
|
GameEventDefinition, GameEventEntry,
|
||||||
GameEventValue, GameEventValueType,
|
GameEventValue, GameEventValueType
|
||||||
} from '../../Data/GameEvent';
|
} from '../../Data/GameEvent';
|
||||||
import {GameEvent, GameEventType, GameEventTypeIdMap, GameEventTypeMap} from '../../Data/GameEventTypes';
|
import {GameEvent, GameEventType, GameEventTypeIdMap, GameEventTypeMap} from '../../Data/GameEventTypes';
|
||||||
import {GameEventPacket} from '../../Data/Packet';
|
import {GameEventPacket} from '../../Data/Packet';
|
||||||
|
|
@ -19,7 +19,7 @@ function parseGameEvent<T extends GameEventType>(definition: GameEventDefinition
|
||||||
|
|
||||||
return {
|
return {
|
||||||
name,
|
name,
|
||||||
values,
|
values
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -98,7 +98,7 @@ export function ParseGameEvent(stream: BitStream, state: ParserState): GameEvent
|
||||||
|
|
||||||
return {
|
return {
|
||||||
packetType: 'gameEvent',
|
packetType: 'gameEvent',
|
||||||
event: event as GameEvent,
|
event: event as GameEvent
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,7 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {GameEventDefinition, GameEventEntry} from '../../Data/GameEvent';
|
import {GameEventDefinition, GameEventEntry} from '../../Data/GameEvent';
|
||||||
import {GameEventListPacket} from '../../Data/Packet';
|
|
||||||
import {GameEvent, GameEventType} from '../../Data/GameEventTypes';
|
import {GameEvent, GameEventType} from '../../Data/GameEventTypes';
|
||||||
|
import {GameEventListPacket} from '../../Data/Packet';
|
||||||
|
|
||||||
export function ParseGameEventList(stream: BitStream): GameEventListPacket { // 30: gameEventList
|
export function ParseGameEventList(stream: BitStream): GameEventListPacket { // 30: gameEventList
|
||||||
const s = stream.index;
|
const s = stream.index;
|
||||||
|
|
@ -18,19 +18,19 @@ export function ParseGameEventList(stream: BitStream): GameEventListPacket { //
|
||||||
while (type !== 0) {
|
while (type !== 0) {
|
||||||
entries.push({
|
entries.push({
|
||||||
type,
|
type,
|
||||||
name: stream.readASCIIString(),
|
name: stream.readASCIIString()
|
||||||
});
|
});
|
||||||
type = stream.readBits(3);
|
type = stream.readBits(3);
|
||||||
}
|
}
|
||||||
eventList.set(id, {
|
eventList.set(id, {
|
||||||
id,
|
id,
|
||||||
name,
|
name,
|
||||||
entries,
|
entries
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
return {
|
return {
|
||||||
packetType: 'gameEventList',
|
packetType: 'gameEventList',
|
||||||
eventList,
|
eventList
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,23 +1,23 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {PacketEntitiesPacket} from '../../Data/Packet';
|
import {PacketEntitiesPacket} from '../../Data/Packet';
|
||||||
import {EntityId, PacketEntity, PVS} from '../../Data/PacketEntity';
|
import {EntityId, PacketEntity, PVS} from '../../Data/PacketEntity';
|
||||||
|
import {getClassBits, getSendTable, ParserState} from '../../Data/ParserState';
|
||||||
import {SendProp} from '../../Data/SendProp';
|
import {SendProp} from '../../Data/SendProp';
|
||||||
import {encodeEntityUpdate, getEntityUpdate} from '../EntityDecoder';
|
import {encodeEntityUpdate, getEntityUpdate} from '../EntityDecoder';
|
||||||
import {readUBitVar, writeBitVar} from '../readBitVar';
|
import {readUBitVar, writeBitVar} from '../readBitVar';
|
||||||
import {getClassBits, getSendTable, ParserState} from '../../Data/ParserState';
|
|
||||||
|
|
||||||
const pvsMap = new Map([
|
const pvsMap = new Map([
|
||||||
[0, PVS.PRESERVE],
|
[0, PVS.PRESERVE],
|
||||||
[2, PVS.ENTER],
|
[2, PVS.ENTER],
|
||||||
[1, PVS.LEAVE],
|
[1, PVS.LEAVE],
|
||||||
[3, PVS.LEAVE + PVS.DELETE],
|
[3, PVS.LEAVE + PVS.DELETE]
|
||||||
]);
|
]);
|
||||||
|
|
||||||
const pvsReverseMap = new Map([
|
const pvsReverseMap = new Map([
|
||||||
[PVS.PRESERVE, 0],
|
[PVS.PRESERVE, 0],
|
||||||
[PVS.ENTER, 2],
|
[PVS.ENTER, 2],
|
||||||
[PVS.LEAVE, 1],
|
[PVS.LEAVE, 1],
|
||||||
[PVS.LEAVE + PVS.DELETE, 3],
|
[PVS.LEAVE + PVS.DELETE, 3]
|
||||||
]);
|
]);
|
||||||
|
|
||||||
function readPVSType(stream: BitStream): PVS {
|
function readPVSType(stream: BitStream): PVS {
|
||||||
|
|
@ -70,7 +70,9 @@ function readEnterPVS(stream: BitStream, entityId: EntityId, state: ParserState,
|
||||||
}
|
}
|
||||||
|
|
||||||
function writeEnterPVS(entity: PacketEntity, stream: BitStream, state: ParserState, baseLineIndex: number) {
|
function writeEnterPVS(entity: PacketEntity, stream: BitStream, state: ParserState, baseLineIndex: number) {
|
||||||
const serverClassId = state.serverClasses.findIndex(serverClass => serverClass && entity.serverClass.id === serverClass.id);
|
const serverClassId = state.serverClasses.findIndex(
|
||||||
|
(existingServerClass) => existingServerClass && entity.serverClass.id === existingServerClass.id
|
||||||
|
);
|
||||||
if (serverClassId === -1) {
|
if (serverClassId === -1) {
|
||||||
throw new Error(`Unknown server class ${entity.serverClass.name}(${entity.serverClass.id})`);
|
throw new Error(`Unknown server class ${entity.serverClass.name}(${entity.serverClass.id})`);
|
||||||
}
|
}
|
||||||
|
|
@ -100,8 +102,8 @@ function writeEnterPVS(entity: PacketEntity, stream: BitStream, state: ParserSta
|
||||||
// console.log(propsToEncode.map(prop => `${prop.definition.name}: ${prop.value}`));
|
// console.log(propsToEncode.map(prop => `${prop.definition.name}: ${prop.value}`));
|
||||||
|
|
||||||
const allProps = sendTable.flattenedProps;
|
const allProps = sendTable.flattenedProps;
|
||||||
propsToEncode.sort((a, b) => allProps.findIndex(propDef => propDef.fullName === a.definition.fullName) -
|
propsToEncode.sort((a, b) => allProps.findIndex((propDef) => propDef.fullName === a.definition.fullName) -
|
||||||
allProps.findIndex(propDef => propDef.fullName === b.definition.fullName));
|
allProps.findIndex((propDef) => propDef.fullName === b.definition.fullName));
|
||||||
|
|
||||||
encodeEntityUpdate(propsToEncode, sendTable, stream);
|
encodeEntityUpdate(propsToEncode, sendTable, stream);
|
||||||
}
|
}
|
||||||
|
|
@ -115,7 +117,11 @@ function getPacketEntityForExisting(entityId: EntityId, state: ParserState, pvs:
|
||||||
return new PacketEntity(serverClass, entityId, pvs);
|
return new PacketEntity(serverClass, entityId, pvs);
|
||||||
}
|
}
|
||||||
|
|
||||||
export function ParsePacketEntities(stream: BitStream, state: ParserState, skip: boolean = false): PacketEntitiesPacket { // 26: packetEntities
|
export function ParsePacketEntities(
|
||||||
|
stream: BitStream,
|
||||||
|
state: ParserState,
|
||||||
|
skip: boolean = false
|
||||||
|
): PacketEntitiesPacket { // 26: packetEntities
|
||||||
// https://github.com/skadistats/smoke/blob/master/smoke/replay/handler/svc_packetentities.pyx
|
// https://github.com/skadistats/smoke/blob/master/smoke/replay/handler/svc_packetentities.pyx
|
||||||
// https://github.com/StatsHelix/demoinfo/blob/3d28ea917c3d44d987b98bb8f976f1a3fcc19821/DemoInfo/DP/Handler/PacketEntitesHandler.cs
|
// https://github.com/StatsHelix/demoinfo/blob/3d28ea917c3d44d987b98bb8f976f1a3fcc19821/DemoInfo/DP/Handler/PacketEntitesHandler.cs
|
||||||
// https://github.com/StatsHelix/demoinfo/blob/3d28ea917c3d44d987b98bb8f976f1a3fcc19821/DemoInfo/DP/Entity.cs
|
// https://github.com/StatsHelix/demoinfo/blob/3d28ea917c3d44d987b98bb8f976f1a3fcc19821/DemoInfo/DP/Entity.cs
|
||||||
|
|
@ -186,7 +192,7 @@ export function ParsePacketEntities(stream: BitStream, state: ParserState, skip:
|
||||||
maxEntries,
|
maxEntries,
|
||||||
delta,
|
delta,
|
||||||
baseLine,
|
baseLine,
|
||||||
updatedBaseLine,
|
updatedBaseLine
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -6,8 +6,8 @@ export type Parser<P extends Packet> = (stream: BitStream, state?: ParserState,
|
||||||
export type Encoder<P extends Packet> = (packet: P, stream: BitStream, state?: ParserState) => void;
|
export type Encoder<P extends Packet> = (packet: P, stream: BitStream, state?: ParserState) => void;
|
||||||
|
|
||||||
export interface PacketHandler<P extends Packet> {
|
export interface PacketHandler<P extends Packet> {
|
||||||
parser: Parser<P>,
|
parser: Parser<P>;
|
||||||
encoder: Encoder<P>
|
encoder: Encoder<P>;
|
||||||
}
|
}
|
||||||
|
|
||||||
export const voidEncoder: Encoder<VoidPacket> = () => {
|
export const voidEncoder: Encoder<VoidPacket> = () => {
|
||||||
|
|
|
||||||
|
|
@ -1,15 +1,15 @@
|
||||||
|
import {BitStream} from 'bit-buffer';
|
||||||
import {PacketMapType, PacketType} from '../../Data/Packet';
|
import {PacketMapType, PacketType} from '../../Data/Packet';
|
||||||
import {Encoder, PacketHandler, Parser} from './Parser';
|
import {Encoder, PacketHandler, Parser} from './Parser';
|
||||||
import {BitStream} from 'bit-buffer';
|
|
||||||
|
|
||||||
export function make<T extends PacketType>(name: T, definition: string): PacketHandler<PacketMapType[T]> {
|
export function make<T extends PacketType>(name: T, definition: string): PacketHandler<PacketMapType[T]> {
|
||||||
const parts = definition.split('}');
|
const parts = definition.split('}');
|
||||||
const items = parts.map((part) => {
|
const items = parts.map((part) => {
|
||||||
return part.split('{');
|
return part.split('{');
|
||||||
}).filter(part => part[0]);
|
}).filter((part) => part[0]);
|
||||||
const parser: Parser<PacketMapType[T]> = (stream: BitStream) => {
|
const parser: Parser<PacketMapType[T]> = (stream: BitStream) => {
|
||||||
const result = {
|
const result = {
|
||||||
packetType: name,
|
packetType: name
|
||||||
};
|
};
|
||||||
try {
|
try {
|
||||||
for (const group of items) {
|
for (const group of items) {
|
||||||
|
|
|
||||||
|
|
@ -11,7 +11,7 @@ export function ParseSetConVar(stream: BitStream): SetConVarPacket { // 5: setco
|
||||||
}
|
}
|
||||||
return {
|
return {
|
||||||
packetType: 'setConVar',
|
packetType: 'setConVar',
|
||||||
vars,
|
vars
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,10 +1,10 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {TempEntitiesPacket} from '../../Data/Packet';
|
import {TempEntitiesPacket} from '../../Data/Packet';
|
||||||
import {PacketEntity, PVS} from '../../Data/PacketEntity';
|
import {PacketEntity, PVS} from '../../Data/PacketEntity';
|
||||||
|
import {getClassBits, getSendTable, ParserState} from '../../Data/ParserState';
|
||||||
|
import {DynamicBitStream} from '../../DynamicBitStream';
|
||||||
import {encodeEntityUpdate, getEntityUpdate} from '../EntityDecoder';
|
import {encodeEntityUpdate, getEntityUpdate} from '../EntityDecoder';
|
||||||
import {readVarInt, writeVarInt} from '../readBitVar';
|
import {readVarInt, writeVarInt} from '../readBitVar';
|
||||||
import {DynamicBitStream} from '../../DynamicBitStream';
|
|
||||||
import {getClassBits, getSendTable, ParserState} from '../../Data/ParserState';
|
|
||||||
|
|
||||||
export function ParseTempEntities(stream: BitStream, state: ParserState, skip: boolean = false): TempEntitiesPacket { // 10: classInfo
|
export function ParseTempEntities(stream: BitStream, state: ParserState, skip: boolean = false): TempEntitiesPacket { // 10: classInfo
|
||||||
const entityCount = stream.readUint8();
|
const entityCount = stream.readUint8();
|
||||||
|
|
@ -45,7 +45,7 @@ export function ParseTempEntities(stream: BitStream, state: ParserState, skip: b
|
||||||
|
|
||||||
return {
|
return {
|
||||||
packetType: 'tempEntities',
|
packetType: 'tempEntities',
|
||||||
entities,
|
entities
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -63,7 +63,7 @@ export function EncodeTempEntities(packet: TempEntitiesPacket, stream: BitStream
|
||||||
|
|
||||||
entityStream.writeBoolean(true);
|
entityStream.writeBoolean(true);
|
||||||
|
|
||||||
const classId = state.serverClasses.findIndex(serverClass => serverClass && serverClass.name === entity.serverClass.name) + 1;
|
const classId = state.serverClasses.findIndex((serverClass) => serverClass && serverClass.name === entity.serverClass.name) + 1;
|
||||||
entityStream.writeBits(classId, getClassBits(state));
|
entityStream.writeBits(classId, getClassBits(state));
|
||||||
|
|
||||||
const sendTable = getSendTable(state, entity.serverClass.dataTable);
|
const sendTable = getSendTable(state, entity.serverClass.dataTable);
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,7 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {UpdateStringTablePacket} from '../../Data/Packet';
|
import {UpdateStringTablePacket} from '../../Data/Packet';
|
||||||
import {encodeStringTableEntries, guessStringTableEntryLength, parseStringTableEntries} from '../StringTableParser';
|
|
||||||
import {ParserState} from '../../Data/ParserState';
|
import {ParserState} from '../../Data/ParserState';
|
||||||
|
import {encodeStringTableEntries, guessStringTableEntryLength, parseStringTableEntries} from '../StringTableParser';
|
||||||
|
|
||||||
export function ParseUpdateStringTable(stream: BitStream, state: ParserState): UpdateStringTablePacket { // 12: updateStringTable
|
export function ParseUpdateStringTable(stream: BitStream, state: ParserState): UpdateStringTablePacket { // 12: updateStringTable
|
||||||
const tableId = stream.readBits(5);
|
const tableId = stream.readBits(5);
|
||||||
|
|
@ -30,7 +30,7 @@ export function ParseUpdateStringTable(stream: BitStream, state: ParserState): U
|
||||||
export function EncodeUpdateStringTable(packet: UpdateStringTablePacket, stream: BitStream, state: ParserState) {
|
export function EncodeUpdateStringTable(packet: UpdateStringTablePacket, stream: BitStream, state: ParserState) {
|
||||||
stream.writeBits(packet.tableId, 5);
|
stream.writeBits(packet.tableId, 5);
|
||||||
|
|
||||||
const changedEntryCount = packet.entries.filter(entry => entry).length;
|
const changedEntryCount = packet.entries.filter((entry) => entry).length;
|
||||||
const multipleChanged = changedEntryCount > 1;
|
const multipleChanged = changedEntryCount > 1;
|
||||||
stream.writeBoolean(multipleChanged);
|
stream.writeBoolean(multipleChanged);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,15 +1,15 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {EncodeSayText2, ParseSayText2} from '../UserMessage/SayText2';
|
|
||||||
import {make} from './ParserGenerator';
|
|
||||||
import {PacketHandler} from './Parser';
|
|
||||||
import {
|
import {
|
||||||
UserMessageType,
|
|
||||||
UserMessagePacket,
|
|
||||||
UnknownUserMessagePacket,
|
|
||||||
UnknownUserMessageBasePacket,
|
UnknownUserMessageBasePacket,
|
||||||
UserMessageTypeMap,
|
UnknownUserMessagePacket,
|
||||||
UserMessagePacketTypeMap
|
UserMessagePacket,
|
||||||
|
UserMessagePacketTypeMap,
|
||||||
|
UserMessageType,
|
||||||
|
UserMessageTypeMap
|
||||||
} from '../../Data/UserMessage';
|
} from '../../Data/UserMessage';
|
||||||
|
import {EncodeSayText2, ParseSayText2} from '../UserMessage/SayText2';
|
||||||
|
import {PacketHandler} from './Parser';
|
||||||
|
import {make} from './ParserGenerator';
|
||||||
|
|
||||||
function unknownPacketHandler<T extends UnknownUserMessagePacket['packetType']>(packetType: T): PacketHandler<UserMessageTypeMap[T]> {
|
function unknownPacketHandler<T extends UnknownUserMessagePacket['packetType']>(packetType: T): PacketHandler<UserMessageTypeMap[T]> {
|
||||||
return {
|
return {
|
||||||
|
|
@ -28,7 +28,8 @@ function unknownPacketHandler<T extends UnknownUserMessagePacket['packetType']>(
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
const userMessageParsers: Map<UserMessageType, PacketHandler<UserMessagePacket>> = new Map<UserMessageType, PacketHandler<UserMessagePacket>>([
|
const userMessageParsers: Map<UserMessageType, PacketHandler<UserMessagePacket>> =
|
||||||
|
new Map<UserMessageType, PacketHandler<UserMessagePacket>>([
|
||||||
[UserMessageType.SayText2, {parser: ParseSayText2, encoder: EncodeSayText2}],
|
[UserMessageType.SayText2, {parser: ParseSayText2, encoder: EncodeSayText2}],
|
||||||
[UserMessageType.TextMsg, make('textMsg', 'destType{8}text{s}substitute1{s}substitute2{s}substitute3{s}substitute4{s}')],
|
[UserMessageType.TextMsg, make('textMsg', 'destType{8}text{s}substitute1{s}substitute2{s}substitute3{s}substitute4{s}')],
|
||||||
[UserMessageType.ResetHUD, make('resetHUD', 'data{8}')],
|
[UserMessageType.ResetHUD, make('resetHUD', 'data{8}')],
|
||||||
|
|
@ -36,7 +37,7 @@ const userMessageParsers: Map<UserMessageType, PacketHandler<UserMessagePacket>>
|
||||||
[UserMessageType.VoiceSubtitle, make('voiceSubtitle', 'client{8}menu{8}item{8}')],
|
[UserMessageType.VoiceSubtitle, make('voiceSubtitle', 'client{8}menu{8}item{8}')],
|
||||||
[UserMessageType.BreakModel_Pumpkin, unknownPacketHandler('breakModelPumpkin')],
|
[UserMessageType.BreakModel_Pumpkin, unknownPacketHandler('breakModelPumpkin')],
|
||||||
[UserMessageType.Shake, make('shake', 'command{8}amplitude{f32}frequency{f32}duration{f32}')]
|
[UserMessageType.Shake, make('shake', 'command{8}amplitude{f32}frequency{f32}duration{f32}')]
|
||||||
]);
|
]);
|
||||||
|
|
||||||
export function ParseUserMessage(stream: BitStream): UserMessagePacket { // 23: user message
|
export function ParseUserMessage(stream: BitStream): UserMessagePacket { // 23: user message
|
||||||
const s = stream.index;
|
const s = stream.index;
|
||||||
|
|
@ -50,7 +51,7 @@ export function ParseUserMessage(stream: BitStream): UserMessagePacket { // 23:
|
||||||
return {
|
return {
|
||||||
packetType: 'unknownUserMessage',
|
packetType: 'unknownUserMessage',
|
||||||
type,
|
type,
|
||||||
data: messageData,
|
data: messageData
|
||||||
};
|
};
|
||||||
} else {
|
} else {
|
||||||
return handler.parser(messageData);
|
return handler.parser(messageData);
|
||||||
|
|
|
||||||
|
|
@ -12,7 +12,7 @@ export function ParseVoiceData(stream: BitStream): VoiceDataPacket {
|
||||||
client,
|
client,
|
||||||
proximity,
|
proximity,
|
||||||
length,
|
length,
|
||||||
data,
|
data
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -12,7 +12,7 @@ export function ParseVoiceInit(stream: BitStream): VoiceInitPacket {
|
||||||
packetType: 'voiceInit',
|
packetType: 'voiceInit',
|
||||||
codec,
|
codec,
|
||||||
quality,
|
quality,
|
||||||
extraData,
|
extraData
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -27,9 +27,6 @@ export class SendPropParser {
|
||||||
}
|
}
|
||||||
|
|
||||||
public static readInt(propDefinition: SendPropDefinition, stream: BitStream) {
|
public static readInt(propDefinition: SendPropDefinition, stream: BitStream) {
|
||||||
if (!propDefinition.hasFlag) {
|
|
||||||
console.log(propDefinition, propDefinition.hasFlag);
|
|
||||||
}
|
|
||||||
if (propDefinition.hasFlag(SendPropFlag.SPROP_VARINT)) {
|
if (propDefinition.hasFlag(SendPropFlag.SPROP_VARINT)) {
|
||||||
return readVarInt(stream, !propDefinition.hasFlag(SendPropFlag.SPROP_UNSIGNED));
|
return readVarInt(stream, !propDefinition.hasFlag(SendPropFlag.SPROP_UNSIGNED));
|
||||||
} else {
|
} else {
|
||||||
|
|
|
||||||
|
|
@ -2,7 +2,12 @@ import {BitStream} from 'bit-buffer';
|
||||||
import {StringTable, StringTableEntry} from '../Data/StringTable';
|
import {StringTable, StringTableEntry} from '../Data/StringTable';
|
||||||
import {logBase2} from '../Math';
|
import {logBase2} from '../Math';
|
||||||
|
|
||||||
export function parseStringTableEntries(stream: BitStream, table: StringTable, entryCount: number, existingEntries: StringTableEntry[] = []): StringTableEntry[] {
|
export function parseStringTableEntries(
|
||||||
|
stream: BitStream,
|
||||||
|
table: StringTable,
|
||||||
|
entryCount: number,
|
||||||
|
existingEntries: StringTableEntry[] = []
|
||||||
|
): StringTableEntry[] {
|
||||||
const entryBits = logBase2(table.maxEntries);
|
const entryBits = logBase2(table.maxEntries);
|
||||||
const entries: StringTableEntry[] = [];
|
const entries: StringTableEntry[] = [];
|
||||||
let lastEntry = -1;
|
let lastEntry = -1;
|
||||||
|
|
@ -64,7 +69,7 @@ export function parseStringTableEntries(stream: BitStream, table: StringTable, e
|
||||||
} else {
|
} else {
|
||||||
entries[entryIndex] = {
|
entries[entryIndex] = {
|
||||||
text: value,
|
text: value,
|
||||||
extraData: userData,
|
extraData: userData
|
||||||
};
|
};
|
||||||
history.push(entries[entryIndex]);
|
history.push(entries[entryIndex]);
|
||||||
}
|
}
|
||||||
|
|
@ -90,7 +95,7 @@ export function guessStringTableEntryLength(table: StringTable, entries: StringT
|
||||||
|
|
||||||
export function encodeStringTableEntries(stream: BitStream, table: StringTable, entries: StringTableEntry[]) {
|
export function encodeStringTableEntries(stream: BitStream, table: StringTable, entries: StringTableEntry[]) {
|
||||||
const entryBits = logBase2(table.maxEntries);
|
const entryBits = logBase2(table.maxEntries);
|
||||||
let lastIndex = -1;
|
const lastIndex = -1;
|
||||||
for (let i = 0; i < entries.length; i++) {
|
for (let i = 0; i < entries.length; i++) {
|
||||||
if (entries[i]) {
|
if (entries[i]) {
|
||||||
const entry = entries[i];
|
const entry = entries[i];
|
||||||
|
|
|
||||||
|
|
@ -49,7 +49,7 @@ export function ParseSayText2(stream: BitStream): SayText2Packet { // 4: ParseSa
|
||||||
raw,
|
raw,
|
||||||
kind,
|
kind,
|
||||||
from,
|
from,
|
||||||
text,
|
text
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,20 +1,20 @@
|
||||||
import * as assert from 'assert';
|
import * as assert from 'assert';
|
||||||
import {readFileSync, createWriteStream, createReadStream} from 'fs';
|
|
||||||
import {Demo} from '../../Demo';
|
|
||||||
import {Packet} from '../../Data/Packet';
|
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
|
import {createReadStream, createWriteStream, readFileSync} from 'fs';
|
||||||
import * as split2 from 'split2';
|
import * as split2 from 'split2';
|
||||||
import {createUnzip, createGunzip} from 'zlib';
|
|
||||||
import {PassThrough} from 'stream';
|
import {PassThrough} from 'stream';
|
||||||
|
import {createGunzip, createUnzip} from 'zlib';
|
||||||
|
import {Packet} from '../../Data/Packet';
|
||||||
import {EntityId, PVS} from '../../Data/PacketEntity';
|
import {EntityId, PVS} from '../../Data/PacketEntity';
|
||||||
import {SendPropValue} from '../../Data/SendProp';
|
import {SendPropValue} from '../../Data/SendProp';
|
||||||
|
import {Demo} from '../../Demo';
|
||||||
|
|
||||||
interface ResultData {
|
interface ResultData {
|
||||||
tick: number,
|
tick: number;
|
||||||
serverClass: string,
|
serverClass: string;
|
||||||
id: EntityId,
|
id: EntityId;
|
||||||
props: {[propName: string]: SendPropValue},
|
props: {[propName: string]: SendPropValue};
|
||||||
pvs: PVS
|
pvs: PVS;
|
||||||
}
|
}
|
||||||
|
|
||||||
function writeEntities(name: string) {
|
function writeEntities(name: string) {
|
||||||
|
|
@ -48,7 +48,7 @@ function* getResultData(packets: Iterable<Packet>): IterableIterator<ResultData>
|
||||||
entityProps[`${prop.definition.name}`] = prop.value;
|
entityProps[`${prop.definition.name}`] = prop.value;
|
||||||
}
|
}
|
||||||
yield {
|
yield {
|
||||||
tick: tick,
|
tick,
|
||||||
serverClass: entity.serverClass.name,
|
serverClass: entity.serverClass.name,
|
||||||
id: entity.entityIndex,
|
id: entity.entityIndex,
|
||||||
props: entityProps,
|
props: entityProps,
|
||||||
|
|
@ -82,7 +82,7 @@ function testEntities(name: string, entityCount: number) {
|
||||||
assert.equal(parsed, entityCount, 'unexpected number of entities');
|
assert.equal(parsed, entityCount, 'unexpected number of entities');
|
||||||
|
|
||||||
resolve();
|
resolve();
|
||||||
}).on('error', err => {
|
}).on('error', (err) => {
|
||||||
reject(err);
|
reject(err);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,7 @@
|
||||||
import * as assert from 'assert';
|
import * as assert from 'assert';
|
||||||
|
import {BitStream} from 'bit-buffer';
|
||||||
import {readFileSync} from 'fs';
|
import {readFileSync} from 'fs';
|
||||||
import {Demo} from '../../Demo';
|
import {Demo} from '../../Demo';
|
||||||
import {BitStream} from 'bit-buffer';
|
|
||||||
|
|
||||||
function testDemo(name: string, fastMode: boolean = false) {
|
function testDemo(name: string, fastMode: boolean = false) {
|
||||||
const target = JSON.parse(readFileSync(`${__dirname}/../data/${name}.json`, 'utf8'));
|
const target = JSON.parse(readFileSync(`${__dirname}/../data/${name}.json`, 'utf8'));
|
||||||
|
|
|
||||||
|
|
@ -1,39 +1,39 @@
|
||||||
import {PacketEntity, PVS} from '../../../Data/PacketEntity';
|
|
||||||
import {ServerClass} from '../../../Data/ServerClass';
|
|
||||||
import {hydrateEntity, propDataDefinition} from '../Parser/Packet/hydrate';
|
|
||||||
import {SendProp} from '../../../Data/SendProp';
|
|
||||||
import * as assert from 'assert';
|
import * as assert from 'assert';
|
||||||
import {readFileSync} from 'fs';
|
import {readFileSync} from 'fs';
|
||||||
|
import {PacketEntity, PVS} from '../../../Data/PacketEntity';
|
||||||
|
import {SendProp} from '../../../Data/SendProp';
|
||||||
|
import {ServerClass} from '../../../Data/ServerClass';
|
||||||
|
import {hydrateEntity, propDataDefinition} from '../Parser/Packet/hydrate';
|
||||||
|
|
||||||
const serverClass = new ServerClass(241, 'CTFPlayer', 'DT_TFPlayer');
|
const serverClass = new ServerClass(241, 'CTFPlayer', 'DT_TFPlayer');
|
||||||
const playerBaseLineData = JSON.parse(readFileSync(__dirname + '/../../data/packetEntitiesPlayerBaseline.json', 'utf8'));
|
const playerBaseLineData = JSON.parse(readFileSync(__dirname + '/../../data/packetEntitiesPlayerBaseline.json', 'utf8'));
|
||||||
const playerEntityData = JSON.parse(readFileSync(__dirname + '/../../data/packetEntitiesPlayerEntity.json', 'utf8'));
|
const playerEntityData = JSON.parse(readFileSync(__dirname + '/../../data/packetEntitiesPlayerEntity.json', 'utf8'));
|
||||||
|
|
||||||
const definition1 = propDataDefinition({
|
const definition1 = propDataDefinition({
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'm_flDucktime',
|
name: 'm_flDucktime',
|
||||||
'flags': 1032,
|
flags: 1032,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 2047.5,
|
highValue: 2047.5,
|
||||||
'bitCount': 12,
|
bitCount: 12,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_Local'
|
ownerTableName: 'DT_Local'
|
||||||
});
|
});
|
||||||
const definition2 = propDataDefinition({
|
const definition2 = propDataDefinition({
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'm_flFallVelocity',
|
name: 'm_flFallVelocity',
|
||||||
'flags': 1024,
|
flags: 1024,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': -4096,
|
lowValue: -4096,
|
||||||
'highValue': 4096,
|
highValue: 4096,
|
||||||
'bitCount': 17,
|
bitCount: 17,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_Local'
|
ownerTableName: 'DT_Local'
|
||||||
});
|
});
|
||||||
|
|
||||||
suite('PacketEntity', () => {
|
suite('PacketEntity', () => {
|
||||||
|
|
|
||||||
|
|
@ -1,8 +1,8 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder} from '../Packet/PacketTest';
|
|
||||||
import {ConsoleCmdHandler} from '../../../../Parser/Message/ConsoleCmd';
|
|
||||||
import {ParserState} from '../../../../Data/ParserState';
|
|
||||||
import {MessageType} from '../../../../Data/Message';
|
import {MessageType} from '../../../../Data/Message';
|
||||||
|
import {ParserState} from '../../../../Data/ParserState';
|
||||||
|
import {ConsoleCmdHandler} from '../../../../Parser/Message/ConsoleCmd';
|
||||||
|
import {assertEncoder} from '../Packet/PacketTest';
|
||||||
|
|
||||||
function parse(stream) {
|
function parse(stream) {
|
||||||
const result = ConsoleCmdHandler.parseMessage(stream, new ParserState());
|
const result = ConsoleCmdHandler.parseMessage(stream, new ParserState());
|
||||||
|
|
|
||||||
|
|
@ -1,21 +1,26 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
|
||||||
import {assertEncoder, assertParser, getStream} from '../Packet/PacketTest';
|
|
||||||
import {readFileSync} from 'fs';
|
|
||||||
import {ParserState} from '../../../../Data/ParserState';
|
|
||||||
import {gunzipSync} from 'zlib';
|
|
||||||
import {DataTableHandler} from '../../../../Parser/Message/DataTable';
|
|
||||||
import {DataTablesMessage} from '../../../../Data/Message';
|
|
||||||
import {hydrateTable} from '../Packet/hydrate';
|
|
||||||
import {ServerClass} from '../../../../Data/ServerClass';
|
|
||||||
import * as assert from 'assert';
|
import * as assert from 'assert';
|
||||||
|
import {BitStream} from 'bit-buffer';
|
||||||
|
import {readFileSync} from 'fs';
|
||||||
|
import {gunzipSync} from 'zlib';
|
||||||
|
import {DataTablesMessage} from '../../../../Data/Message';
|
||||||
|
import {ParserState} from '../../../../Data/ParserState';
|
||||||
|
import {ServerClass} from '../../../../Data/ServerClass';
|
||||||
|
import {DataTableHandler} from '../../../../Parser/Message/DataTable';
|
||||||
|
import {hydrateTable} from '../Packet/hydrate';
|
||||||
|
import {assertEncoder, assertParser, getStream} from '../Packet/PacketTest';
|
||||||
|
|
||||||
const data = Array.from(readFileSync(__dirname + '/../../../data/dataTableData.bin').values());
|
const data = Array.from(readFileSync(__dirname + '/../../../data/dataTableData.bin').values());
|
||||||
const expectedRaw = JSON.parse(gunzipSync(readFileSync(__dirname + '/../../../data/dataTableResult.json.gz')).toString('utf8')) as DataTablesMessage;
|
const expectedRaw = JSON.parse(
|
||||||
|
gunzipSync(
|
||||||
|
readFileSync(__dirname + '/../../../data/dataTableResult.json.gz'
|
||||||
|
)
|
||||||
|
).toString('utf8')
|
||||||
|
) as DataTablesMessage;
|
||||||
|
|
||||||
const expected = {
|
const expected = {
|
||||||
type: expectedRaw.type,
|
type: expectedRaw.type,
|
||||||
tick: expectedRaw.tick,
|
tick: expectedRaw.tick,
|
||||||
serverClasses: expectedRaw.serverClasses.map(serverClass => new ServerClass(serverClass.id, serverClass.name, serverClass.dataTable)),
|
serverClasses: expectedRaw.serverClasses.map((serverClass) => new ServerClass(serverClass.id, serverClass.name, serverClass.dataTable)),
|
||||||
tables: expectedRaw.tables.map(hydrateTable)
|
tables: expectedRaw.tables.map(hydrateTable)
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,9 +1,9 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from '../Packet/PacketTest';
|
|
||||||
import {readFileSync} from 'fs';
|
import {readFileSync} from 'fs';
|
||||||
import {PacketMessageHandler} from '../../../../Parser/Message/Packet';
|
|
||||||
import {ParserState} from '../../../../Data/ParserState';
|
|
||||||
import {PacketTypeId} from '../../../../Data/Packet';
|
import {PacketTypeId} from '../../../../Data/Packet';
|
||||||
|
import {ParserState} from '../../../../Data/ParserState';
|
||||||
|
import {PacketMessageHandler} from '../../../../Parser/Message/Packet';
|
||||||
|
import {assertEncoder, assertParser, getStream} from '../Packet/PacketTest';
|
||||||
|
|
||||||
const data = Object.values(JSON.parse(readFileSync(__dirname + '/../../../data/packetMessageData.json', 'utf8')));
|
const data = Object.values(JSON.parse(readFileSync(__dirname + '/../../../data/packetMessageData.json', 'utf8')));
|
||||||
const expected = JSON.parse(readFileSync(__dirname + '/../../../data/packetMessageResult.json', 'utf8'));
|
const expected = JSON.parse(readFileSync(__dirname + '/../../../data/packetMessageResult.json', 'utf8'));
|
||||||
|
|
@ -14,7 +14,7 @@ const getParserState = (fastMode) => {
|
||||||
state.skippedPackets = fastMode ? [
|
state.skippedPackets = fastMode ? [
|
||||||
PacketTypeId.packetEntities,
|
PacketTypeId.packetEntities,
|
||||||
PacketTypeId.tempEntities,
|
PacketTypeId.tempEntities,
|
||||||
PacketTypeId.entityMessage,
|
PacketTypeId.entityMessage
|
||||||
] : [];
|
] : [];
|
||||||
return state;
|
return state;
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -1,18 +1,18 @@
|
||||||
import {StringTable, StringTableEntry} from '../../../../Data/StringTable';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {readFileSync} from 'fs';
|
import {readFileSync} from 'fs';
|
||||||
import {ParserState} from '../../../../Data/ParserState';
|
import {ParserState} from '../../../../Data/ParserState';
|
||||||
|
import {StringTable, StringTableEntry} from '../../../../Data/StringTable';
|
||||||
import {StringTableHandler} from '../../../../Parser/Message/StringTable';
|
import {StringTableHandler} from '../../../../Parser/Message/StringTable';
|
||||||
import {assertEncoder, assertParser, getStream} from '../Packet/PacketTest';
|
import {assertEncoder, assertParser, getStream} from '../Packet/PacketTest';
|
||||||
import {BitStream} from 'bit-buffer';
|
|
||||||
|
|
||||||
const encodeEntry = (entry: StringTableEntry) => {
|
const encodeEntry = (entry: StringTableEntry) => {
|
||||||
const encodeEntry: any = {
|
const result: any = {
|
||||||
text: entry.text,
|
text: entry.text
|
||||||
};
|
};
|
||||||
if (entry.extraData) {
|
if (entry.extraData) {
|
||||||
encodeEntry.extraData = Array.from(entry.extraData.readArrayBuffer(Math.ceil(entry.extraData.length / 8)).values());
|
result.extraData = Array.from(entry.extraData.readArrayBuffer(Math.ceil(entry.extraData.length / 8)).values());
|
||||||
}
|
}
|
||||||
return encodeEntry;
|
return result;
|
||||||
};
|
};
|
||||||
const encodeTables = (tables) => {
|
const encodeTables = (tables) => {
|
||||||
return tables.map((table) => {
|
return tables.map((table) => {
|
||||||
|
|
@ -27,13 +27,13 @@ const encodeTables = (tables) => {
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
const decodeEntry = (entry) => {
|
const decodeEntry = (entry) => {
|
||||||
const decodeEntry: any = {
|
const result: any = {
|
||||||
text: entry.text,
|
text: entry.text
|
||||||
};
|
};
|
||||||
if (entry.extraData) {
|
if (entry.extraData) {
|
||||||
decodeEntry.extraData = getStream(entry.extraData);
|
result.extraData = getStream(entry.extraData);
|
||||||
}
|
}
|
||||||
return decodeEntry;
|
return result;
|
||||||
};
|
};
|
||||||
const decodeTables = (tables) => {
|
const decodeTables = (tables) => {
|
||||||
return tables.map((table) => {
|
return tables.map((table) => {
|
||||||
|
|
@ -62,7 +62,6 @@ const expected = {
|
||||||
rawData: getStream('')
|
rawData: getStream('')
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
const getParserState = () => {
|
const getParserState = () => {
|
||||||
return new ParserState();
|
return new ParserState();
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -1,11 +1,11 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
|
||||||
import {
|
import {
|
||||||
EncodeBSPDecal, encodeVecCoord, getVecCoord,
|
EncodeBSPDecal, encodeVecCoord, getVecCoord,
|
||||||
ParseBSPDecal
|
ParseBSPDecal
|
||||||
} from '../../../../Parser/Packet/BSPDecal';
|
} from '../../../../Parser/Packet/BSPDecal';
|
||||||
import {SendPropParser} from '../../../../Parser/SendPropParser';
|
|
||||||
import {SendPropEncoder} from '../../../../Parser/SendPropEncoder';
|
import {SendPropEncoder} from '../../../../Parser/SendPropEncoder';
|
||||||
|
import {SendPropParser} from '../../../../Parser/SendPropParser';
|
||||||
|
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
||||||
|
|
||||||
const data = [239, 236, 208, 85, 33, 127, 128, 9, 8];
|
const data = [239, 236, 208, 85, 33, 127, 128, 9, 8];
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
|
||||||
import {EncodeClassInfo, ParseClassInfo} from '../../../../Parser/Packet/ClassInfo';
|
import {EncodeClassInfo, ParseClassInfo} from '../../../../Parser/Packet/ClassInfo';
|
||||||
|
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
||||||
|
|
||||||
suite('ClassInfo', () => {
|
suite('ClassInfo', () => {
|
||||||
test('Parse classInfo', () => {
|
test('Parse classInfo', () => {
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
|
||||||
import {EncodeCreateStringTable, ParseCreateStringTable} from '../../../../Parser/Packet/CreateStringTable';
|
import {EncodeCreateStringTable, ParseCreateStringTable} from '../../../../Parser/Packet/CreateStringTable';
|
||||||
|
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
||||||
|
|
||||||
const exampleData = [
|
const exampleData = [
|
||||||
100,
|
100,
|
||||||
|
|
@ -80,7 +80,6 @@ const examplePacket2 = {
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
suite('CreateStringTable', () => {
|
suite('CreateStringTable', () => {
|
||||||
test('Parse createStringTable', () => {
|
test('Parse createStringTable', () => {
|
||||||
assertParser(ParseCreateStringTable, getStream(exampleData), examplePacket, 388);
|
assertParser(ParseCreateStringTable, getStream(exampleData), examplePacket, 388);
|
||||||
|
|
|
||||||
|
|
@ -1,15 +1,15 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
|
||||||
import {readFileSync} from 'fs';
|
import {readFileSync} from 'fs';
|
||||||
import {encodeEntityUpdate, getEntityUpdate} from '../../../../Parser/EntityDecoder';
|
|
||||||
import {SendProp, SendPropValue} from '../../../../Data/SendProp';
|
import {SendProp, SendPropValue} from '../../../../Data/SendProp';
|
||||||
import {SendPropType} from '../../../../Data/SendPropDefinition';
|
import {SendPropType} from '../../../../Data/SendPropDefinition';
|
||||||
|
import {encodeEntityUpdate, getEntityUpdate} from '../../../../Parser/EntityDecoder';
|
||||||
import {SendPropEncoder} from '../../../../Parser/SendPropEncoder';
|
import {SendPropEncoder} from '../../../../Parser/SendPropEncoder';
|
||||||
import {SendPropParser} from '../../../../Parser/SendPropParser';
|
import {SendPropParser} from '../../../../Parser/SendPropParser';
|
||||||
import {hydrateEntity, hydrateTable} from './hydrate';
|
import {hydrateEntity, hydrateTable} from './hydrate';
|
||||||
|
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
||||||
|
|
||||||
const data = [
|
// tslint:disable-next-line
|
||||||
9, 128, 64, 64, 64, 64, 0, 0, 0, 0, 0, 16, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 36, 0, 64, 0, 1, 128, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 64, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 32, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 136, 0, 128, 0, 0, 8, 0, 128, 0, 0, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 4, 2, 64, 0, 32, 0, 16, 0, 32, 240, 255, 255, 255, 31, 0, 2, 32, 48, 0, 128, 0, 0, 4, 254, 255, 127, 224, 255, 255, 7, 254, 255, 127, 0, 8, 64, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 128, 0, 64, 64, 64, 64, 0, 32, 224, 136, 10, 248, 91, 2, 63, 18, 8, 40, 38, 3, 250, 163, 192, 126, 7, 2, 2, 0, 0, 0, 0, 1, 0, 0, 0, 128, 0, 0, 0, 224, 111, 0, 0, 0, 0, 32, 192, 129, 172, 140, 46, 44, 141, 237, 133, 172, 140, 46, 44, 141, 109, 14, 78, 46, 141, 174, 108, 238, 107, 46, 236, 174, 45, 141, 141, 45, 0];
|
const data = [9, 128, 64, 64, 64, 64, 0, 0, 0, 0, 0, 16, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 36, 0, 64, 0, 1, 128, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 64, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 32, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 16, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 136, 0, 128, 0, 0, 8, 0, 128, 0, 0, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 4, 2, 64, 0, 32, 0, 16, 0, 32, 240, 255, 255, 255, 31, 0, 2, 32, 48, 0, 128, 0, 0, 4, 254, 255, 127, 224, 255, 255, 7, 254, 255, 127, 0, 8, 64, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 128, 0, 64, 64, 64, 64, 0, 32, 224, 136, 10, 248, 91, 2, 63, 18, 8, 40, 38, 3, 250, 163, 192, 126, 7, 2, 2, 0, 0, 0, 0, 1, 0, 0, 0, 128, 0, 0, 0, 224, 111, 0, 0, 0, 0, 32, 192, 129, 172, 140, 46, 44, 141, 237, 133, 172, 140, 46, 44, 141, 109, 14, 78, 46, 141, 174, 108, 238, 107, 46, 236, 174, 45, 141, 141, 45, 0];
|
||||||
|
|
||||||
const entityData = JSON.parse(readFileSync(__dirname + '/../../../data/worldEntity.json', 'utf8'));
|
const entityData = JSON.parse(readFileSync(__dirname + '/../../../data/worldEntity.json', 'utf8'));
|
||||||
const sendTableData = JSON.parse(readFileSync(__dirname + '/../../../data/sendTableDTWorld.json', 'utf8'));
|
const sendTableData = JSON.parse(readFileSync(__dirname + '/../../../data/sendTableDTWorld.json', 'utf8'));
|
||||||
|
|
@ -24,15 +24,14 @@ export function encodeUpdate(props: SendProp[], stream: BitStream) {
|
||||||
encodeEntityUpdate(props, sendTable, stream);
|
encodeEntityUpdate(props, sendTable, stream);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
function encodeProp(prop: SendProp) {
|
function encodeProp(prop: SendProp) {
|
||||||
return function (value: SendPropValue, stream: BitStream) {
|
return (value: SendPropValue, stream: BitStream) => {
|
||||||
return SendPropEncoder.encode(value, prop.definition, stream);
|
return SendPropEncoder.encode(value, prop.definition, stream);
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
function decodeProp(prop: SendProp) {
|
function decodeProp(prop: SendProp) {
|
||||||
return function (stream: BitStream) {
|
return (stream: BitStream) => {
|
||||||
return SendPropParser.decode(prop.definition, stream);
|
return SendPropParser.decode(prop.definition, stream);
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
@ -41,7 +40,7 @@ suite('Entity Decoder', () => {
|
||||||
test('Encode sendProps', () => {
|
test('Encode sendProps', () => {
|
||||||
for (const prop of entity.props) {
|
for (const prop of entity.props) {
|
||||||
if (prop.value !== null) {
|
if (prop.value !== null) {
|
||||||
assertEncoder(decodeProp(prop), encodeProp(prop), prop.value, 0, ` for ${SendPropType[prop.definition.type]} with flags ${prop.definition.allFlags}`);
|
assertEncoder(decodeProp(prop), encodeProp(prop), prop.value, 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
|
||||||
|
|
@ -1,9 +1,9 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
|
||||||
import {readFileSync} from 'fs';
|
import {readFileSync} from 'fs';
|
||||||
import {EncodeGameEventList, ParseGameEventList} from '../../../../Parser/Packet/GameEventList';
|
|
||||||
import {GameEventListPacket} from '../../../../Data/Packet';
|
|
||||||
import {GameEvent} from '../../../../Data/GameEventTypes';
|
import {GameEvent} from '../../../../Data/GameEventTypes';
|
||||||
|
import {GameEventListPacket} from '../../../../Data/Packet';
|
||||||
|
import {EncodeGameEventList, ParseGameEventList} from '../../../../Parser/Packet/GameEventList';
|
||||||
|
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
||||||
|
|
||||||
const data = JSON.parse(readFileSync(__dirname + '/../../../data/gameEventListData.json', 'utf8'));
|
const data = JSON.parse(readFileSync(__dirname + '/../../../data/gameEventListData.json', 'utf8'));
|
||||||
const expectedSource = JSON.parse(readFileSync(__dirname + '/../../../data/gameEventList.json', 'utf8'));
|
const expectedSource = JSON.parse(readFileSync(__dirname + '/../../../data/gameEventList.json', 'utf8'));
|
||||||
|
|
@ -14,71 +14,71 @@ const expected = {
|
||||||
};
|
};
|
||||||
|
|
||||||
const eventList: GameEventListPacket = {
|
const eventList: GameEventListPacket = {
|
||||||
'packetType': 'gameEventList',
|
packetType: 'gameEventList',
|
||||||
'eventList': new Map([
|
eventList: new Map([
|
||||||
[0, {
|
[0, {
|
||||||
'id': 0,
|
id: 0,
|
||||||
'name': 'server_spawn' as GameEvent['name'],
|
name: 'server_spawn' as GameEvent['name'],
|
||||||
'entries': [
|
entries: [
|
||||||
{
|
{
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'hostname'
|
name: 'hostname'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'address'
|
name: 'address'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 3,
|
type: 3,
|
||||||
'name': 'ip'
|
name: 'ip'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 4,
|
type: 4,
|
||||||
'name': 'port'
|
name: 'port'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'game'
|
name: 'game'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'mapname'
|
name: 'mapname'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 3,
|
type: 3,
|
||||||
'name': 'maxplayers'
|
name: 'maxplayers'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'os'
|
name: 'os'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 6,
|
type: 6,
|
||||||
'name': 'dedicated'
|
name: 'dedicated'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 6,
|
type: 6,
|
||||||
'name': 'password'
|
name: 'password'
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}],
|
}],
|
||||||
[1, {
|
[1, {
|
||||||
'id': 1,
|
id: 1,
|
||||||
'name': 'server_changelevel_failed' as GameEvent['name'],
|
name: 'server_changelevel_failed' as GameEvent['name'],
|
||||||
'entries': [
|
entries: [
|
||||||
{
|
{
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'levelname'
|
name: 'levelname'
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}],
|
}],
|
||||||
[2, {
|
[2, {
|
||||||
'id': 2,
|
id: 2,
|
||||||
'name': 'server_shutdown' as GameEvent['name'],
|
name: 'server_shutdown' as GameEvent['name'],
|
||||||
'entries': [
|
entries: [
|
||||||
{
|
{
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'reason'
|
name: 'reason'
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}]
|
}]
|
||||||
|
|
|
||||||
|
|
@ -1,9 +1,9 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
|
||||||
import {EncodeGameEvent, ParseGameEvent} from '../../../../Parser/Packet/GameEvent';
|
|
||||||
import {GameEventPacket} from '../../../../Data/Packet';
|
|
||||||
import {GameEventValueType} from '../../../../Data/GameEvent';
|
import {GameEventValueType} from '../../../../Data/GameEvent';
|
||||||
|
import {GameEventPacket} from '../../../../Data/Packet';
|
||||||
import {createParserState} from '../../../../Data/ParserState';
|
import {createParserState} from '../../../../Data/ParserState';
|
||||||
|
import {EncodeGameEvent, ParseGameEvent} from '../../../../Parser/Packet/GameEvent';
|
||||||
|
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
||||||
|
|
||||||
const data = [25, 240, 149, 0, 0];
|
const data = [25, 240, 149, 0, 0];
|
||||||
const expected = {
|
const expected = {
|
||||||
|
|
|
||||||
|
|
@ -1,20 +1,20 @@
|
||||||
|
import * as assert from 'assert';
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
|
||||||
import {hydrateEntity, hydrateTable} from './hydrate';
|
|
||||||
import {ServerClass} from '../../../../Data/ServerClass';
|
|
||||||
import {PacketEntitiesPacket} from '../../../../Data/Packet';
|
|
||||||
import {readFileSync} from 'fs';
|
import {readFileSync} from 'fs';
|
||||||
import {gunzipSync} from 'zlib';
|
import {gunzipSync} from 'zlib';
|
||||||
import {EncodePacketEntities, ParsePacketEntities} from '../../../../Parser/Packet/PacketEntities';
|
import {PacketEntitiesPacket} from '../../../../Data/Packet';
|
||||||
import * as assert from 'assert';
|
|
||||||
import {deepEqual} from '../../deepEqual';
|
|
||||||
import {createParserState} from '../../../../Data/ParserState';
|
import {createParserState} from '../../../../Data/ParserState';
|
||||||
|
import {ServerClass} from '../../../../Data/ServerClass';
|
||||||
|
import {EncodePacketEntities, ParsePacketEntities} from '../../../../Parser/Packet/PacketEntities';
|
||||||
|
import {deepEqual} from '../../deepEqual';
|
||||||
|
import {hydrateEntity, hydrateTable} from './hydrate';
|
||||||
|
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
||||||
|
|
||||||
const data = JSON.parse(readFileSync(__dirname + '/../../../data/packetEntitiesData.json', 'utf8'));
|
const data = JSON.parse(readFileSync(__dirname + '/../../../data/packetEntitiesData.json', 'utf8'));
|
||||||
const packetData = JSON.parse(gunzipSync(readFileSync(__dirname + '/../../../data/packetEntitiesResult.json.gz')).toString('utf8'));
|
const packetData = JSON.parse(gunzipSync(readFileSync(__dirname + '/../../../data/packetEntitiesResult.json.gz')).toString('utf8'));
|
||||||
const sendTableData = JSON.parse(gunzipSync(readFileSync(__dirname + '/../../../data/packetEntitiesSendTables.json.gz')).toString('utf8'));
|
const sendTableData = JSON.parse(gunzipSync(readFileSync(__dirname + '/../../../data/packetEntitiesSendTables.json.gz')).toString('utf8'));
|
||||||
const serverClassesData = JSON.parse(readFileSync(__dirname + '/../../../data/packetEntitiesServerClasses.json', 'utf8'));
|
const serverClassesData = JSON.parse(readFileSync(__dirname + '/../../../data/packetEntitiesServerClasses.json', 'utf8'));
|
||||||
const baselineData: [number, number[]][] = JSON.parse(readFileSync(__dirname + '/../../../data/packetEntityBaseLines.json', 'utf8'));
|
const baselineData: Array<[number, number[]]> = JSON.parse(readFileSync(__dirname + '/../../../data/packetEntityBaseLines.json', 'utf8'));
|
||||||
const playerEntityData = JSON.parse(readFileSync(__dirname + '/../../../data/packetEntitiesPlayerEntity.json', 'utf8'));
|
const playerEntityData = JSON.parse(readFileSync(__dirname + '/../../../data/packetEntitiesPlayerEntity.json', 'utf8'));
|
||||||
|
|
||||||
const expected: PacketEntitiesPacket = {
|
const expected: PacketEntitiesPacket = {
|
||||||
|
|
@ -58,69 +58,69 @@ function encode(value: PacketEntitiesPacket, stream: BitStream) {
|
||||||
}
|
}
|
||||||
|
|
||||||
const sunEntityData = {
|
const sunEntityData = {
|
||||||
'serverClass': {
|
serverClass: {
|
||||||
'id': 123,
|
id: 123,
|
||||||
'name': 'CSun',
|
name: 'CSun',
|
||||||
'dataTable': 'DT_Sun'
|
dataTable: 'DT_Sun'
|
||||||
},
|
},
|
||||||
'entityIndex': 403,
|
entityIndex: 403,
|
||||||
'props': [
|
props: [
|
||||||
{
|
{
|
||||||
'definition': {
|
definition: {
|
||||||
'type': 0,
|
type: 0,
|
||||||
'name': 'm_clrRender',
|
name: 'm_clrRender',
|
||||||
'flags': 1,
|
flags: 1,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 32,
|
bitCount: 32,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_Sun'
|
ownerTableName: 'DT_Sun'
|
||||||
},
|
},
|
||||||
'value': 4276271871
|
value: 4276271871
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'definition': {
|
definition: {
|
||||||
'type': 0,
|
type: 0,
|
||||||
'name': 'm_clrOverlay',
|
name: 'm_clrOverlay',
|
||||||
'flags': 1,
|
flags: 1,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 32,
|
bitCount: 32,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_Sun'
|
ownerTableName: 'DT_Sun'
|
||||||
},
|
},
|
||||||
'value': 0
|
value: 0
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'definition': {
|
definition: {
|
||||||
'type': 2,
|
type: 2,
|
||||||
'name': 'm_vDirection',
|
name: 'm_vDirection',
|
||||||
'flags': 32,
|
flags: 32,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': -121121.125,
|
highValue: -121121.125,
|
||||||
'bitCount': 0,
|
bitCount: 0,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_Sun'
|
ownerTableName: 'DT_Sun'
|
||||||
},
|
},
|
||||||
'value': {
|
value: {
|
||||||
'x': -0.6453346360527601,
|
x: -0.6453346360527601,
|
||||||
'y': -0.504152418172936,
|
y: -0.504152418172936,
|
||||||
'z': 0.1880801172447484
|
z: 0.1880801172447484
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
'inPVS': true,
|
inPVS: true,
|
||||||
'pvs': 1,
|
pvs: 1,
|
||||||
'serialNumber': 664
|
serialNumber: 664
|
||||||
};
|
};
|
||||||
|
|
||||||
suite('PacketEntities', () => {
|
suite('PacketEntities', () => {
|
||||||
|
|
@ -129,7 +129,11 @@ suite('PacketEntities', () => {
|
||||||
const stream = getStream(data);
|
const stream = getStream(data);
|
||||||
const start = stream.index;
|
const start = stream.index;
|
||||||
const resultPacket = parse(stream);
|
const resultPacket = parse(stream);
|
||||||
assert.equal(stream.index - start, length, 'Unexpected number of bits consumed from stream');
|
assert.equal(
|
||||||
|
stream.index - start,
|
||||||
|
length,
|
||||||
|
'Unexpected number of bits consumed from stream'
|
||||||
|
);
|
||||||
|
|
||||||
for (let i = 0; i < resultPacket.entities.length; i++) {
|
for (let i = 0; i < resultPacket.entities.length; i++) {
|
||||||
const resultEntity = resultPacket.entities[i];
|
const resultEntity = resultPacket.entities[i];
|
||||||
|
|
@ -138,9 +142,12 @@ suite('PacketEntities', () => {
|
||||||
assert.equal(expectedEntity.serialNumber, resultEntity.serialNumber);
|
assert.equal(expectedEntity.serialNumber, resultEntity.serialNumber);
|
||||||
assert.equal(expectedEntity.entityIndex, resultEntity.entityIndex);
|
assert.equal(expectedEntity.entityIndex, resultEntity.entityIndex);
|
||||||
if (!deepEqual(resultEntity, expectedEntity)) {
|
if (!deepEqual(resultEntity, expectedEntity)) {
|
||||||
for (let i = 0; i < expectedEntity.props.length; i++) {
|
for (let j = 0; j < expectedEntity.props.length; j++) {
|
||||||
console.log(resultEntity.getPropByDefinition(expectedEntity.props[i].definition),expectedEntity.props[i].definition);
|
assert.deepEqual(
|
||||||
assert.deepEqual(resultEntity.getPropByDefinition(expectedEntity.props[i].definition), expectedEntity.props[i], `invalid property #${i} for ${resultEntity.serverClass.name}`);
|
resultEntity.getPropByDefinition(expectedEntity.props[j].definition),
|
||||||
|
expectedEntity.props[j],
|
||||||
|
`invalid property #${j} for ${resultEntity.serverClass.name}`
|
||||||
|
);
|
||||||
}
|
}
|
||||||
assert.equal(resultEntity.props.length, expectedEntity.props.length, `Unexpected number of props for ${resultEntity.serverClass.name}`);
|
assert.equal(resultEntity.props.length, expectedEntity.props.length, `Unexpected number of props for ${resultEntity.serverClass.name}`);
|
||||||
assert(false, 'Invalid entity ' + resultEntity.serverClass.name);
|
assert(false, 'Invalid entity ' + resultEntity.serverClass.name);
|
||||||
|
|
@ -153,7 +160,6 @@ suite('PacketEntities', () => {
|
||||||
assertEncoder(parse, encode, toEncode, 0);
|
assertEncoder(parse, encode, toEncode, 0);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
test('Encode small packetEntities', () => {
|
test('Encode small packetEntities', () => {
|
||||||
assertEncoder(parse, encode, {
|
assertEncoder(parse, encode, {
|
||||||
packetType: 'packetEntities',
|
packetType: 'packetEntities',
|
||||||
|
|
@ -172,7 +178,7 @@ suite('PacketEntities', () => {
|
||||||
removedEntities: [10, 11],
|
removedEntities: [10, 11],
|
||||||
updatedBaseLine: false,
|
updatedBaseLine: false,
|
||||||
baseLine: 0,
|
baseLine: 0,
|
||||||
delta: 0,
|
delta: 1,
|
||||||
maxEntries: 16,
|
maxEntries: 16,
|
||||||
entities: [hydrateEntity(sunEntityData)]
|
entities: [hydrateEntity(sunEntityData)]
|
||||||
}, 181);
|
}, 181);
|
||||||
|
|
@ -184,7 +190,7 @@ suite('PacketEntities', () => {
|
||||||
removedEntities: [10, 11],
|
removedEntities: [10, 11],
|
||||||
updatedBaseLine: false,
|
updatedBaseLine: false,
|
||||||
baseLine: 0,
|
baseLine: 0,
|
||||||
delta: 0,
|
delta: 1,
|
||||||
maxEntries: 16,
|
maxEntries: 16,
|
||||||
entities: []
|
entities: []
|
||||||
}, 102);
|
}, 102);
|
||||||
|
|
|
||||||
|
|
@ -1,9 +1,9 @@
|
||||||
import * as assert from 'assert';
|
import * as assert from 'assert';
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {Packet} from '../../../../Data/Packet';
|
|
||||||
import {deepEqual} from '../../deepEqual';
|
|
||||||
import {isObject} from 'util';
|
import {isObject} from 'util';
|
||||||
|
import {Packet} from '../../../../Data/Packet';
|
||||||
import {ParserState} from '../../../../Data/ParserState';
|
import {ParserState} from '../../../../Data/ParserState';
|
||||||
|
import {deepEqual} from '../../deepEqual';
|
||||||
|
|
||||||
export function getStream(data: string | number[]) {
|
export function getStream(data: string | number[]) {
|
||||||
if (typeof data === 'string') {
|
if (typeof data === 'string') {
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
|
||||||
import {EncodeParseSounds, ParseParseSounds} from '../../../../Parser/Packet/ParseSounds';
|
import {EncodeParseSounds, ParseParseSounds} from '../../../../Parser/Packet/ParseSounds';
|
||||||
|
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
||||||
|
|
||||||
const data = [
|
const data = [
|
||||||
18,
|
18,
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,5 @@
|
||||||
import {make} from '../../../../Parser/Packet/ParserGenerator';
|
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
|
import {make} from '../../../../Parser/Packet/ParserGenerator';
|
||||||
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
||||||
|
|
||||||
function assertGeneratedParser(definition: string, stream: BitStream, expected: any, length: number) {
|
function assertGeneratedParser(definition: string, stream: BitStream, expected: any, length: number) {
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
|
||||||
import {EncodeSetConVar, ParseSetConVar} from '../../../../Parser/Packet/SetConVar';
|
import {EncodeSetConVar, ParseSetConVar} from '../../../../Parser/Packet/SetConVar';
|
||||||
|
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
||||||
|
|
||||||
suite('SetConVar', () => {
|
suite('SetConVar', () => {
|
||||||
test('Parse setConVar', () => {
|
test('Parse setConVar', () => {
|
||||||
|
|
|
||||||
|
|
@ -1,11 +1,11 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
import {readFileSync} from 'fs';
|
||||||
|
import {TempEntitiesPacket} from '../../../../Data/Packet';
|
||||||
|
import {createParserState} from '../../../../Data/ParserState';
|
||||||
|
import {ServerClass} from '../../../../Data/ServerClass';
|
||||||
import {EncodeTempEntities, ParseTempEntities} from '../../../../Parser/Packet/TempEntities';
|
import {EncodeTempEntities, ParseTempEntities} from '../../../../Parser/Packet/TempEntities';
|
||||||
import {hydrateEntity, hydrateTable} from './hydrate';
|
import {hydrateEntity, hydrateTable} from './hydrate';
|
||||||
import {ServerClass} from '../../../../Data/ServerClass';
|
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
||||||
import {TempEntitiesPacket} from '../../../../Data/Packet';
|
|
||||||
import {readFileSync} from 'fs';
|
|
||||||
import {createParserState} from '../../../../Data/ParserState';
|
|
||||||
|
|
||||||
const data = [
|
const data = [
|
||||||
2,
|
2,
|
||||||
|
|
@ -32,332 +32,332 @@ const data = [
|
||||||
|
|
||||||
const entityData = JSON.parse(readFileSync(__dirname + '/../../../data/tempEntitiesResult.json', 'utf8'));
|
const entityData = JSON.parse(readFileSync(__dirname + '/../../../data/tempEntitiesResult.json', 'utf8'));
|
||||||
const sendTableData = {
|
const sendTableData = {
|
||||||
'name': 'DT_TEPlayerAnimEvent',
|
name: 'DT_TEPlayerAnimEvent',
|
||||||
'props': [
|
props: [
|
||||||
{
|
{
|
||||||
'type': 0,
|
type: 0,
|
||||||
'name': 'm_iPlayerIndex',
|
name: 'm_iPlayerIndex',
|
||||||
'flags': 1,
|
flags: 1,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 7,
|
bitCount: 7,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TEPlayerAnimEvent'
|
ownerTableName: 'DT_TEPlayerAnimEvent'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 0,
|
type: 0,
|
||||||
'name': 'm_iEvent',
|
name: 'm_iEvent',
|
||||||
'flags': 1,
|
flags: 1,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 6,
|
bitCount: 6,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TEPlayerAnimEvent'
|
ownerTableName: 'DT_TEPlayerAnimEvent'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 0,
|
type: 0,
|
||||||
'name': 'm_nData',
|
name: 'm_nData',
|
||||||
'flags': 0,
|
flags: 0,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 12,
|
bitCount: 12,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TEPlayerAnimEvent'
|
ownerTableName: 'DT_TEPlayerAnimEvent'
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
'cachedFlattenedProps': []
|
cachedFlattenedProps: []
|
||||||
};
|
};
|
||||||
const sendTableData2 = {
|
const sendTableData2 = {
|
||||||
'name': 'DT_TETFParticleEffect',
|
name: 'DT_TETFParticleEffect',
|
||||||
'props': [
|
props: [
|
||||||
{
|
{
|
||||||
'type': 6,
|
type: 6,
|
||||||
'name': 'baseclass',
|
name: 'baseclass',
|
||||||
'flags': 4096,
|
flags: 4096,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 0,
|
bitCount: 0,
|
||||||
'table': {
|
table: {
|
||||||
'name': 'DT_BaseTempEntity',
|
name: 'DT_BaseTempEntity',
|
||||||
'props': [],
|
props: [],
|
||||||
'cachedFlattenedProps': []
|
cachedFlattenedProps: []
|
||||||
},
|
},
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'm_vecOrigin[0]',
|
name: 'm_vecOrigin[0]',
|
||||||
'flags': 32772,
|
flags: 32772,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 32,
|
bitCount: 32,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'm_vecOrigin[1]',
|
name: 'm_vecOrigin[1]',
|
||||||
'flags': 32772,
|
flags: 32772,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 32,
|
bitCount: 32,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'm_vecOrigin[2]',
|
name: 'm_vecOrigin[2]',
|
||||||
'flags': 32772,
|
flags: 32772,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 32,
|
bitCount: 32,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'm_vecStart[0]',
|
name: 'm_vecStart[0]',
|
||||||
'flags': 32772,
|
flags: 32772,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 32,
|
bitCount: 32,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'm_vecStart[1]',
|
name: 'm_vecStart[1]',
|
||||||
'flags': 32772,
|
flags: 32772,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 32,
|
bitCount: 32,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'm_vecStart[2]',
|
name: 'm_vecStart[2]',
|
||||||
'flags': 32772,
|
flags: 32772,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 32,
|
bitCount: 32,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 2,
|
type: 2,
|
||||||
'name': 'm_vecAngles',
|
name: 'm_vecAngles',
|
||||||
'flags': 0,
|
flags: 0,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 360,
|
highValue: 360,
|
||||||
'bitCount': 7,
|
bitCount: 7,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 0,
|
type: 0,
|
||||||
'name': 'm_iParticleSystemIndex',
|
name: 'm_iParticleSystemIndex',
|
||||||
'flags': 1,
|
flags: 1,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 16,
|
bitCount: 16,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 0,
|
type: 0,
|
||||||
'name': 'entindex',
|
name: 'entindex',
|
||||||
'flags': 1,
|
flags: 1,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 11,
|
bitCount: 11,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 0,
|
type: 0,
|
||||||
'name': 'm_iAttachType',
|
name: 'm_iAttachType',
|
||||||
'flags': 1,
|
flags: 1,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 5,
|
bitCount: 5,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 0,
|
type: 0,
|
||||||
'name': 'm_iAttachmentPointIndex',
|
name: 'm_iAttachmentPointIndex',
|
||||||
'flags': 0,
|
flags: 0,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 32,
|
bitCount: 32,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 0,
|
type: 0,
|
||||||
'name': 'm_bResetParticles',
|
name: 'm_bResetParticles',
|
||||||
'flags': 1,
|
flags: 1,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 1,
|
bitCount: 1,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 0,
|
type: 0,
|
||||||
'name': 'm_bCustomColors',
|
name: 'm_bCustomColors',
|
||||||
'flags': 1,
|
flags: 1,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 1,
|
bitCount: 1,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 2,
|
type: 2,
|
||||||
'name': 'm_CustomColors.m_vecColor1',
|
name: 'm_CustomColors.m_vecColor1',
|
||||||
'flags': 0,
|
flags: 0,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 1,
|
highValue: 1,
|
||||||
'bitCount': 8,
|
bitCount: 8,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 2,
|
type: 2,
|
||||||
'name': 'm_CustomColors.m_vecColor2',
|
name: 'm_CustomColors.m_vecColor2',
|
||||||
'flags': 0,
|
flags: 0,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 1,
|
highValue: 1,
|
||||||
'bitCount': 8,
|
bitCount: 8,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 0,
|
type: 0,
|
||||||
'name': 'm_bControlPoint1',
|
name: 'm_bControlPoint1',
|
||||||
'flags': 1,
|
flags: 1,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 1,
|
bitCount: 1,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 0,
|
type: 0,
|
||||||
'name': 'm_ControlPoint1.m_eParticleAttachment',
|
name: 'm_ControlPoint1.m_eParticleAttachment',
|
||||||
'flags': 1,
|
flags: 1,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 5,
|
bitCount: 5,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'm_ControlPoint1.m_vecOffset[0]',
|
name: 'm_ControlPoint1.m_vecOffset[0]',
|
||||||
'flags': 8196,
|
flags: 8196,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 32,
|
bitCount: 32,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'm_ControlPoint1.m_vecOffset[1]',
|
name: 'm_ControlPoint1.m_vecOffset[1]',
|
||||||
'flags': 8196,
|
flags: 8196,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 32,
|
bitCount: 32,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
'type': 1,
|
type: 1,
|
||||||
'name': 'm_ControlPoint1.m_vecOffset[2]',
|
name: 'm_ControlPoint1.m_vecOffset[2]',
|
||||||
'flags': 8196,
|
flags: 8196,
|
||||||
'excludeDTName': null,
|
excludeDTName: null,
|
||||||
'lowValue': 0,
|
lowValue: 0,
|
||||||
'highValue': 0,
|
highValue: 0,
|
||||||
'bitCount': 32,
|
bitCount: 32,
|
||||||
'table': null,
|
table: null,
|
||||||
'numElements': 0,
|
numElements: 0,
|
||||||
'arrayProperty': null,
|
arrayProperty: null,
|
||||||
'ownerTableName': 'DT_TETFParticleEffect'
|
ownerTableName: 'DT_TETFParticleEffect'
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
'cachedFlattenedProps': []
|
cachedFlattenedProps: []
|
||||||
};
|
};
|
||||||
const sendTable = hydrateTable(sendTableData);
|
const sendTable = hydrateTable(sendTableData);
|
||||||
const sendTable2 = hydrateTable(sendTableData2);
|
const sendTable2 = hydrateTable(sendTableData2);
|
||||||
|
|
|
||||||
|
|
@ -1,9 +1,9 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
|
||||||
import {EncodeUpdateStringTable, ParseUpdateStringTable} from '../../../../Parser/Packet/UpdateStringTable';
|
|
||||||
import {StringTable} from '../../../../Data/StringTable';
|
|
||||||
import {UpdateStringTablePacket} from '../../../../Data/Packet';
|
import {UpdateStringTablePacket} from '../../../../Data/Packet';
|
||||||
import {createParserState} from '../../../../Data/ParserState';
|
import {createParserState} from '../../../../Data/ParserState';
|
||||||
|
import {StringTable} from '../../../../Data/StringTable';
|
||||||
|
import {EncodeUpdateStringTable, ParseUpdateStringTable} from '../../../../Parser/Packet/UpdateStringTable';
|
||||||
|
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
||||||
|
|
||||||
const exampleData = [200, 3, 0, 48, 130, 53];
|
const exampleData = [200, 3, 0, 48, 130, 53];
|
||||||
|
|
||||||
|
|
@ -36,7 +36,6 @@ examplePacket.entries[70] = {
|
||||||
)
|
)
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
const examplePacket2: UpdateStringTablePacket = {
|
const examplePacket2: UpdateStringTablePacket = {
|
||||||
packetType: 'updateStringTable',
|
packetType: 'updateStringTable',
|
||||||
entries: [
|
entries: [
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,7 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
|
||||||
import {EncodeUserMessage, ParseUserMessage} from '../../../../Parser/Packet/UserMessage';
|
|
||||||
import {HudTextLocation} from '../../../../Data/UserMessage';
|
import {HudTextLocation} from '../../../../Data/UserMessage';
|
||||||
|
import {EncodeUserMessage, ParseUserMessage} from '../../../../Parser/Packet/UserMessage';
|
||||||
|
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
||||||
|
|
||||||
const data = [
|
const data = [
|
||||||
5,
|
5,
|
||||||
|
|
@ -40,7 +40,7 @@ const expected = {
|
||||||
substitute1: 'sekr',
|
substitute1: 'sekr',
|
||||||
substitute2: '',
|
substitute2: '',
|
||||||
substitute3: '',
|
substitute3: '',
|
||||||
substitute4: '',
|
substitute4: ''
|
||||||
};
|
};
|
||||||
|
|
||||||
suite('UserMessage', () => {
|
suite('UserMessage', () => {
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
|
||||||
import {EncodeVoiceData, ParseVoiceData} from '../../../../Parser/Packet/VoiceData';
|
import {EncodeVoiceData, ParseVoiceData} from '../../../../Parser/Packet/VoiceData';
|
||||||
|
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
||||||
|
|
||||||
const data = [5, 18, 24, 0, 123, 219, 1];
|
const data = [5, 18, 24, 0, 123, 219, 1];
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
|
||||||
import {EncodeVoiceInit, ParseVoiceInit} from '../../../../Parser/Packet/VoiceInit';
|
import {EncodeVoiceInit, ParseVoiceInit} from '../../../../Parser/Packet/VoiceInit';
|
||||||
|
import {assertEncoder, assertParser, getStream} from './PacketTest';
|
||||||
|
|
||||||
const data = [118, 97, 117, 100, 105, 111, 95, 99, 101, 108, 116, 0, 255, 34, 86];
|
const data = [118, 97, 117, 100, 105, 111, 95, 99, 101, 108, 116, 0, 255, 34, 86];
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,12 +1,12 @@
|
||||||
import {SendProp, SendPropValue} from '../../../../Data/SendProp';
|
|
||||||
import {PacketEntity} from '../../../../Data/PacketEntity';
|
import {PacketEntity} from '../../../../Data/PacketEntity';
|
||||||
|
import {SendProp, SendPropValue} from '../../../../Data/SendProp';
|
||||||
import {SendPropDefinition, SendPropType} from '../../../../Data/SendPropDefinition';
|
import {SendPropDefinition, SendPropType} from '../../../../Data/SendPropDefinition';
|
||||||
import {Vector} from '../../../../Data/Vector';
|
|
||||||
import {SendTable} from '../../../../Data/SendTable';
|
import {SendTable} from '../../../../Data/SendTable';
|
||||||
|
import {Vector} from '../../../../Data/Vector';
|
||||||
|
|
||||||
export function hydrateEntity(entityData): PacketEntity {
|
export function hydrateEntity(entityData): PacketEntity {
|
||||||
const entity = new PacketEntity(entityData.serverClass, entityData.entityIndex, entityData.pvs);
|
const entity = new PacketEntity(entityData.serverClass, entityData.entityIndex, entityData.pvs);
|
||||||
entity.props = entityData.props.map(propData => {
|
entity.props = entityData.props.map((propData) => {
|
||||||
const prop = new SendProp(propDataDefinition(propData.definition));
|
const prop = new SendProp(propDataDefinition(propData.definition));
|
||||||
prop.value = hydrateProp(propData.value, prop.definition);
|
prop.value = hydrateProp(propData.value, prop.definition);
|
||||||
return prop;
|
return prop;
|
||||||
|
|
@ -27,7 +27,7 @@ function hydrateProp(value: any, definition: SendPropDefinition): SendPropValue
|
||||||
if (arrayProp === null) {
|
if (arrayProp === null) {
|
||||||
throw new Error('arrayProperty not set for array property');
|
throw new Error('arrayProperty not set for array property');
|
||||||
}
|
}
|
||||||
return value.map(arrayValue => hydrateProp(arrayValue, arrayProp)) as SendPropValue;
|
return value.map((arrayValue) => hydrateProp(arrayValue, arrayProp)) as SendPropValue;
|
||||||
} else if (definition.type === SendPropType.DPT_Vector || definition.type === SendPropType.DPT_VectorXY) {
|
} else if (definition.type === SendPropType.DPT_Vector || definition.type === SendPropType.DPT_VectorXY) {
|
||||||
return new Vector(value.x, value.y, value.z);
|
return new Vector(value.x, value.y, value.z);
|
||||||
} else {
|
} else {
|
||||||
|
|
|
||||||
|
|
@ -1,9 +1,9 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from './Packet/PacketTest';
|
|
||||||
import {readBitVar, readVarInt, writeBitVar, writeVarInt} from '../../../Parser/readBitVar';
|
|
||||||
import {SendPropParser} from '../../../Parser/SendPropParser';
|
|
||||||
import {SendPropDefinition, SendPropFlag, SendPropType} from '../../../Data/SendPropDefinition';
|
import {SendPropDefinition, SendPropFlag, SendPropType} from '../../../Data/SendPropDefinition';
|
||||||
|
import {readBitVar, readVarInt, writeBitVar, writeVarInt} from '../../../Parser/readBitVar';
|
||||||
import {SendPropEncoder} from '../../../Parser/SendPropEncoder';
|
import {SendPropEncoder} from '../../../Parser/SendPropEncoder';
|
||||||
|
import {SendPropParser} from '../../../Parser/SendPropParser';
|
||||||
|
import {assertEncoder, assertParser, getStream} from './Packet/PacketTest';
|
||||||
|
|
||||||
function basicIntReader(bitCount: number, signed: boolean) {
|
function basicIntReader(bitCount: number, signed: boolean) {
|
||||||
return (stream: BitStream) => {
|
return (stream: BitStream) => {
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from '../Packet/PacketTest';
|
|
||||||
import {EncodeSayText2, ParseSayText2} from '../../../../Parser/UserMessage/SayText2';
|
import {EncodeSayText2, ParseSayText2} from '../../../../Parser/UserMessage/SayText2';
|
||||||
|
import {assertEncoder, assertParser, getStream} from '../Packet/PacketTest';
|
||||||
|
|
||||||
const data = [
|
const data = [
|
||||||
3,
|
3,
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
import {BitStream} from 'bit-buffer';
|
||||||
import {assertEncoder, assertParser, getStream} from './Packet/PacketTest';
|
|
||||||
import {readBitVar, readVarInt, writeBitVar, writeVarInt} from '../../../Parser/readBitVar';
|
import {readBitVar, readVarInt, writeBitVar, writeVarInt} from '../../../Parser/readBitVar';
|
||||||
|
import {assertEncoder, assertParser, getStream} from './Packet/PacketTest';
|
||||||
|
|
||||||
function readVarIntSigned(stream: BitStream) {
|
function readVarIntSigned(stream: BitStream) {
|
||||||
return readVarInt(stream, true);
|
return readVarInt(stream, true);
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,5 @@
|
||||||
import {BitStream} from 'bit-buffer';
|
|
||||||
import * as assert from 'assert';
|
import * as assert from 'assert';
|
||||||
|
import {BitStream} from 'bit-buffer';
|
||||||
|
|
||||||
export interface EqualOpts {
|
export interface EqualOpts {
|
||||||
strict?: boolean;
|
strict?: boolean;
|
||||||
|
|
@ -15,7 +15,8 @@ export function deepEqual(actual, expected, opts: EqualOpts = {}) {
|
||||||
|
|
||||||
// 7.3. Other pairs that do not both pass typeof value == 'object',
|
// 7.3. Other pairs that do not both pass typeof value == 'object',
|
||||||
// equivalence is determined by ==.
|
// equivalence is determined by ==.
|
||||||
} else if (!actual || !expected || typeof actual != 'object' && typeof expected != 'object') {
|
} else if (!actual || !expected || typeof actual !== 'object' && typeof expected !== 'object') {
|
||||||
|
// tslint:disable-next-line
|
||||||
return opts.strict ? actual === expected : actual == expected;
|
return opts.strict ? actual === expected : actual == expected;
|
||||||
|
|
||||||
// 7.4. For all other Object pairs, including Array objects, equivalence is
|
// 7.4. For all other Object pairs, including Array objects, equivalence is
|
||||||
|
|
@ -34,7 +35,9 @@ function isUndefinedOrNull(value) {
|
||||||
}
|
}
|
||||||
|
|
||||||
function isBuffer(x): x is Buffer {
|
function isBuffer(x): x is Buffer {
|
||||||
if (!x || typeof x !== 'object' || typeof x.length !== 'number') return false;
|
if (!x || typeof x !== 'object' || typeof x.length !== 'number') {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
if (typeof x.copy !== 'function' || typeof x.slice !== 'function') {
|
if (typeof x.copy !== 'function' || typeof x.slice !== 'function') {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
@ -46,14 +49,16 @@ function isStream(stream): stream is BitStream {
|
||||||
}
|
}
|
||||||
|
|
||||||
function objEquiv(a, b, opts) {
|
function objEquiv(a, b, opts) {
|
||||||
let i, key;
|
let i;
|
||||||
if (isUndefinedOrNull(a) || isUndefinedOrNull(b))
|
let key;
|
||||||
|
if (isUndefinedOrNull(a) || isUndefinedOrNull(b)) {
|
||||||
return false;
|
return false;
|
||||||
|
}
|
||||||
// an identical 'prototype' property.
|
// an identical 'prototype' property.
|
||||||
if (a.prototype !== b.prototype) {
|
if (a.prototype !== b.prototype) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
//~~~I've managed to break Object.keys through screwy arguments passing.
|
// ~~~I've managed to break Object.keys through screwy arguments passing.
|
||||||
// Converting to array solves the problem.
|
// Converting to array solves the problem.
|
||||||
if (isBuffer(a)) {
|
if (isBuffer(a)) {
|
||||||
if (!isBuffer(b)) {
|
if (!isBuffer(b)) {
|
||||||
|
|
@ -95,24 +100,28 @@ function objEquiv(a, b, opts) {
|
||||||
|
|
||||||
// having the same number of owned properties (keys incorporates
|
// having the same number of owned properties (keys incorporates
|
||||||
// hasOwnProperty)
|
// hasOwnProperty)
|
||||||
if (ka.length != kb.length)
|
if (ka.length !== kb.length) {
|
||||||
return false;
|
return false;
|
||||||
//the same set of keys (although not necessarily the same order),
|
}
|
||||||
|
// the same set of keys (although not necessarily the same order),
|
||||||
ka.sort();
|
ka.sort();
|
||||||
kb.sort();
|
kb.sort();
|
||||||
//~~~cheap key test
|
// ~~~cheap key test
|
||||||
for (i = ka.length - 1; i >= 0; i--) {
|
for (i = ka.length - 1; i >= 0; i--) {
|
||||||
if (ka[i] != kb[i])
|
if (ka[i] !== kb[i]) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
//equivalent values for every corresponding key, and
|
}
|
||||||
//~~~possibly expensive deep test
|
// equivalent values for every corresponding key, and
|
||||||
|
// ~~~possibly expensive deep test
|
||||||
for (i = ka.length - 1; i >= 0; i--) {
|
for (i = ka.length - 1; i >= 0; i--) {
|
||||||
key = ka[i];
|
key = ka[i];
|
||||||
if (!deepEqual(a[key], b[key], opts)) return false;
|
if (!deepEqual(a[key], b[key], opts)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return typeof a === typeof b;
|
return typeof a === typeof b;
|
||||||
} catch (e) {//happens when one is a string literal and the other isn't
|
} catch (e) {// happens when one is a string literal and the other isn't
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -34,7 +34,14 @@
|
||||||
"timeEnd",
|
"timeEnd",
|
||||||
"trace"
|
"trace"
|
||||||
]
|
]
|
||||||
|
},
|
||||||
|
"trailing-comma": [
|
||||||
|
true,
|
||||||
|
{
|
||||||
|
"multiline": "never",
|
||||||
|
"singleline": "never"
|
||||||
}
|
}
|
||||||
|
]
|
||||||
},
|
},
|
||||||
"jsRules": {
|
"jsRules": {
|
||||||
"max-line-length": {
|
"max-line-length": {
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue