emergence-mini-dilles/web/style.css
Jeuners e7ad200bb0 Add Replay / timeline animation to web UI
- New backend endpoint /api/history?hours=N returns chronological
  replay frames reconstructed from the events table: agent positions,
  energy/knowledge/influence/credits/mood, tool, model, tau, pace,
  clocks and drift per tick/action.
- Frontend: new Replay panel with Play/Pause, timeline slider,
  Live button and history window selector (1h/3h/6h/12h/24h).
- Canvas draw() now renders either the live snapshot or the current
  replay frame; agent cards and drift/clock panels sync in replay mode.
- Overlay on the canvas shows current tick, timestamp, agent action
  and model while replaying.
- Also adds the missing refreshTexts() implementation so the
  Generated Texts panel is populated.

Verified: /api/history returns frames; JS syntax check passes;
pytest 100/100; web UI renders with new Replay controls.
2026-06-15 14:35:16 +02:00

92 lines
6.2 KiB
CSS

* { box-sizing: border-box; }
body { margin: 0; font-family: ui-monospace, "SF Mono", Menlo, monospace;
background: #0b0f14; color: #d6e2ee; }
header { display: flex; justify-content: space-between; align-items: baseline;
padding: 12px 18px; border-bottom: 1px solid #1c2733; background: #0e141b; }
header h1 { margin: 0; font-size: 18px; letter-spacing: 1px; color: #6cf0c2; }
.meta span { margin-left: 14px; color: #8aa1b6; font-size: 12px; }
.meta b { color: #d6e2ee; }
.ws-status.connected { color: #6cf0c2; }
.ws-status.disconnected { color: #ff6c6c; }
.llm-info { color: #82aaff; font-size: 11px; }
.clock-card { background: #0a1018; border: 1px solid #1c2733; padding: 6px 8px; margin: 4px 0; }
.clock-card .name { font-weight: bold; }
.clock-card .tau-bar { height: 4px; background: #1c2733; border-radius: 2px; margin: 4px 0; }
.clock-card .tau-bar > i { display: block; height: 100%; border-radius: 2px; }
.clock-card .meta { color: #6c8aa6; font-size: 10px; }
.drift-warn { background: #2a1018; border: 1px solid #ff6c6c; padding: 8px; margin: 6px 0; color: #ff8fb1; font-size: 11px; }
.drift-ok { background: #0a1018; border: 1px solid #1c2733; padding: 8px; margin: 6px 0; color: #6cf0c2; font-size: 11px; }
.text-card { background: #0a1018; border: 1px solid #1c2733; padding: 8px; margin: 6px 0; font-size: 12px; }
.text-card .head { display: flex; justify-content: space-between; align-items: baseline; margin-bottom: 4px; }
.text-card .agent { font-weight: bold; }
.text-card .agent.anchor { color: #ffd166; }
.text-card .agent.flora { color: #6cf0c2; }
.text-card .agent.lovely { color: #ff8fb1; }
.text-card .agent.spark { color: #82aaff; }
.text-card .model { font-size: 9px; padding: 1px 4px; border-radius: 2px; background: #1c2733; color: #82aaff; }
.text-card .model.local { color: #6cf0c2; }
.text-card .model.cloud { color: #ffd166; }
.text-card .kind { font-size: 9px; padding: 1px 4px; border-radius: 2px; background: #2a1a18; color: #ff8fb1; text-transform: uppercase; }
.text-card .body { color: #d6e2ee; line-height: 1.4; margin-top: 4px; word-wrap: break-word; }
.text-card .body.llm { color: #6cf0c2; }
.text-card .body.fallback { color: #8aa1b6; font-style: italic; }
.text-card .ts { color: #6c8aa6; font-size: 10px; }
main { display: grid; grid-template-columns: 1fr 360px; gap: 16px; padding: 16px; }
.canvas-wrap { background: #0e141b; padding: 10px; border: 1px solid #1c2733; }
canvas { display: block; width: 100%; height: auto; image-rendering: pixelated;
background: #060a0e; }
.legend { padding-top: 8px; font-size: 12px; color: #8aa1b6; }
.legend .dot { display: inline-block; width: 10px; height: 10px; border-radius: 50%;
margin-right: 4px; margin-left: 12px; vertical-align: middle; }
.dot.anchor { background: #ffd166; }
.dot.flora { background: #6cf0c2; }
.dot.lovely { background: #ff8fb1; }
.dot.spark { background: #82aaff; }
aside { background: #0e141b; padding: 14px; border: 1px solid #1c2733;
height: calc(100vh - 80px); overflow-y: auto; }
aside h2 { font-size: 12px; text-transform: uppercase; letter-spacing: 1px;
color: #6cf0c2; margin: 18px 0 6px; }
#feed { list-style: none; padding: 0; margin: 0; max-height: 220px; overflow-y: auto; }
#feed li { font-size: 12px; padding: 4px 0; border-bottom: 1px dotted #1c2733; }
#feed li .who { color: #82aaff; }
#feed li .tool { color: #ffd166; }
#feed li .why { color: #6c8aa6; font-style: italic; }
.agent-card { background: #0a1018; border: 1px solid #1c2733; padding: 8px; margin: 6px 0; }
.agent-card h3 { margin: 0 0 4px; font-size: 13px; }
.agent-card .model-tag { display: inline-block; font-size: 9px; padding: 1px 5px; border-radius: 3px; margin-left: 4px; vertical-align: middle; font-weight: normal; }
.agent-card .model-tag.local { background: #1a2a1a; color: #6cf0c2; border: 1px solid #2a3a2a; }
.agent-card .model-tag.cloud { background: #2a2a1a; color: #ffd166; border: 1px solid #3a3a1a; }
.agent-card .model-tag.short { background: #1c2733; color: #8aa1b6; }
.agent-card .bar { height: 4px; background: #1c2733; margin: 2px 0; border-radius: 2px; }
.agent-card .bar > i { display: block; height: 100%; border-radius: 2px; }
.bar.energy > i { background: #ffd166; }
.bar.knowledge > i { background: #82aaff; }
.bar.influence > i { background: #ff8fb1; }
.bar.credits > i { background: #6cf0c2; }
.proposal { background: #0a1018; border: 1px solid #1c2733; padding: 8px; margin: 6px 0; }
.proposal h4 { margin: 0 0 4px; font-size: 13px; color: #ffd166; }
.proposal small { color: #6c8aa6; }
#constitution { font-size: 12px; }
#constitution .article { background: #0a1018; border: 1px solid #1c2733; padding: 8px;
margin: 6px 0; }
#constitution .article b { color: #6cf0c2; }
form#manual { display: grid; gap: 6px; }
form#manual label { display: grid; gap: 2px; font-size: 11px; color: #8aa1b6; }
form#manual select, form#manual input { background: #060a0e; color: #d6e2ee;
border: 1px solid #1c2733; padding: 6px;
font-family: inherit; }
form#manual button { background: #6cf0c2; color: #060a0e; border: 0; padding: 6px;
font-weight: bold; cursor: pointer; }
form#manual button:hover { background: #82ffd6; }
.replay-panel { margin-top: 12px; padding: 10px; background: #0a1018; border: 1px solid #1c2733; }
.replay-panel h2 { margin: 0 0 8px; font-size: 12px; text-transform: uppercase; letter-spacing: 1px; color: #6cf0c2; }
.replay-controls { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.replay-controls button { background: #1c2733; color: #d6e2ee; border: 1px solid #2c3a4a; padding: 5px 10px; font-family: inherit; cursor: pointer; border-radius: 2px; }
.replay-controls button:hover { background: #2c3a4a; }
.replay-controls button.active { background: #6cf0c2; color: #060a0e; font-weight: bold; border-color: #6cf0c2; }
.replay-controls input[type=range] { flex: 1; min-width: 120px; }
.replay-controls select { background: #060a0e; color: #d6e2ee; border: 1px solid #1c2733; padding: 4px; font-family: inherit; }
#replayTime { font-size: 11px; color: #8aa1b6; min-width: 90px; }
.replay-mode { display: none; font-size: 10px; color: #ff8fb1; margin-top: 6px; text-transform: uppercase; }
.replay-panel.active .replay-mode { display: block; }