diff --git a/backend/game.ts b/backend/game.ts index db4b8a5..ab7a554 100644 --- a/backend/game.ts +++ b/backend/game.ts @@ -2,7 +2,7 @@ import EventEmitter from "node:events" import type { PlayerBroadcast } from "../shared/broadcast" import { script } from "../shared/script" import type { SceneDefinition } from "../shared/script/types" -import { sceneTypesById } from "./scene-types" +import { type SceneEvent, sceneTypesById } from "./scene-types" import type { Tagged } from "type-fest" import type { SessionId } from "./session" @@ -32,7 +32,7 @@ export class Game { getConnectionPlayerBroadcasts(): PlayerBroadcast[] { const events: PlayerBroadcast[] = [] events.push({ type: "scene-changed", sceneId: this.currentScene.id }) - events.push(...this.currentScene.state.getConnectionEvents()) + events.push(...this.currentScene.state.getConnectionEvents().map((event: SceneEvent) => ({ type: "scene-event", event }))) return events } @@ -45,12 +45,14 @@ export class Game { const definition = script.scenesById.get(sceneId) if (definition === undefined) throw new Error(`Unknown scene: ${sceneId}`) const type = sceneTypesById[definition.type] + + this.eventBus.emit("player-broadcast", { type: "scene-changed", sceneId: sceneId }) + this.currentScene = { id: sceneId, definition, state: type.createState(this, definition as any) } - this.eventBus.emit("player-broadcast", { type: "scene-changed", sceneId: sceneId }) } withSceneState(type: Type, block: (state: ReturnType) => R): R | null { diff --git a/backend/scene-types/interaction.ts b/backend/scene-types/interaction.ts index 7a07495..d6dbb4b 100644 --- a/backend/scene-types/interaction.ts +++ b/backend/scene-types/interaction.ts @@ -19,14 +19,14 @@ export class InteractionSceneState implements SceneState private objectVisibilityById = new Map() constructor(private game: Game, private definition: InteractionSceneDefinition) { - definition.objectsById.entries().forEach(([id, o]) => this.objectVisibilityById.set(id, o.reveal)) + definition.objectsById.entries().forEach(([id, o]) => this.setObjectVisibility(id, o.reveal)) } getConnectionEvents(): InteractionSceneEvent[] { const events: InteractionSceneEvent[] = [] events.push(this.getVotesChangedEvent()) - this.objectVisibilityById.entries().forEach(([id, isVisible]) => events.push({ type: "object-visibility-changed", id, isVisible })) + this.objectVisibilityById.entries().forEach(([id, isVisible]) => events.push({ type: "object-visibility-changed", objectId: id, isVisible })) if (this.ongoingInteractionExecution !== null) events.push({ type: "interaction-execution-started", interaction: this.ongoingInteractionExecution }) @@ -107,7 +107,7 @@ export class InteractionSceneState implements SceneState switch (interaction.type) { case "use": if (interaction.consume) { - this.emit({ type: "object-visibility-changed", id: interaction.objectId, isVisible: false }) + this.emit({ type: "object-visibility-changed", objectId: interaction.objectId, isVisible: false }) } break @@ -139,10 +139,9 @@ export class InteractionSceneState implements SceneState setObjectVisibility(objectId: string, isVisible: boolean) { const current = this.objectVisibilityById.get(objectId) - if (current === undefined) throw new Error(`Unknown object: ${objectId}`) if (current === isVisible) return this.objectVisibilityById.set(objectId, isVisible) - this.emit({ type: "object-visibility-changed", id: objectId, isVisible }) + this.emit({ type: "object-visibility-changed", objectId: objectId, isVisible }) } } \ No newline at end of file diff --git a/frontend/App.vue b/frontend/App.vue index dd4c2e3..7836df3 100644 --- a/frontend/App.vue +++ b/frontend/App.vue @@ -1,8 +1,8 @@