- make each event update have a key/data interface
- separate .d.ts file for event updates - fix initialisation of global items
This commit is contained in:
parent
494913d3b9
commit
5208d9affd
14 changed files with 451 additions and 266 deletions
|
|
@ -1,16 +1,17 @@
|
||||||
import {emitConfigurationUpdate} from "./main/config-update/handleConfigurationUpdate";
|
import {emitConfigurationUpdate} from "./main/config-update/handleConfigurationUpdate";
|
||||||
import {emitPrototypes} from "./main/config-update/prototypes";
|
import {emitPrototypes} from "./main/config-update/prototypes";
|
||||||
import {Queue} from "./main/queue/queue";
|
import {initGlobal} from "./main/global-init";
|
||||||
import {EventDataCache} from "./main/cache/EventDataCache";
|
|
||||||
|
|
||||||
require("./main/events/registerHandlers")
|
require("./main/events/registerHandlers")
|
||||||
|
require("./main/events/playerEvents")
|
||||||
|
require("./main/events/mapEvents")
|
||||||
require("./main/commands/kafkatorioCommands")
|
require("./main/commands/kafkatorioCommands")
|
||||||
require("./main/cache/cacheChecker")
|
require("./main/cache/cacheChecker")
|
||||||
|
|
||||||
script.on_configuration_changed((data: ConfigurationChangedData) => {
|
script.on_configuration_changed((data: ConfigurationChangedData) => {
|
||||||
// runs whenever the version of the base game, or a mod, changes
|
// runs whenever the version of the base game, or a mod, changes
|
||||||
|
|
||||||
reInitGlobal()
|
initGlobal(true)
|
||||||
emitConfigurationUpdate(data)
|
emitConfigurationUpdate(data)
|
||||||
emitPrototypes()
|
emitPrototypes()
|
||||||
})
|
})
|
||||||
|
|
@ -18,27 +19,5 @@ script.on_configuration_changed((data: ConfigurationChangedData) => {
|
||||||
|
|
||||||
script.on_init(() => {
|
script.on_init(() => {
|
||||||
// runs only once (when the mod is first added to the save)
|
// runs only once (when the mod is first added to the save)
|
||||||
initGlobal()
|
initGlobal(true)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|
||||||
function initGlobal() {
|
|
||||||
log("Initialising Kafkatorio Global variables...")
|
|
||||||
|
|
||||||
Queue.init()
|
|
||||||
EventDataCache.init()
|
|
||||||
|
|
||||||
log("Finished initialising Kafkatorio Global variables")
|
|
||||||
}
|
|
||||||
|
|
||||||
function reInitGlobal() {
|
|
||||||
log("Re-initialising Kafkatorio Global variables...")
|
|
||||||
|
|
||||||
global.MOD_VERSION = script.active_mods[script.mod_name]
|
|
||||||
global.FACTORIO_VERSION = script.active_mods["base"]
|
|
||||||
|
|
||||||
Queue.reset()
|
|
||||||
EventDataCache.reset()
|
|
||||||
|
|
||||||
log("Finished re-initialising Kafkatorio Global variables")
|
|
||||||
}
|
|
||||||
|
|
|
||||||
|
|
@ -6,6 +6,33 @@ interface FactorioObjectData {
|
||||||
objectName: ObjectName;
|
objectName: ObjectName;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
interface PlayerData extends FactorioObjectData, FactorioLuaControl {
|
||||||
|
associatedCharactersUnitNumbers: uint[];
|
||||||
|
characterUnitNumber: uint | null;
|
||||||
|
chatColour: Colour;
|
||||||
|
colour: Colour;
|
||||||
|
force: uint;
|
||||||
|
lastOnline: uint;
|
||||||
|
name: string;
|
||||||
|
objectName: ObjectName;
|
||||||
|
position: MapEntityPosition;
|
||||||
|
surface: uint;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface EntityData extends FactorioObjectData, FactorioLuaControl {
|
||||||
|
active: boolean;
|
||||||
|
force: uint;
|
||||||
|
health: double | null;
|
||||||
|
healthRatio: double;
|
||||||
|
name: string;
|
||||||
|
objectName: ObjectName;
|
||||||
|
playerIndex: uint | null;
|
||||||
|
position: MapEntityPosition;
|
||||||
|
surface: uint;
|
||||||
|
type: string;
|
||||||
|
unitNumber: uint | null;
|
||||||
|
}
|
||||||
|
|
||||||
interface SurfaceData extends FactorioObjectData {
|
interface SurfaceData extends FactorioObjectData {
|
||||||
daytime: double;
|
daytime: double;
|
||||||
index: uint;
|
index: uint;
|
||||||
|
|
|
||||||
|
|
@ -7,19 +7,6 @@ interface KafkatorioPacket {
|
||||||
packetType: PacketType;
|
packetType: PacketType;
|
||||||
}
|
}
|
||||||
|
|
||||||
type FactorioEventUpdateType = "PLAYER" | "MAP_CHUNK" | "ENTITY";
|
|
||||||
|
|
||||||
interface FactorioEventUpdate {
|
|
||||||
updateType: FactorioEventUpdateType;
|
|
||||||
}
|
|
||||||
|
|
||||||
interface FactorioEventUpdatePacket extends KafkatorioPacket {
|
|
||||||
modVersion: string;
|
|
||||||
packetType: PacketType;
|
|
||||||
tick: uint;
|
|
||||||
update: FactorioEventUpdate;
|
|
||||||
}
|
|
||||||
|
|
||||||
interface FactorioEvent extends KafkatorioPacket {
|
interface FactorioEvent extends KafkatorioPacket {
|
||||||
data: FactorioObjectData;
|
data: FactorioObjectData;
|
||||||
eventType: string;
|
eventType: string;
|
||||||
|
|
@ -46,33 +33,6 @@ interface Colour {
|
||||||
red: float;
|
red: float;
|
||||||
}
|
}
|
||||||
|
|
||||||
interface PlayerData extends FactorioObjectData, FactorioLuaControl {
|
|
||||||
associatedCharactersUnitNumbers: uint[];
|
|
||||||
characterUnitNumber: uint | null;
|
|
||||||
chatColour: Colour;
|
|
||||||
colour: Colour;
|
|
||||||
force: uint;
|
|
||||||
lastOnline: uint;
|
|
||||||
name: string;
|
|
||||||
objectName: ObjectName;
|
|
||||||
position: MapEntityPosition;
|
|
||||||
surface: uint;
|
|
||||||
}
|
|
||||||
|
|
||||||
interface EntityData extends FactorioObjectData, FactorioLuaControl {
|
|
||||||
active: boolean;
|
|
||||||
force: uint;
|
|
||||||
health: double | null;
|
|
||||||
healthRatio: double;
|
|
||||||
name: string;
|
|
||||||
objectName: ObjectName;
|
|
||||||
playerIndex: uint | null;
|
|
||||||
position: MapEntityPosition;
|
|
||||||
surface: uint;
|
|
||||||
type: string;
|
|
||||||
unitNumber: uint | null;
|
|
||||||
}
|
|
||||||
|
|
||||||
interface MapTilePosition {
|
interface MapTilePosition {
|
||||||
x: int;
|
x: int;
|
||||||
y: int;
|
y: int;
|
||||||
|
|
@ -99,56 +59,3 @@ interface EntityIdentifiers {
|
||||||
type: string;
|
type: string;
|
||||||
unitNumber: uint | null;
|
unitNumber: uint | null;
|
||||||
}
|
}
|
||||||
|
|
||||||
interface PlayerUpdate extends FactorioEventUpdate {
|
|
||||||
afkTime: uint | null;
|
|
||||||
bannedReason: string | null;
|
|
||||||
characterUnitNumber: uint | null;
|
|
||||||
chatColour: Colour | null;
|
|
||||||
colour: Colour | null;
|
|
||||||
diedCause: EntityIdentifiers | null;
|
|
||||||
disconnectReason: string | null;
|
|
||||||
forceIndex: uint | null;
|
|
||||||
index: uint;
|
|
||||||
isAdmin: boolean | null;
|
|
||||||
isConnected: boolean | null;
|
|
||||||
isRemoved: boolean | null;
|
|
||||||
isShowOnMap: boolean | null;
|
|
||||||
isSpectator: boolean | null;
|
|
||||||
kickedReason: string | null;
|
|
||||||
lastOnline: uint | null;
|
|
||||||
name: string | null;
|
|
||||||
onlineTime: uint | null;
|
|
||||||
position: MapEntityPosition | null;
|
|
||||||
surfaceIndex: uint | null;
|
|
||||||
tag: string | null;
|
|
||||||
ticksToRespawn: uint | null;
|
|
||||||
updateType: FactorioEventUpdateType;
|
|
||||||
}
|
|
||||||
|
|
||||||
interface EntityUpdate extends FactorioEventUpdate, EntityIdentifiers {
|
|
||||||
chunkPosition: MapChunkPosition | null;
|
|
||||||
graphicsVariation: number | null;
|
|
||||||
health: float | null;
|
|
||||||
isActive: boolean | null;
|
|
||||||
isRotatable: boolean | null;
|
|
||||||
lastUser: int | null;
|
|
||||||
localisedDescription: string | null;
|
|
||||||
localisedName: string | null;
|
|
||||||
name: string;
|
|
||||||
prototype: string | null;
|
|
||||||
type: string;
|
|
||||||
unitNumber: uint;
|
|
||||||
updateType: FactorioEventUpdateType;
|
|
||||||
}
|
|
||||||
|
|
||||||
interface MapChunkUpdate extends FactorioEventUpdate {
|
|
||||||
chunkPosition: MapChunkPosition;
|
|
||||||
force: uint | null;
|
|
||||||
isDeleted: boolean | null;
|
|
||||||
player: uint | null;
|
|
||||||
robot: EntityIdentifiers | null;
|
|
||||||
surfaceIndex: uint;
|
|
||||||
tiles: Map<MapTilePosition, string> | null;
|
|
||||||
updateType: FactorioEventUpdateType;
|
|
||||||
}
|
|
||||||
|
|
|
||||||
134
modules/events-mod/src/main/typescript/generated/kafkatorio-schema/update.d.ts
vendored
Normal file
134
modules/events-mod/src/main/typescript/generated/kafkatorio-schema/update.d.ts
vendored
Normal file
|
|
@ -0,0 +1,134 @@
|
||||||
|
// Generated by TypeScriptGenerator - do not edit this file manually
|
||||||
|
|
||||||
|
type FactorioEventUpdateType = "PLAYER" | "MAP_CHUNK" | "ENTITY";
|
||||||
|
|
||||||
|
interface FactorioEventUpdateKey {
|
||||||
|
updateType: FactorioEventUpdateType;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface FactorioEventUpdateData {
|
||||||
|
updateType: FactorioEventUpdateType;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface FactorioEventUpdate extends FactorioEventUpdateKey, FactorioEventUpdateData {
|
||||||
|
updateType: FactorioEventUpdateType;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface FactorioEventUpdatePacket extends KafkatorioPacket {
|
||||||
|
modVersion: string;
|
||||||
|
packetType: PacketType;
|
||||||
|
tick: uint;
|
||||||
|
update: FactorioEventUpdate;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface PlayerUpdateKey extends FactorioEventUpdateKey {
|
||||||
|
index: uint;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface PlayerUpdateData extends FactorioEventUpdateData {
|
||||||
|
afkTime: uint | null;
|
||||||
|
bannedReason: string | null;
|
||||||
|
characterUnitNumber: uint | null;
|
||||||
|
chatColour: Colour | null;
|
||||||
|
colour: Colour | null;
|
||||||
|
diedCause: EntityIdentifiers | null;
|
||||||
|
disconnectReason: string | null;
|
||||||
|
forceIndex: uint | null;
|
||||||
|
isAdmin: boolean | null;
|
||||||
|
isConnected: boolean | null;
|
||||||
|
isRemoved: boolean | null;
|
||||||
|
isShowOnMap: boolean | null;
|
||||||
|
isSpectator: boolean | null;
|
||||||
|
kickedReason: string | null;
|
||||||
|
lastOnline: uint | null;
|
||||||
|
name: string | null;
|
||||||
|
onlineTime: uint | null;
|
||||||
|
position: MapEntityPosition | null;
|
||||||
|
surfaceIndex: uint | null;
|
||||||
|
tag: string | null;
|
||||||
|
ticksToRespawn: uint | null;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface PlayerUpdate extends FactorioEventUpdate, PlayerUpdateKey, PlayerUpdateData {
|
||||||
|
afkTime: uint | null;
|
||||||
|
bannedReason: string | null;
|
||||||
|
characterUnitNumber: uint | null;
|
||||||
|
chatColour: Colour | null;
|
||||||
|
colour: Colour | null;
|
||||||
|
diedCause: EntityIdentifiers | null;
|
||||||
|
disconnectReason: string | null;
|
||||||
|
forceIndex: uint | null;
|
||||||
|
index: uint;
|
||||||
|
isAdmin: boolean | null;
|
||||||
|
isConnected: boolean | null;
|
||||||
|
isRemoved: boolean | null;
|
||||||
|
isShowOnMap: boolean | null;
|
||||||
|
isSpectator: boolean | null;
|
||||||
|
kickedReason: string | null;
|
||||||
|
lastOnline: uint | null;
|
||||||
|
name: string | null;
|
||||||
|
onlineTime: uint | null;
|
||||||
|
position: MapEntityPosition | null;
|
||||||
|
surfaceIndex: uint | null;
|
||||||
|
tag: string | null;
|
||||||
|
ticksToRespawn: uint | null;
|
||||||
|
updateType: FactorioEventUpdateType;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface EntityUpdateKey extends EntityIdentifiers, FactorioEventUpdateKey {
|
||||||
|
name: string;
|
||||||
|
type: string;
|
||||||
|
unitNumber: uint;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface EntityUpdateData extends FactorioEventUpdateData {
|
||||||
|
chunkPosition: MapChunkPosition | null;
|
||||||
|
graphicsVariation: number | null;
|
||||||
|
health: float | null;
|
||||||
|
isActive: boolean | null;
|
||||||
|
isRotatable: boolean | null;
|
||||||
|
lastUser: int | null;
|
||||||
|
localisedDescription: string | null;
|
||||||
|
localisedName: string | null;
|
||||||
|
prototype: string | null;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface EntityUpdate extends FactorioEventUpdate, EntityIdentifiers, EntityUpdateKey, EntityUpdateData {
|
||||||
|
chunkPosition: MapChunkPosition | null;
|
||||||
|
graphicsVariation: number | null;
|
||||||
|
health: float | null;
|
||||||
|
isActive: boolean | null;
|
||||||
|
isRotatable: boolean | null;
|
||||||
|
lastUser: int | null;
|
||||||
|
localisedDescription: string | null;
|
||||||
|
localisedName: string | null;
|
||||||
|
name: string;
|
||||||
|
prototype: string | null;
|
||||||
|
type: string;
|
||||||
|
unitNumber: uint;
|
||||||
|
updateType: FactorioEventUpdateType;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface MapChunkUpdateKey extends FactorioEventUpdateKey {
|
||||||
|
chunkPosition: MapChunkPosition;
|
||||||
|
surfaceIndex: uint;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface MapChunkUpdateData extends FactorioEventUpdateData {
|
||||||
|
force: uint | null;
|
||||||
|
isDeleted: boolean | null;
|
||||||
|
player: uint | null;
|
||||||
|
robot: EntityIdentifiers | null;
|
||||||
|
tiles: MapTile[] | null;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface MapChunkUpdate extends FactorioEventUpdate, MapChunkUpdateKey, MapChunkUpdateData {
|
||||||
|
chunkPosition: MapChunkPosition;
|
||||||
|
force: uint | null;
|
||||||
|
isDeleted: boolean | null;
|
||||||
|
player: uint | null;
|
||||||
|
robot: EntityIdentifiers | null;
|
||||||
|
surfaceIndex: uint;
|
||||||
|
tiles: MapTile[] | null;
|
||||||
|
updateType: FactorioEventUpdateType;
|
||||||
|
}
|
||||||
|
|
@ -1,32 +1,34 @@
|
||||||
import {ExcludeNullKeys, NonNullableKeys} from "../types";
|
import {NonNullableKeys} from "../types";
|
||||||
|
|
||||||
export namespace EventDataCache {
|
export namespace EventDataCache {
|
||||||
|
|
||||||
|
|
||||||
declare const global: {
|
declare const global: {
|
||||||
cache: LuaTable<CacheKey<FactorioEventUpdateType>, CacheEntry<FactorioEventUpdateType>>,
|
cache: LuaTable<CacheKey<FactorioEventUpdateType>, CacheEntry<FactorioEventUpdateType>>,
|
||||||
DEFAULT_CACHE_DURATION_TICKS2: Record<FactorioEventUpdateType | "default", uint>,
|
defaultCacheDurationTicks: Record<FactorioEventUpdateType | "default", uint>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
export function reset() {
|
export function init(force?: boolean) {
|
||||||
log("Resetting EventDataCache")
|
|
||||||
global.cache = new LuaTable<CacheKey<FactorioEventUpdateType>, CacheEntry<FactorioEventUpdateType>>()
|
|
||||||
}
|
|
||||||
|
|
||||||
|
const isAnythingUndefined = global.cache == undefined ||
|
||||||
|
global.defaultCacheDurationTicks == undefined
|
||||||
|
|
||||||
export function init() {
|
log(`Initialising EventDataCache (force=${force}, isAnythingUndefined=${isAnythingUndefined})...`)
|
||||||
if (typeof global.cache == undefined) {
|
|
||||||
log("Initialising EventDataCache")
|
|
||||||
reset()
|
|
||||||
|
|
||||||
global.DEFAULT_CACHE_DURATION_TICKS2 = {
|
if (force == true || isAnythingUndefined) {
|
||||||
"PLAYER": 30, // 0.5 seconds
|
log("Initialising global.cache")
|
||||||
"MAP_CHUNK": 60 * 15, // ~ 15 seconds
|
global.cache = new LuaTable<CacheKey<FactorioEventUpdateType>, CacheEntry<FactorioEventUpdateType>>()
|
||||||
"ENTITY": 60 * 2, // ~2 seconds
|
|
||||||
"default": 60
|
log("Initialising global.DEFAULT_CACHE_DURATION_TICKS")
|
||||||
|
global.defaultCacheDurationTicks = {
|
||||||
|
"PLAYER": 60, // 1 second
|
||||||
|
"MAP_CHUNK": 60 * 30, // 30 seconds
|
||||||
|
"ENTITY": 60 * 2, // 2 seconds
|
||||||
|
"default": 60 * 5, // 5 seconds
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
log(`Finished initialising EventDataCache`)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -73,7 +75,7 @@ export namespace EventDataCache {
|
||||||
*/
|
*/
|
||||||
export function setExpiration(
|
export function setExpiration(
|
||||||
key: CacheKey<FactorioEventUpdateType>,
|
key: CacheKey<FactorioEventUpdateType>,
|
||||||
expirationDurationTicks?: uint,
|
expirationDurationTicks: uint,
|
||||||
) {
|
) {
|
||||||
const entry = getCacheEntry(key)
|
const entry = getCacheEntry(key)
|
||||||
if (entry != undefined) {
|
if (entry != undefined) {
|
||||||
|
|
@ -82,11 +84,12 @@ export namespace EventDataCache {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
export function extractExpired(): Array<CacheData<FactorioEventUpdateType>> {
|
export function extractExpired(): Array<FactorioEventUpdate> {
|
||||||
const expiredData: Array<CacheData<FactorioEventUpdateType>> = []
|
const expiredData: Array<FactorioEventUpdate> = []
|
||||||
for (let [key, entry] of global.cache) {
|
for (let [key, entry] of global.cache) {
|
||||||
if (entry.isExpired()) {
|
if (isExpired(entry)) {
|
||||||
expiredData.push(entry.data)
|
const update: FactorioEventUpdate = {...key, ...entry.data}
|
||||||
|
expiredData.push(update)
|
||||||
global.cache.delete(key)
|
global.cache.delete(key)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -114,7 +117,7 @@ export namespace EventDataCache {
|
||||||
key: CacheKey<TYPE>,
|
key: CacheKey<TYPE>,
|
||||||
mutate: CacheDataMutator<TYPE>,
|
mutate: CacheDataMutator<TYPE>,
|
||||||
): CacheEntry<TYPE> {
|
): CacheEntry<TYPE> {
|
||||||
// @ts-ignore // TODO remove ts-ignore for "not assignable to type"
|
// @ts-ignore // TODO resolve ts-ignore for "not assignable to type"
|
||||||
const data: CacheData<TYPE> = {updateType: key.updateType}
|
const data: CacheData<TYPE> = {updateType: key.updateType}
|
||||||
mutate(data)
|
mutate(data)
|
||||||
let entry: CacheEntry<TYPE> = new CacheEntry<TYPE>(data)
|
let entry: CacheEntry<TYPE> = new CacheEntry<TYPE>(data)
|
||||||
|
|
@ -123,24 +126,35 @@ export namespace EventDataCache {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/** Map a {@link FactorioEventUpdateType} to a {@link FactorioEventUpdate} DTO */
|
// /** Map a {@link FactorioEventUpdateType} to a {@link FactorioEventUpdate} DTO */
|
||||||
type ConvertUpdateType<TYPE extends FactorioEventUpdateType> =
|
// type ConvertUpdateType<TYPE extends FactorioEventUpdateType> =
|
||||||
TYPE extends "PLAYER" ? PlayerUpdate :
|
// TYPE extends "PLAYER" ? PlayerUpdate :
|
||||||
TYPE extends "MAP_CHUNK" ? MapChunkUpdate :
|
// TYPE extends "MAP_CHUNK" ? MapChunkUpdate :
|
||||||
TYPE extends "ENTITY" ? EntityUpdate :
|
// TYPE extends "ENTITY" ? EntityUpdate :
|
||||||
|
// never
|
||||||
|
|
||||||
|
type ConvertKeyType<TYPE extends FactorioEventUpdateType> =
|
||||||
|
TYPE extends "PLAYER" ? PlayerUpdateKey :
|
||||||
|
TYPE extends "MAP_CHUNK" ? MapChunkUpdateKey :
|
||||||
|
TYPE extends "ENTITY" ? EntityUpdateKey :
|
||||||
|
never
|
||||||
|
type ConvertKeyData<TYPE extends FactorioEventUpdateType> =
|
||||||
|
TYPE extends "PLAYER" ? PlayerUpdateData :
|
||||||
|
TYPE extends "MAP_CHUNK" ? MapChunkUpdateData :
|
||||||
|
TYPE extends "ENTITY" ? EntityUpdateData :
|
||||||
never
|
never
|
||||||
|
|
||||||
|
|
||||||
/** Only include the non-null properties, and make `updateType` specific */
|
/** Only include the non-null properties, and make `updateType` specific */
|
||||||
export type CacheKey<TYPE extends FactorioEventUpdateType> =
|
export type CacheKey<TYPE extends FactorioEventUpdateType> =
|
||||||
CacheTyped<TYPE>
|
CacheTyped<TYPE>
|
||||||
& Omit<ExcludeNullKeys<ConvertUpdateType<TYPE>>, "updateType">
|
& Omit<ConvertKeyType<TYPE>, "updateType">
|
||||||
|
|
||||||
|
|
||||||
/** Exclude {@link CacheKey} fields, and make `updateType` specific */
|
/** Exclude {@link CacheKey} fields, and make `updateType` specific */
|
||||||
export type CacheData<TYPE extends FactorioEventUpdateType> =
|
export type CacheData<TYPE extends FactorioEventUpdateType> =
|
||||||
CacheTyped<TYPE>
|
CacheTyped<TYPE>
|
||||||
& NonNullableKeys<Partial<Omit<ConvertUpdateType<TYPE>, keyof CacheKey<TYPE> | "updateType">>>
|
& NonNullableKeys<Partial<Omit<ConvertKeyData<TYPE>, "updateType">>>
|
||||||
|
|
||||||
|
|
||||||
export type CacheTyped<TYPE extends FactorioEventUpdateType> = {
|
export type CacheTyped<TYPE extends FactorioEventUpdateType> = {
|
||||||
|
|
@ -163,17 +177,15 @@ export namespace EventDataCache {
|
||||||
expirationDurationTicks?: uint,
|
expirationDurationTicks?: uint,
|
||||||
) {
|
) {
|
||||||
this.data = data
|
this.data = data
|
||||||
if (expirationDurationTicks != undefined) {
|
this.expirationDurationTicks = expirationDurationTicks
|
||||||
this.expirationDurationTicks = expirationDurationTicks
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
isExpired(): boolean {
|
|
||||||
const cacheDuration =
|
|
||||||
this.expirationDurationTicks ?? global.DEFAULT_CACHE_DURATION_TICKS2[this.data.updateType]
|
|
||||||
|
|
||||||
return game.tick - this.lastUpdatedTick > cacheDuration
|
function isExpired<TYPE extends FactorioEventUpdateType>(entry: CacheEntry<TYPE>): boolean {
|
||||||
}
|
const expiryDuration =
|
||||||
|
entry.expirationDurationTicks ?? global.defaultCacheDurationTicks[entry.data.updateType]
|
||||||
|
return game.tick - entry.lastUpdatedTick > expiryDuration
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -4,7 +4,7 @@ import {emitPacket} from "../emitKafkatorioPacket";
|
||||||
/** Every 0.1 seconds */
|
/** Every 0.1 seconds */
|
||||||
script.on_nth_tick(6, (nthTick: NthTickEventData) => {
|
script.on_nth_tick(6, (nthTick: NthTickEventData) => {
|
||||||
|
|
||||||
const cachedEvents: Array<EventDataCache.CacheData<any>> = EventDataCache.extractExpired()
|
const cachedEvents: Array<FactorioEventUpdate> = EventDataCache.extractExpired()
|
||||||
|
|
||||||
if (cachedEvents.length > 0) {
|
if (cachedEvents.length > 0) {
|
||||||
log(`nth tick ${nthTick.tick} has ${cachedEvents.length} events`)
|
log(`nth tick ${nthTick.tick} has ${cachedEvents.length} events`)
|
||||||
|
|
@ -22,34 +22,3 @@ script.on_nth_tick(6, (nthTick: NthTickEventData) => {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
|
||||||
//
|
|
||||||
// function createEntityUpdate(cacheKey: EntityCacheKey, events: EventName[]): EntityUpdate | null {
|
|
||||||
//
|
|
||||||
//
|
|
||||||
// return null
|
|
||||||
// }
|
|
||||||
//
|
|
||||||
// interface EntityUpdate {
|
|
||||||
// name: string
|
|
||||||
//
|
|
||||||
// unit_number: uint
|
|
||||||
//
|
|
||||||
// unhandledEvents?: string[]
|
|
||||||
//
|
|
||||||
// chunkPosition: MapChunkPosition
|
|
||||||
// graphics_variation?: uint8
|
|
||||||
// health?: float
|
|
||||||
// isActive?: boolean
|
|
||||||
// isRotatable?: boolean
|
|
||||||
// last_user?: uint
|
|
||||||
// localised_description?: string
|
|
||||||
// localised_name?: string
|
|
||||||
// prototype?: string
|
|
||||||
//
|
|
||||||
// // ghost_localised_description?: string
|
|
||||||
// // ghost_localised_name?: string
|
|
||||||
// // ghost_name?: string
|
|
||||||
// // ghost_prototype?: string
|
|
||||||
// // ghost_unit_number?: uint
|
|
||||||
// }
|
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,6 @@
|
||||||
import {emitPrototypes} from "../config-update/prototypes";
|
import {emitPrototypes} from "../config-update/prototypes";
|
||||||
import {Queue} from "../queue/queue";
|
import {Queue} from "../queue/queue";
|
||||||
|
import {initGlobal} from "../global-init";
|
||||||
import floor = math.floor;
|
import floor = math.floor;
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -8,18 +9,20 @@ commands.add_command(
|
||||||
"kafkatorio innit bruv",
|
"kafkatorio innit bruv",
|
||||||
(e: CustomCommandData) => {
|
(e: CustomCommandData) => {
|
||||||
|
|
||||||
let player = (e.player_index != null) ? game.get_player(e.player_index) : null
|
const player = (e.player_index != null) ? game.get_player(e.player_index) : null
|
||||||
|
|
||||||
if (e.parameter == undefined) {
|
const paramUppercase = e.parameter?.toUpperCase()
|
||||||
|
|
||||||
|
if (paramUppercase == undefined) {
|
||||||
if (player != null) {
|
if (player != null) {
|
||||||
player.print("no parameter")
|
player.print("no parameter")
|
||||||
}
|
}
|
||||||
// do nothing
|
// do nothing
|
||||||
} else if ("PROTOTYPES" == e.parameter.toUpperCase()) {
|
} else if ("PROTOTYPES" == paramUppercase) {
|
||||||
emitPrototypes()
|
emitPrototypes()
|
||||||
} else if (e.parameter.toUpperCase().startsWith("CHUNKS")) {
|
} else if (paramUppercase.startsWith("CHUNKS")) {
|
||||||
|
|
||||||
let size = e.parameter.split(" ")?.[1] ?? null
|
let size = paramUppercase.split(" ")?.[1] ?? null
|
||||||
let radius = (size != null) ? parseInt(size) : 1
|
let radius = (size != null) ? parseInt(size) : 1
|
||||||
|
|
||||||
if (e.player_index != undefined) {
|
if (e.player_index != undefined) {
|
||||||
|
|
@ -60,10 +63,8 @@ commands.add_command(
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else if ("QUEUE_RESET" == e.parameter.toUpperCase()) {
|
} else if (paramUppercase.startsWith("INIT_GLOBAL")) {
|
||||||
Queue.reset()
|
initGlobal(paramUppercase.startsWith("INIT_GLOBAL FORCE"))
|
||||||
} else if ("QUEUE_INIT" == e.parameter.toUpperCase()) {
|
|
||||||
Queue.init()
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,5 @@
|
||||||
|
|
||||||
function isEventType<ED extends EventData | CustomInputEvent>(
|
export function isEventType<ED extends EventData | CustomInputEvent>(
|
||||||
eventData: EventData,
|
eventData: EventData,
|
||||||
type: ED extends CustomInputEvent ? string : EventId<ED>
|
type: ED extends CustomInputEvent ? string : EventId<ED>
|
||||||
): eventData is ED {
|
): eventData is ED {
|
||||||
|
|
|
||||||
|
|
@ -1,4 +1,5 @@
|
||||||
import {EventDataCache} from "../cache/EventDataCache";
|
import {EventDataCache} from "../cache/EventDataCache";
|
||||||
|
import {isEventType} from "./eventTypeCheck";
|
||||||
import CacheKey = EventDataCache.CacheKey;
|
import CacheKey = EventDataCache.CacheKey;
|
||||||
import CacheData = EventDataCache.CacheData;
|
import CacheData = EventDataCache.CacheData;
|
||||||
|
|
||||||
|
|
@ -24,12 +25,17 @@ function mapTilesUpdateDebounce(
|
||||||
},
|
},
|
||||||
data => {
|
data => {
|
||||||
if (data.tiles == undefined) {
|
if (data.tiles == undefined) {
|
||||||
data.tiles = new Map<MapTilePosition, string>()
|
data.tiles = []
|
||||||
}
|
}
|
||||||
|
|
||||||
for (const tile of tiles) {
|
for (const tile of tiles) {
|
||||||
const position: MapTilePosition = {x: tile.position.x, y: tile.position.y}
|
data.tiles.push(
|
||||||
data.tiles.set(position, tile.name)
|
{
|
||||||
|
x: tile.position.x,
|
||||||
|
y: tile.position.y,
|
||||||
|
proto: tile.name,
|
||||||
|
}
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (updater != undefined) {
|
if (updater != undefined) {
|
||||||
|
|
@ -58,6 +64,8 @@ function getSurface(surfaceIndex: uint): LuaSurface | undefined {
|
||||||
script.on_event(
|
script.on_event(
|
||||||
defines.events.on_chunk_generated,
|
defines.events.on_chunk_generated,
|
||||||
(e: OnChunkGeneratedEvent) => {
|
(e: OnChunkGeneratedEvent) => {
|
||||||
|
log(`on_chunk_generated ${e.tick}`)
|
||||||
|
|
||||||
let tiles = getTiles(e.surface, e.area)
|
let tiles = getTiles(e.surface, e.area)
|
||||||
mapTilesUpdateDebounce(e.surface, e.position, tiles)
|
mapTilesUpdateDebounce(e.surface, e.position, tiles)
|
||||||
}
|
}
|
||||||
|
|
@ -66,6 +74,7 @@ script.on_event(
|
||||||
script.on_event(
|
script.on_event(
|
||||||
defines.events.on_chunk_charted,
|
defines.events.on_chunk_charted,
|
||||||
(e: OnChunkChartedEvent) => {
|
(e: OnChunkChartedEvent) => {
|
||||||
|
log(`on_chunk_charted ${e.tick}`)
|
||||||
|
|
||||||
const surface = getSurface(e.surface_index)
|
const surface = getSurface(e.surface_index)
|
||||||
if (surface == undefined) {
|
if (surface == undefined) {
|
||||||
|
|
@ -82,6 +91,7 @@ script.on_event(
|
||||||
script.on_event(
|
script.on_event(
|
||||||
defines.events.script_raised_set_tiles,
|
defines.events.script_raised_set_tiles,
|
||||||
(e: ScriptRaisedSetTilesEvent) => {
|
(e: ScriptRaisedSetTilesEvent) => {
|
||||||
|
log(`script_raised_set_tiles ${e.tick}`)
|
||||||
|
|
||||||
const surface = getSurface(e.surface_index)
|
const surface = getSurface(e.surface_index)
|
||||||
if (surface == undefined) {
|
if (surface == undefined) {
|
||||||
|
|
@ -164,8 +174,14 @@ function onBuildTileEvent(event: OnPlayerBuiltTileEvent | OnRobotBuiltTileEvent)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
script.on_event(defines.events.on_player_built_tile, (e: OnPlayerBuiltTileEvent) => onBuildTileEvent(e))
|
script.on_event(defines.events.on_player_built_tile, (e: OnPlayerBuiltTileEvent) => {
|
||||||
script.on_event(defines.events.on_robot_built_tile, (e: OnRobotBuiltTileEvent) => onBuildTileEvent(e))
|
log(`on_player_built_tile ${e.tick}`)
|
||||||
|
onBuildTileEvent(e)
|
||||||
|
})
|
||||||
|
script.on_event(defines.events.on_robot_built_tile, (e: OnRobotBuiltTileEvent) => {
|
||||||
|
log(`on_robot_built_tile ${e.tick}`)
|
||||||
|
onBuildTileEvent(e)
|
||||||
|
})
|
||||||
|
|
||||||
// script.on_event(
|
// script.on_event(
|
||||||
// defines.events.on_player_mined_tile,
|
// defines.events.on_player_mined_tile,
|
||||||
|
|
@ -187,6 +203,7 @@ script.on_event(defines.events.on_robot_built_tile, (e: OnRobotBuiltTileEvent) =
|
||||||
script.on_event(
|
script.on_event(
|
||||||
defines.events.on_pre_chunk_deleted,
|
defines.events.on_pre_chunk_deleted,
|
||||||
(e: OnPreChunkDeletedEvent) => {
|
(e: OnPreChunkDeletedEvent) => {
|
||||||
|
log(`on_pre_chunk_deleted ${e.tick}`)
|
||||||
|
|
||||||
const surface = getSurface(e.surface_index)
|
const surface = getSurface(e.surface_index)
|
||||||
if (surface == undefined) {
|
if (surface == undefined) {
|
||||||
|
|
|
||||||
|
|
@ -7,6 +7,7 @@ import {
|
||||||
} from "./handlers";
|
} from "./handlers";
|
||||||
import {Queue} from "../queue/queue";
|
import {Queue} from "../queue/queue";
|
||||||
import {EventName} from "../types";
|
import {EventName} from "../types";
|
||||||
|
import {isEventType} from "./eventTypeCheck";
|
||||||
|
|
||||||
|
|
||||||
const mapEventIdToName = new LuaTable<defines.Events, EventName>()
|
const mapEventIdToName = new LuaTable<defines.Events, EventName>()
|
||||||
|
|
|
||||||
15
modules/events-mod/src/main/typescript/main/global-init.ts
Normal file
15
modules/events-mod/src/main/typescript/main/global-init.ts
Normal file
|
|
@ -0,0 +1,15 @@
|
||||||
|
import {Queue} from "./queue/queue";
|
||||||
|
import {EventDataCache} from "./cache/EventDataCache";
|
||||||
|
|
||||||
|
|
||||||
|
export function initGlobal(force: boolean = false) {
|
||||||
|
log(`Initialising Kafkatorio Global variables (force=${force})...`)
|
||||||
|
|
||||||
|
global.MOD_VERSION = script.active_mods[script.mod_name]
|
||||||
|
global.FACTORIO_VERSION = script.active_mods["base"]
|
||||||
|
|
||||||
|
Queue.init(true)
|
||||||
|
EventDataCache.init(true)
|
||||||
|
|
||||||
|
log("Finished initialising Kafkatorio Global variables")
|
||||||
|
}
|
||||||
|
|
@ -10,24 +10,27 @@ export namespace Queue {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
export function init() {
|
export function init(force?: boolean) {
|
||||||
if (global.store == undefined) {
|
|
||||||
log("initialising EventQueue")
|
const isAnythingUndefined = global.store == undefined ||
|
||||||
reset()
|
global.size == undefined ||
|
||||||
|
global.head == undefined ||
|
||||||
|
global.tail == undefined
|
||||||
|
|
||||||
|
log(`Initialising EventQueue globals (force=${force}, isAnythingUndefined=${isAnythingUndefined})`)
|
||||||
|
|
||||||
|
if (force == true || isAnythingUndefined) {
|
||||||
|
global.store = {}
|
||||||
|
global.head = null
|
||||||
|
global.tail = null
|
||||||
|
global.size = 0
|
||||||
}
|
}
|
||||||
|
|
||||||
|
log(`Finished initialising EventQueue`)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
export function reset() {
|
export function size(): uint | undefined {
|
||||||
log("Resetting EventQueue")
|
|
||||||
global.store = {}
|
|
||||||
global.head = null
|
|
||||||
global.tail = null
|
|
||||||
global.size = 0
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
export function size(): uint {
|
|
||||||
return global.size
|
return global.size
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,6 @@
|
||||||
package dev.adamko.kafkatorio.events.schema
|
package dev.adamko.kafkatorio.events.schema
|
||||||
|
|
||||||
|
import dev.adamko.kafkatorio.events.schema.FactorioEventUpdate.FactorioEventUpdateType
|
||||||
import kotlinx.serialization.DeserializationStrategy
|
import kotlinx.serialization.DeserializationStrategy
|
||||||
import kotlinx.serialization.EncodeDefault
|
import kotlinx.serialization.EncodeDefault
|
||||||
import kotlinx.serialization.Serializable
|
import kotlinx.serialization.Serializable
|
||||||
|
|
@ -22,11 +23,24 @@ class FactorioEventUpdatePacket(
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
|
||||||
|
|
||||||
|
|
||||||
|
sealed interface FactorioEventUpdateKey {
|
||||||
|
val updateType: FactorioEventUpdateType
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
sealed interface FactorioEventUpdateData {
|
||||||
|
val updateType: FactorioEventUpdateType
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
@Serializable(with = FactorioEventUpdate.Companion.JsonSerializer::class)
|
@Serializable(with = FactorioEventUpdate.Companion.JsonSerializer::class)
|
||||||
sealed class FactorioEventUpdate {
|
sealed class FactorioEventUpdate : FactorioEventUpdateKey, FactorioEventUpdateData {
|
||||||
|
|
||||||
@EncodeDefault
|
@EncodeDefault
|
||||||
abstract val updateType: FactorioEventUpdateType
|
abstract override val updateType: FactorioEventUpdateType
|
||||||
|
|
||||||
@Serializable
|
@Serializable
|
||||||
enum class FactorioEventUpdateType {
|
enum class FactorioEventUpdateType {
|
||||||
|
|
@ -61,7 +75,7 @@ sealed class FactorioEventUpdate {
|
||||||
|
|
||||||
return when (type) {
|
return when (type) {
|
||||||
FactorioEventUpdateType.PLAYER -> PlayerUpdate.serializer()
|
FactorioEventUpdateType.PLAYER -> PlayerUpdate.serializer()
|
||||||
FactorioEventUpdateType.MAP_CHUNK -> TODO()
|
FactorioEventUpdateType.MAP_CHUNK -> MapChunkUpdate.serializer()
|
||||||
FactorioEventUpdateType.ENTITY -> EntityUpdate.serializer()
|
FactorioEventUpdateType.ENTITY -> EntityUpdate.serializer()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -71,75 +85,154 @@ sealed class FactorioEventUpdate {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
|
||||||
|
|
||||||
|
|
||||||
|
sealed interface PlayerUpdateKey : FactorioEventUpdateKey {
|
||||||
|
val index: PlayerIndex
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
sealed interface PlayerUpdateData : FactorioEventUpdateData {
|
||||||
|
val characterUnitNumber: UnitNumber?
|
||||||
|
val chatColour: Colour?
|
||||||
|
val colour: Colour?
|
||||||
|
val name: String?
|
||||||
|
|
||||||
|
val afkTime: Tick?
|
||||||
|
val ticksToRespawn: Tick?
|
||||||
|
val forceIndex: ForceIndex?
|
||||||
|
val isAdmin: Boolean?
|
||||||
|
val isConnected: Boolean?
|
||||||
|
val isShowOnMap: Boolean?
|
||||||
|
val isSpectator: Boolean?
|
||||||
|
val lastOnline: Tick?
|
||||||
|
val onlineTime: Tick?
|
||||||
|
val position: MapEntityPosition?
|
||||||
|
val surfaceIndex: SurfaceIndex?
|
||||||
|
val tag: String?
|
||||||
|
val diedCause: EntityIdentifiers?
|
||||||
|
|
||||||
|
val bannedReason: String?
|
||||||
|
val kickedReason: String?
|
||||||
|
val disconnectReason: String?
|
||||||
|
/** `true` when a player is removed (deleted) from the game */
|
||||||
|
val isRemoved: Boolean?
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
@Serializable
|
@Serializable
|
||||||
data class PlayerUpdate(
|
data class PlayerUpdate(
|
||||||
val index: PlayerIndex,
|
override val index: PlayerIndex,
|
||||||
|
|
||||||
val characterUnitNumber: UnitNumber? = null,
|
override val characterUnitNumber: UnitNumber? = null,
|
||||||
val chatColour: Colour? = null,
|
override val chatColour: Colour? = null,
|
||||||
val colour: Colour? = null,
|
override val colour: Colour? = null,
|
||||||
val name: String? = null,
|
override val name: String? = null,
|
||||||
|
|
||||||
val afkTime: Tick? = null,
|
override val afkTime: Tick? = null,
|
||||||
val ticksToRespawn: Tick? = null,
|
override val ticksToRespawn: Tick? = null,
|
||||||
val forceIndex: ForceIndex? = null,
|
override val forceIndex: ForceIndex? = null,
|
||||||
val isAdmin: Boolean? = null,
|
override val isAdmin: Boolean? = null,
|
||||||
val isConnected: Boolean? = null,
|
override val isConnected: Boolean? = null,
|
||||||
val isShowOnMap: Boolean? = null,
|
override val isShowOnMap: Boolean? = null,
|
||||||
val isSpectator: Boolean? = null,
|
override val isSpectator: Boolean? = null,
|
||||||
val lastOnline: Tick? = null,
|
override val lastOnline: Tick? = null,
|
||||||
val onlineTime: Tick? = null,
|
override val onlineTime: Tick? = null,
|
||||||
val position: MapEntityPosition? = null,
|
override val position: MapEntityPosition? = null,
|
||||||
val surfaceIndex: SurfaceIndex? = null,
|
override val surfaceIndex: SurfaceIndex? = null,
|
||||||
val tag: String? = null,
|
override val tag: String? = null,
|
||||||
val diedCause: EntityIdentifiers? = null,
|
override val diedCause: EntityIdentifiers? = null,
|
||||||
|
|
||||||
val bannedReason: String? = null,
|
override val bannedReason: String? = null,
|
||||||
val kickedReason: String? = null,
|
override val kickedReason: String? = null,
|
||||||
val disconnectReason: String? = null,
|
override val disconnectReason: String? = null,
|
||||||
/** `true` when a player is removed (deleted) from the game */
|
/** `true` when a player is removed (deleted) from the game */
|
||||||
val isRemoved: Boolean? = null,
|
override val isRemoved: Boolean? = null,
|
||||||
) : FactorioEventUpdate() {
|
) : FactorioEventUpdate(), PlayerUpdateKey, PlayerUpdateData {
|
||||||
@EncodeDefault
|
@EncodeDefault
|
||||||
override val updateType: FactorioEventUpdateType = FactorioEventUpdateType.PLAYER
|
override val updateType: FactorioEventUpdateType = FactorioEventUpdateType.PLAYER
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
|
||||||
|
|
||||||
|
|
||||||
|
sealed interface EntityUpdateKey : EntityIdentifiers, FactorioEventUpdateKey {
|
||||||
|
/** A [unitNumber] is required for caching */
|
||||||
|
override val unitNumber: UnitNumber
|
||||||
|
override val name: String
|
||||||
|
override val type: String
|
||||||
|
}
|
||||||
|
|
||||||
|
sealed interface EntityUpdateData : FactorioEventUpdateData {
|
||||||
|
val chunkPosition: MapChunkPosition?
|
||||||
|
val graphicsVariation: UShort?
|
||||||
|
val health: Float?
|
||||||
|
val isActive: Boolean?
|
||||||
|
val isRotatable: Boolean?
|
||||||
|
val lastUser: UInt?
|
||||||
|
val localisedDescription: String?
|
||||||
|
val localisedName: String?
|
||||||
|
val prototype: PrototypeName?
|
||||||
|
}
|
||||||
|
|
||||||
@Serializable
|
@Serializable
|
||||||
data class EntityUpdate(
|
data class EntityUpdate(
|
||||||
/** A [unitNumber] is required for caching */
|
|
||||||
override val unitNumber: UnitNumber,
|
override val unitNumber: UnitNumber,
|
||||||
override val name: String,
|
override val name: String,
|
||||||
override val type: String,
|
override val type: String,
|
||||||
|
|
||||||
val chunkPosition: MapChunkPosition? = null,
|
override val chunkPosition: MapChunkPosition? = null,
|
||||||
val graphicsVariation: UShort? = null,
|
override val graphicsVariation: UShort? = null,
|
||||||
val health: Float? = null,
|
override val health: Float? = null,
|
||||||
val isActive: Boolean? = null,
|
override val isActive: Boolean? = null,
|
||||||
val isRotatable: Boolean? = null,
|
override val isRotatable: Boolean? = null,
|
||||||
val lastUser: UInt? = null,
|
override val lastUser: UInt? = null,
|
||||||
val localisedDescription: String? = null,
|
override val localisedDescription: String? = null,
|
||||||
val localisedName: String? = null,
|
override val localisedName: String? = null,
|
||||||
val prototype: PrototypeName? = null,
|
override val prototype: PrototypeName? = null,
|
||||||
) : FactorioEventUpdate(), EntityIdentifiers {
|
) : FactorioEventUpdate(), EntityIdentifiers, EntityUpdateKey, EntityUpdateData {
|
||||||
@EncodeDefault
|
@EncodeDefault
|
||||||
override val updateType: FactorioEventUpdateType = FactorioEventUpdateType.ENTITY
|
override val updateType: FactorioEventUpdateType = FactorioEventUpdateType.ENTITY
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
|
||||||
|
|
||||||
|
|
||||||
|
sealed interface MapChunkUpdateKey : FactorioEventUpdateKey {
|
||||||
|
val chunkPosition: MapChunkPosition
|
||||||
|
val surfaceIndex: SurfaceIndex
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
sealed interface MapChunkUpdateData : FactorioEventUpdateData {
|
||||||
|
val player: PlayerIndex?
|
||||||
|
val robot: EntityIdentifiers?
|
||||||
|
val force: ForceIndex?
|
||||||
|
/** updated tiles - might be partial */
|
||||||
|
val tiles: List<MapTile>?
|
||||||
|
val isDeleted: Boolean?
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
@Serializable
|
@Serializable
|
||||||
data class MapChunkUpdate(
|
data class MapChunkUpdate(
|
||||||
val chunkPosition: MapChunkPosition,
|
override val chunkPosition: MapChunkPosition,
|
||||||
val surfaceIndex: SurfaceIndex,
|
override val surfaceIndex: SurfaceIndex,
|
||||||
|
|
||||||
val player: PlayerIndex? = null,
|
override val player: PlayerIndex? = null,
|
||||||
val robot: EntityIdentifiers? = null,
|
override val robot: EntityIdentifiers? = null,
|
||||||
val force: ForceIndex? = null,
|
override val force: ForceIndex? = null,
|
||||||
|
// note: this must be a List, not a Map<Location, ProtoName>
|
||||||
/** Might be a partial list of updated tiles */
|
// because JSON can't have non-string keys.
|
||||||
val tiles: Map<MapTilePosition, PrototypeName>? = null,
|
override val tiles: List<MapTile>? = null,
|
||||||
val isDeleted: Boolean? = null,
|
override val isDeleted: Boolean? = null,
|
||||||
) : FactorioEventUpdate() {
|
) : FactorioEventUpdate(), MapChunkUpdateKey, MapChunkUpdateData {
|
||||||
@EncodeDefault
|
@EncodeDefault
|
||||||
override val updateType: FactorioEventUpdateType = FactorioEventUpdateType.MAP_CHUNK
|
override val updateType: FactorioEventUpdateType = FactorioEventUpdateType.MAP_CHUNK
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
|
||||||
|
|
|
||||||
|
|
@ -14,12 +14,19 @@ fun main(args: Array<String>) {
|
||||||
TypeScriptGenerator(
|
TypeScriptGenerator(
|
||||||
rootClasses = buildSet {
|
rootClasses = buildSet {
|
||||||
addAll(KafkatorioPacket::class.sealedSubclasses)
|
addAll(KafkatorioPacket::class.sealedSubclasses)
|
||||||
|
|
||||||
addAll(FactorioObjectData::class.sealedSubclasses)
|
addAll(FactorioObjectData::class.sealedSubclasses)
|
||||||
|
|
||||||
addAll(FactorioPrototype::class.sealedSubclasses)
|
addAll(FactorioPrototype::class.sealedSubclasses)
|
||||||
add(FactorioPrototypes::class)
|
add(FactorioPrototypes::class)
|
||||||
add(FactorioConfigurationUpdate::class)
|
add(FactorioConfigurationUpdate::class)
|
||||||
|
|
||||||
|
|
||||||
add(FactorioEventUpdatePacket::class)
|
add(FactorioEventUpdatePacket::class)
|
||||||
addAll(FactorioEventUpdate::class.sealedSubclasses)
|
addAll(FactorioEventUpdate::class.sealedSubclasses)
|
||||||
|
addAll(FactorioEventUpdateKey::class.sealedSubclasses)
|
||||||
|
addAll(FactorioEventUpdateData::class.sealedSubclasses)
|
||||||
|
|
||||||
},
|
},
|
||||||
mappings = mapOf(
|
mappings = mapOf(
|
||||||
// builtin Factorio numeric types > `typed-factorio/generated/builtin-types.d.ts`
|
// builtin Factorio numeric types > `typed-factorio/generated/builtin-types.d.ts`
|
||||||
|
|
@ -66,18 +73,38 @@ private fun splitDefinitions(definitions: String): Map<String, String> {
|
||||||
return definitions
|
return definitions
|
||||||
.split("\n\n")
|
.split("\n\n")
|
||||||
.groupBy { def ->
|
.groupBy { def ->
|
||||||
|
|
||||||
|
|
||||||
when {
|
when {
|
||||||
"extends FactorioObjectData " in def ||
|
|
||||||
"interface FactorioObjectData " in def ||
|
"interface FactorioObjectData " in def ||
|
||||||
"type ObjectName " in def -> "object-data.d.ts"
|
"type ObjectName " in def ||
|
||||||
|
def.contains(Regex("interface.+extends.+(FactorioObjectData).*"))
|
||||||
|
-> "object-data.d.ts"
|
||||||
|
|
||||||
"extends FactorioPrototype " in def ||
|
"extends FactorioPrototype " in def ||
|
||||||
"interface FactorioPrototypes " in def ||
|
"interface FactorioPrototypes " in def ||
|
||||||
"interface FactorioPrototype " in def ||
|
"interface FactorioPrototype " in def ||
|
||||||
"type PrototypeObjectName " in def -> "prototype.d.ts"
|
"type PrototypeObjectName " in def -> "prototype.d.ts"
|
||||||
|
|
||||||
"extends FactorioConfigurationUpdate " in def ||
|
"extends FactorioConfigurationUpdate " in def ||
|
||||||
"interface FactorioConfigurationUpdate " in def ||
|
"interface FactorioConfigurationUpdate " in def ||
|
||||||
"FactorioGameDataUpdate " in def ||
|
"FactorioGameDataUpdate " in def ||
|
||||||
"FactorioModInfo " in def -> "config-update.d.ts"
|
"FactorioModInfo " in def -> "config-update.d.ts"
|
||||||
|
|
||||||
|
"interface FactorioEventUpdatePacket" in def ||
|
||||||
|
"type FactorioEventUpdateType =" in def ||
|
||||||
|
"interface FactorioEventUpdateKey {" in def ||
|
||||||
|
"interface FactorioEventUpdateData {" in def ||
|
||||||
|
def.contains(
|
||||||
|
Regex(
|
||||||
|
"""
|
||||||
|
interface.+extends.+(FactorioEventUpdate|PlayerUpdateKey|PlayerUpdateData).*
|
||||||
|
""".trimIndent()
|
||||||
|
)
|
||||||
|
)
|
||||||
|
-> "update.d.ts"
|
||||||
|
|
||||||
else -> "schema.d.ts"
|
else -> "schema.d.ts"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue