1e51ef7def
- Konzept/, didaktik_geografie/, didaktik_simulation/, v2-modules/, v2-platform/ - 12 code-workspace-Files - STATUS-*.md - viele M/D/R-Änderungen an bereits getrackten Files - .gitignore verstärkt: **/.humaninput/, **/secret_keys.txt Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
207 lines
8.2 KiB
Markdown
207 lines
8.2 KiB
Markdown
---
|
||
titel: Tech-Spec — Autobahn-Abfahrt-Minispiel als Modul
|
||
zielgruppe: Externer Entwickler*in (oder Atlas-Instanz), die das Spiel in passender Technologie neu baut
|
||
host: Logistik Europa (App/sims/logistik/game.html)
|
||
stand: 2026-04-25
|
||
---
|
||
|
||
# Spec — Autobahn-Abfahrt-Minispiel
|
||
|
||
Das Spiel wird in der Logistik-Simulation als **Overlay** geöffnet, sobald
|
||
ein LKW an einem ausgewählten Knotenpunkt die Autobahn verlässt. Während
|
||
das Spiel läuft, **steht die Logistik-Sim still**. Ergebnis (Bonus / Strafe
|
||
/ Unfall) wird zurück an die Logistik gemeldet.
|
||
|
||
Das Spiel ist ein **eigenständiges Modul** ohne Abhängigkeit zur
|
||
Logistik-Engine. Logistik ruft nur eine Init-Funktion auf und bekommt
|
||
einen Callback.
|
||
|
||
## 1. Schnittstelle
|
||
|
||
### Eintritt: ein einziger globaler Init-Funktions-Aufruf
|
||
|
||
```js
|
||
window.lgAutobahnGame.start({
|
||
container: HTMLElement, // Logistik liefert ein leeres div, exklusiv für das Spiel
|
||
scenario: 'bregenz' | 'salzburg' | 'innsbruck' | 'muenchen' | 'leipzig' | 'verona',
|
||
driverName: 'Anna', // optional, für Anzeige
|
||
truckLabel: 'Mittlerer LKW', // optional, für Anzeige
|
||
easyMode: false, // optional, vereinfachte Sprache/Hilfen
|
||
onEnd: (result) => { ... }, // Callback, EXAKT EINMAL aufgerufen
|
||
});
|
||
```
|
||
|
||
### Austritt: Callback `onEnd(result)` — Pflichtfeld
|
||
|
||
```js
|
||
result = {
|
||
outcome: 'success' | 'late' | 'crash',
|
||
scenario: 'bregenz',
|
||
// success: korrekte Abfahrt erkannt + keine Kollision
|
||
// late: Abfahrt verpasst oder falsche Spur (Strafzeit zu addieren)
|
||
// crash: Auffahren oder in Baustelle gekracht (Vehicle-Ausfall)
|
||
|
||
// Optional: für späteres Tuning
|
||
decisionTimeMs: 12500, // wie lange war der Spieler im Spiel
|
||
laneChanges: 3,
|
||
brakeUsed: true,
|
||
};
|
||
```
|
||
|
||
Logistik mappt das auf:
|
||
- **success** → Bonus-Pill (45 min Ladezeit) + positive Voice-Line
|
||
- **late** → +30 min auf Restfahrt-Dauer + neutrale Voice
|
||
- **crash** → Vehicle ausgefallen für 24 Sim-Stunden + Reparaturkosten + Crash-Sound
|
||
|
||
Logistik kümmert sich selbst darum, das `container`-DOM-Element zu
|
||
entfernen, sobald `onEnd` gefeuert hat.
|
||
|
||
## 2. Lifecycle
|
||
|
||
1. Logistik erstellt ein leeres `<div>` über der Karte (z.B. Modal-Overlay), füllt
|
||
es als `container` an `start()`.
|
||
2. Modul rendert sein Spielfeld komplett **innerhalb dieses Divs**.
|
||
3. Spieler interagiert. Sim-Zeit in Logistik steht still (das ist Logistik-Sache).
|
||
4. Nach Spiel-Ende: Modul ruft `onEnd(result)` auf, **genau einmal**.
|
||
5. Modul macht keinen `container.innerHTML = ''` — das macht Logistik nach
|
||
Callback-Empfang.
|
||
|
||
**Wichtig**: `onEnd` darf nur **einmal** feuern, auch bei Fehler/Abbruch.
|
||
|
||
## 3. Technische Vorgaben
|
||
|
||
### Was MUSS gehen
|
||
|
||
- **Vanilla JavaScript**. Kein Framework-Bundle.
|
||
- **Kein globales DOM** anfassen außerhalb des `container`. Kein
|
||
`document.body.appendChild`, kein `position: fixed` direkt aufs Body.
|
||
- **CSS-Prefix `lg-aut-`** auf allen Klassen. Keine generischen Selektoren
|
||
wie `button { ... }`.
|
||
- Asset-Loading **relativ** zum Modul-Pfad oder per Daten-URL. Kein CDN
|
||
zur Laufzeit (DSGVO + Schul-Offline-Tauglichkeit).
|
||
- **Tastatur + Touch + Maus** als Eingabe (Logistik wird primär auf iPad
|
||
Landscape genutzt, 1180 × 820, Touch-Ziele ≥ 36 px).
|
||
- **Pausierbar bei `visibility: hidden` des Containers** — wenn der Tab
|
||
in den Hintergrund geht oder Logistik den Container verbirgt, soll der
|
||
RAF-Loop sich selbst stoppen und bei `visible` weiterlaufen.
|
||
|
||
### Was darf gehen
|
||
|
||
- **Three.js erlaubt**, wenn nötig — Logistik nutzt Leaflet (kein WebGL).
|
||
Bitte lokal hosten unter `App/sims/logistik/assets/vendor/three/` (kein CDN).
|
||
- **Web Audio API** für Sounds (Motorgeräusch, Bremsen, Crash). Volumes
|
||
niedriger als 0.4 default, damit es nicht über die Logistik-Sprachausgabe
|
||
brüllt. Logistik wird selbst die eigene Musik dücken während Modul aktiv.
|
||
- **CanvasRenderingContext2D** auch erlaubt, wenn Three nicht nötig.
|
||
- **Eigene Schriftarten** als `@font-face` im Modul-eigenen `<style>` —
|
||
nicht im Logistik-Header.
|
||
|
||
### Was nicht erlaubt ist
|
||
|
||
- Kein Schreiben in `localStorage` (Logistik nutzt das schon und ist quota-empfindlich).
|
||
- Keine Cookies, kein `window.alert/confirm/prompt`.
|
||
- Keine externen Netzwerk-Calls. Kein fetch. Kein WebSocket.
|
||
- Keine Modifikation von `window.*` außer dem dokumentierten `window.lgAutobahnGame`.
|
||
- Kein eigener Click-Handler auf `document` oder `window` ohne dass er beim
|
||
`onEnd` wieder removeEventListener-ed wird (sonst Leak in Logistik).
|
||
|
||
## 4. Sechs Knotenpunkt-Szenarien
|
||
|
||
Logistik wählt das Szenario per `scenario`-Property. Liste der sechs:
|
||
|
||
| Szenario-Key | Knoten | Empfohlene Geografie |
|
||
|---|---|---|
|
||
| `bregenz` | Bregenz, A14 | Westautobahn-Verzweigung, Vorarlberg |
|
||
| `salzburg` | Salzburg West, A1/A10 | Tauern-Abzweigung, Salzburger Land |
|
||
| `innsbruck` | Innsbruck, A12/A13 | Brenner-Süd-Abfahrt, Tirol |
|
||
| `muenchen` | München-Nord, A9/A99 | Autobahn-Ring, Bayern |
|
||
| `leipzig` | Leipzig West, A9/A14 | Sachsen, viel Verkehr |
|
||
| `verona` | Verona Nord, A22 | Brenner-Süd, Italien |
|
||
|
||
Pro Szenario im Modul fest definiert: Beschilderung, korrekte Spur,
|
||
Hindernisse, Ausfahrt-Position. Logistik liefert nur den Key.
|
||
|
||
## 5. Visuelle Integration mit Logistik
|
||
|
||
- Logistik-Farbpalette (Atlas-Design-System):
|
||
- Primär `--ggs-fjord` `#2d6d4d` (Dunkelgrün)
|
||
- Akzent `--ggs-mustard` `#e8c547` (Senfgelb)
|
||
- Hintergrund `--ggs-bg` `#f5f3ea` (Beige)
|
||
- Text `--ggs-text` `#2a2a2a`
|
||
- Bitte CSS-Variablen `--lg-aut-*` definieren mit den passenden Werten,
|
||
dann kann Logistik bei Bedarf override-n.
|
||
|
||
## 6. Erwartete Spielmechanik (kurz)
|
||
|
||
1. **Start-Overlay**: Spieler sieht Ziel („Du musst nach Bregenz abfahren") und Spielanleitung
|
||
2. **Anfahrt**: 3-spurige Autobahn, LKW fährt Richtung Vorwegweiser
|
||
3. **Schild lesen**: erstes Vorwegweiser-Schild bei Distanz 80 m, zweites bei 280 m
|
||
4. **Spurwechsel**: links / rechts per Button oder Pfeiltaste
|
||
5. **Hindernis**: AI-Auto, Baustelle oder Unfall in einer Spur — ausweichen oder bremsen
|
||
6. **Ausfahrt**: bei Ausfahrt-Position muss Spieler korrekte Spur (meist rechts) erreichen
|
||
7. **Bewertung**:
|
||
- Korrekte Spur + keine Kollision → `success`
|
||
- Falsche Spur / Ausfahrt verpasst → `late`
|
||
- In Hindernis gekracht / aufgefahren → `crash`
|
||
|
||
Schwierigkeit darf gestaffelt sein (`easyMode: true` macht z.B. Schilder
|
||
deutlicher, Reaktionszeit länger).
|
||
|
||
## 7. Maximaldauer pro Spiel
|
||
|
||
**< 60 Sekunden** Spielzeit pro Szenario. Logistik-Spieler verlieren sonst
|
||
den Kontext zur Sim. Lieber kurz und intensiv.
|
||
|
||
## 8. Asset-Ablage
|
||
|
||
- Code: `App/sims/logistik/assets/vendor/autobahn-game/autobahn-game.js`
|
||
- CSS: gleiche Datei oder `autobahn-game.css` daneben
|
||
- Three (falls nötig): `App/sims/logistik/assets/vendor/three/three.min.js`
|
||
- Texturen / Sprites: `App/sims/logistik/assets/vendor/autobahn-game/assets/`
|
||
|
||
Logistik bindet das Modul per `<script src="...">` einmalig im Header ein
|
||
und ruft `window.lgAutobahnGame.start(...)` bei Bedarf.
|
||
|
||
## 9. Auswahl-Trigger (Logistik-Seite, nur zur Info)
|
||
|
||
Logistik wird das Spiel öffnen, wenn ein LKW eines bestimmten Auftrags
|
||
durch einen der 6 Knoten fährt. Dafür brauche ich pro Knoten eine
|
||
ungefähre Geo-Position (lat/lon), damit Logistik beim Routen-Tick prüfen
|
||
kann, ob das Vehicle nahe genug am Knoten ist (z.B. < 5 km).
|
||
|
||
→ Bitte im Modul eine kleine Konstante exportieren:
|
||
```js
|
||
window.lgAutobahnGame.NODES = {
|
||
bregenz: { lat: 47.50, lon: 9.74, label: 'Bregenz' },
|
||
salzburg: { lat: 47.81, lon: 13.05, label: 'Salzburg-West' },
|
||
// ...
|
||
};
|
||
```
|
||
|
||
## 10. Test-Modus / Debug
|
||
|
||
Bitte eine Demo-Datei `autobahn-game.test.html` mitliefern:
|
||
- Lädt das Modul
|
||
- 6 Buttons, einer pro Szenario
|
||
- Konsolen-Output des Result-Callbacks
|
||
|
||
Damit kann ich das Modul ohne Logistik-Hülle testen.
|
||
|
||
## 11. Was Logistik bereitstellt (kein Aufwand für dich)
|
||
|
||
- Der Container (Modal-Overlay)
|
||
- Pause der Sim-Zeit während Spiel
|
||
- Auswertung des Results: Bonus / Strafe / Vehicle-Ausfall
|
||
- Ducking der Hintergrundmusik
|
||
- Voice-Line vor / nach dem Spiel
|
||
|
||
## 12. Bitte beachten
|
||
|
||
- Code soll **ohne Inline-Kommentare zu Anlass / Tickets** auskommen — der
|
||
produktive Code soll selbsterklärend sein.
|
||
- Falls dynamisch DOM-Elemente erstellt werden, am Spiel-Ende **alle
|
||
Listener entfernen** (`removeEventListener`).
|
||
- Bitte keine globalen Sound-Loops, die nach `onEnd` weiterlaufen.
|
||
|
||
— Logistik
|