feat: Ghost Log HUD + evil meter + tells (Workstream D)
App-shell HUD (mounted in App.tsx alongside HauntingLayer, visible on every screen) that shows ambient idle status until a séance is active, then streams `tell` WS frames as terminal-style log lines with a "hacker witch" crescent-arc evil-meter gauge (occult sigils/runes fused with Transcript.tsx's monospace log vocabulary). - lib/evilMeter.ts: pure function computing a malevolent<->benevolent belief from the accumulated tell history — starts wide/uncertain, narrows geometrically and shifts per tell (deterministic hash of the tell text, since tells never leak ground truth), and snaps to definitive certainty on a successful ritual_complete's revealed.alignment. Fully unit tested (narrowing, ordering, determinism, ritual override, idle/empty history). - lib/ghostLogBus.ts: tiny typed event bus (mirrors lib/haunting.ts's HauntBus) so the app-shell-level GhostLog can react to live séance frames — SeanceProvider is only mounted inside the séance route, so a shell-level sibling can't read its context directly. - state/seance.tsx: publish entity/tell/ritual_complete onto the bus, and session_end on provider teardown so the HUD falls back to idle when the seeker leaves the séance page. - lib/types.ts: add the `tell` and `ritual_complete` server frames from the Character Depth spec's Contract section (only what this workstream consumes). - components/GhostLog.tsx/.css: the HUD itself, plus i18n keys in en.json/es.json. 168/168 frontend tests pass (137 pre-existing + 20 evilMeter + 11 GhostLog); tsc -b and the i18n coverage pretest are clean. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
@@ -4,6 +4,7 @@
|
||||
import { BrowserRouter, Route, Routes } from 'react-router-dom'
|
||||
import { AuthProvider } from './state/auth'
|
||||
import { HauntingLayer } from './components/HauntingLayer'
|
||||
import { GhostLog } from './components/GhostLog'
|
||||
import { CodexEntityPage } from './pages/CodexEntityPage'
|
||||
import { CodexPage } from './pages/CodexPage'
|
||||
import { EnterPage } from './pages/EnterPage'
|
||||
@@ -20,6 +21,7 @@ function App() {
|
||||
<div className="crt-vignette" />
|
||||
</div>
|
||||
<HauntingLayer />
|
||||
<GhostLog />
|
||||
<Routes>
|
||||
<Route path="/" element={<LandingPage />} />
|
||||
<Route path="/enter" element={<EnterPage />} />
|
||||
|
||||
Reference in New Issue
Block a user