Fix floor-start shifts booting inert, and the floor carrying last night into this one
applyLocation() only moved flags — it never announced the move. FloorDemoScene latches `present` when it binds the night context, which (now the night preloads every prop texture) happens BEFORE the initial applyLocation runs, so every floor-start shift — bartender, glassie, DJ — came up visible but completely inert, with the audio filter still in door mode. The night now emits night:phaseChange and audio:location for the starting post. Phaser reuses scene instances across restarts, so class-field initialisers run once per GAME, not once per night: a DJ shift left djMode set and the next night's floor booted with movement locked and the keyboard eaten, last night's puddles kept slipping people through destroyed sprites, and the handled-patron sets marked fresh arrivals as already dealt with. resetNightState() now wipes all of it in create(). Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
parent
79cd80dc01
commit
164b4480c5
@ -310,7 +310,17 @@ export class NightScene extends Phaser.Scene {
|
|||||||
// Door and Floor BOTH run all night; the flags below decide which one
|
// Door and Floor BOTH run all night; the flags below decide which one
|
||||||
// the player is inhabiting. Floor starts hidden.
|
// the player is inhabiting. Floor starts hidden.
|
||||||
// The roster decides where you stand when the doors open (design §6).
|
// The roster decides where you stand when the doors open (design §6).
|
||||||
this.time.delayedCall(0, () => this.applyLocation(this.role.startLoc));
|
this.time.delayedCall(0, () => {
|
||||||
|
this.applyLocation(this.role.startLoc);
|
||||||
|
// ...and ANNOUNCE it. applyLocation only moves flags; the room latches
|
||||||
|
// onto the event. FloorDemoScene reads `present` when it binds this
|
||||||
|
// context, which — now that the night preloads every prop texture —
|
||||||
|
// happens before this runs, so a floor-start shift (bartender, glassie,
|
||||||
|
// DJ) came up visible but completely inert, and the audio filter stayed
|
||||||
|
// in door mode while you stood on the dancefloor.
|
||||||
|
this.bus.emit('night:phaseChange', { location: this.role.startLoc });
|
||||||
|
this.bus.emit('audio:location', { location: this.role.startLoc });
|
||||||
|
});
|
||||||
};
|
};
|
||||||
if (missing.length === 0) return launch();
|
if (missing.length === 0) return launch();
|
||||||
for (const k of missing) this.load.image(`gen:prop:${k}`, `props/${k}.png`);
|
for (const k of missing) this.load.image(`gen:prop:${k}`, `props/${k}.png`);
|
||||||
|
|||||||
@ -203,6 +203,7 @@ export class FloorDemoScene extends Phaser.Scene {
|
|||||||
|
|
||||||
create(data?: { night?: NightContext }): void {
|
create(data?: { night?: NightContext }): void {
|
||||||
this.nightCtx = data?.night ?? null;
|
this.nightCtx = data?.night ?? null;
|
||||||
|
this.resetNightState();
|
||||||
// Wired explicitly: Phaser does not invoke a `shutdown` METHOD on a Scene
|
// Wired explicitly: Phaser does not invoke a `shutdown` METHOD on a Scene
|
||||||
// subclass; without this, listeners and sprites leak on every scene stop.
|
// subclass; without this, listeners and sprites leak on every scene stop.
|
||||||
this.events.once(Phaser.Scenes.Events.SHUTDOWN, () => this.teardown());
|
this.events.once(Phaser.Scenes.Events.SHUTDOWN, () => this.teardown());
|
||||||
@ -217,6 +218,42 @@ export class FloorDemoScene extends Phaser.Scene {
|
|||||||
this.load.start();
|
this.load.start();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Wipe everything that belongs to ONE night.
|
||||||
|
*
|
||||||
|
* Phaser reuses the scene instance across restarts, so class-field
|
||||||
|
* initialisers run exactly once in the lifetime of the game — every field
|
||||||
|
* below would otherwise carry last night into this one. That is not
|
||||||
|
* theoretical: a DJ shift left `djMode` set, so the next night's floor booted
|
||||||
|
* with movement locked and the keyboard eaten; last night's puddles kept
|
||||||
|
* slipping people through sprites Phaser had already destroyed; and the
|
||||||
|
* handled-patron sets marked fresh arrivals as already dealt with, because
|
||||||
|
* patron ids restart with the run.
|
||||||
|
*/
|
||||||
|
private resetNightState(): void {
|
||||||
|
this.djMode = false;
|
||||||
|
this.djBuild = null;
|
||||||
|
this.barMode = false;
|
||||||
|
this.carryingCup = false;
|
||||||
|
this.mop = null;
|
||||||
|
// The graphics these referenced went down with the previous scene shutdown;
|
||||||
|
// dropping the references is the whole job.
|
||||||
|
this.puddles = [];
|
||||||
|
this.vomitCount = 0;
|
||||||
|
this.filming = null;
|
||||||
|
this.fainter = null;
|
||||||
|
this.rack = null;
|
||||||
|
this.escorting = null;
|
||||||
|
this.target = null;
|
||||||
|
this.liveFight = null;
|
||||||
|
this.uvMode = false;
|
||||||
|
this.jointDealt.clear();
|
||||||
|
this.maggotSeen.clear();
|
||||||
|
this.spotted.clear();
|
||||||
|
this.cutOffDealt.clear();
|
||||||
|
this.slipCooldown.clear();
|
||||||
|
}
|
||||||
|
|
||||||
private loadGenProps(): void {
|
private loadGenProps(): void {
|
||||||
const manifest = this.cache.json.get('propManifest') as { props?: string[] } | undefined;
|
const manifest = this.cache.json.get('propManifest') as { props?: string[] } | undefined;
|
||||||
const kinds = manifest?.props ?? [];
|
const kinds = manifest?.props ?? [];
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user