# Falukant: UI-Anpassung - WebSocket & Familie / Liebschaften Dieses Dokument beschreibt die Nachrichten, die der externe Falukant-Daemon über den WebSocket-Broadcast sendet, damit die UI gezielt reagieren kann. Transport: - Alle Clients erhalten denselben Broadcast. - Die UI muss nach `user_id` filtern und nur Events für die eingeloggte Session verarbeiten. ## 1. Übersicht der Events | `event` | Pflichtfelder | Typische UI-Reaktion | |---------|----------------|----------------------| | `falukantUpdateFamily` | `user_id`, `reason` | Gezielter Refresh Familie/Liebe/Geld je nach `reason` | | `falukantUpdateStatus` | `user_id` | Allgemeiner Status-/Spielstands-Refresh | | `falukantUpdateProductionCertificate` | `user_id`, `reason`, `old_certificate`, `new_certificate` | Produkte / Produktions-UI / Zertifikat neu laden | | `children_update` | `user_id` | Kinderliste / FamilyView aktualisieren | | `falukant_family_scandal_hint` | `relationship_id` | Optionaler Toast oder Log; kein `user_id` | | `falukantUpdateChurch` | `user_id`, `reason` | Kirchenämter, Bewerbungen, Ernennungen | | `falukantUpdateDebt` | `user_id`, `reason` | Schuldturm, Verzug, Pfändung, Freilassung | ## 2. JSON-Payloads ### 2.1 `falukantUpdateFamily` ```json { "event": "falukantUpdateFamily", "user_id": 123, "reason": "daily" } ``` `reason` ist immer genau einer dieser festen Strings: - `daily` - `monthly` - `lover_installment` - `scandal` - `lover_birth` ### 2.2 `falukantUpdateChurch` ```json { "event": "falukantUpdateChurch", "user_id": 123, "reason": "applications" } ``` Mögliche `reason`: - `applications` - `npc_decision` - `appointment` - `vacancy_fill` - `promotion` ### 2.3 `falukantUpdateStatus` ```json { "event": "falukantUpdateStatus", "user_id": 123 } ``` Dieses Event wird typischerweise direkt nach einem fachlichen Falukant-Event mit derselben `user_id` gesendet. ### 2.4 `falukantUpdateProductionCertificate` ```json { "event": "falukantUpdateProductionCertificate", "user_id": 123, "reason": "daily_recalculation", "old_certificate": 2, "new_certificate": 3 } ``` ### 2.5 `children_update` ```json { "event": "children_update", "user_id": 123 } ``` Dieses Event tritt bei Geburt aus einer Liebschaft auf, meist zusammen mit: - `falukantUpdateFamily` mit `reason: "lover_birth"` - `falukantUpdateStatus` ### 2.6 `falukant_family_scandal_hint` ```json { "event": "falukant_family_scandal_hint", "relationship_id": 456 } ``` Hinweis: - Dieses Event enthält kein `user_id`. - Die UI kann es ignorieren oder optional nur für Log-/Toast-Zwecke verwenden. - Die eigentliche nutzerbezogene Aktualisierung läuft über `falukantUpdateFamily` mit `reason: "scandal"`. ### 2.7 `falukantUpdateDebt` ```json { "event": "falukantUpdateDebt", "user_id": 123, "reason": "debtors_prison_entered" } ``` Mögliche `reason`: - `delinquency` - `debtors_prison_entered` - `asset_seizure` - `vehicle_liquidation` - `house_seizure` - `branch_closure` - `debtors_prison_released` ## 3. Fachliche Bedeutung von `reason` ### 3.1 `falukantUpdateFamily` #### `reason: "daily"` `daily` ist der Sammelgrund für tägliche Änderungen im Familien- und Liebschaftssystem. Darunter fallen insbesondere: - tägliche Drift und Änderung der Ehezufriedenheit - `marriage_public_stability` - `household_tension_score` - Ehe-Buffs und temporäre Zähler wie Geschenk-, Fest- oder Haus-Effekte - tägliche Liebschaftslogik für aktive Beziehungen - Rufverlust bei zwei oder mehr sichtbaren Liebschaften - Zufalls-Mali wie Gerücht oder Tadel Wichtig: - Es gibt kein separates Event für „nur Ehe-Buff“. - Es gibt kein separates Event für „nur zwei sichtbare Liebschaften“. - Es gibt kein separates Event für „nur Gerücht/Tadel“. - Alles davon erscheint in der UI ausschließlich als `falukantUpdateFamily` mit `reason: "daily"`. #### `reason: "monthly"` `monthly` steht für monatliche Verarbeitung, insbesondere: - Dienerschaftskosten - laufende Kosten - Unterversorgung - Geldänderungen #### `reason: "lover_installment"` `lover_installment` steht für die 2-Stunden-Unterhaltsbelastung von Liebschaften. Die UI sollte dafür mindestens: - Geld neu laden - Family-/Liebschaftsstatus neu laden #### `reason: "scandal"` `scandal` wird zusätzlich zu einem gelungenen Skandalwurf gesendet. Typischer Ablauf: - optional `falukant_family_scandal_hint` - `falukantUpdateFamily` mit `reason: "scandal"` - `falukantUpdateStatus` Danach kann für denselben Nutzer am selben Tag zusätzlich noch `daily` folgen. #### `reason: "lover_birth"` `lover_birth` signalisiert ein neues Kind aus einer Liebschaft. Meist folgen zusammen: - `falukantUpdateFamily` mit `reason: "lover_birth"` - `children_update` - `falukantUpdateStatus` ### 3.2 `falukantUpdateChurch` - `applications`: Spieler ist kirchlicher Vorgesetzter; offene Bewerbungen warten - `npc_decision`: NPC-Vorgesetzter hat entschieden - `appointment`: automatische Annahme älterer Bewerbung - `vacancy_fill`: Interimsbesetzung - `promotion`: reserviert / zukünftig ### 3.3 `falukantUpdateProductionCertificate` - `daily_recalculation`: Zertifikat nach täglicher Prüfung geändert ### 3.4 `falukantUpdateDebt` - `delinquency`: Mahnstufe oder Verzug aktualisiert - `debtors_prison_entered`: Eintritt in den Schuldturm - `asset_seizure`: Geld, Waren oder sonstige Vermögenswerte eingezogen - `vehicle_liquidation`: Fahrzeuge zwangsverkauft - `house_seizure`: Haus gepfändet - `branch_closure`: Niederlassung geschlossen - `debtors_prison_released`: Freilassung ## 4. Empfohlene Handler-Logik ```text onMessage(json): if json.user_id exists and json.user_id != currentUserId: return switch json.event: case "falukantUpdateStatus": refreshPlayerStatus() return case "falukantUpdateProductionCertificate": refreshProductsAndProductionUi() return case "children_update": refreshChildrenAndFamilyView() return case "falukantUpdateChurch": refreshChurchContextByReason(json.reason) return case "falukantUpdateDebt": refreshDebtAndAffectedViews(json.reason) return case "falukantUpdateFamily": switch json.reason: case "daily": refreshFamilyAndRelationships() refreshReputationIfNeeded() break case "monthly": refreshMoney() refreshFamilyAndRelationships() break case "lover_installment": refreshMoney() refreshFamilyAndRelationships() break case "scandal": showScandalToastOptional() refreshFamilyAndRelationships() refreshReputationIfNeeded() break case "lover_birth": refreshChildrenAndFamilyView() break return case "falukant_family_scandal_hint": // optional: nur als Hinweis verarbeiten return ``` ## 5. Deduplizierung Ein Nutzer kann kurz hintereinander mehrere relevante Events erhalten, zum Beispiel: - `scandal` - danach `daily` - danach `falukantUpdateStatus` oder: - `falukantUpdateDebt` - direkt danach `falukantUpdateStatus` - zusätzlich `falukantUpdateFamily` Die UI sollte deshalb: - Refreshes bündeln oder entprellen - idempotente Reloads verwenden - nicht davon ausgehen, dass jeder fachliche Effekt einen eigenen Spezial-Eventpfad hat ## 6. Welche Daten sollten neu geladen werden? | Situation | Sinnvolle Reaktion | |-----------|--------------------| | Jede `falukantUpdateFamily` | Family-/Relationship-Daten neu laden | | `reason: "monthly"` | Family-Daten plus Geld/Status neu laden | | `reason: "lover_installment"` | Geld plus Family-Daten neu laden | | `reason: "daily"` | Family-Daten neu laden, bei Bedarf auch Ruf-/Statusdaten | | `reason: "scandal"` | Family-Daten plus Ruf-/Statusdaten neu laden | | `children_update` / `lover_birth` | Kinderdaten und FamilyView neu laden | | `falukantUpdateChurch` | Kirchenämter, Bewerbungen, freie Positionen je nach `reason` | | `falukantUpdateProductionCertificate` | User-Status, Zertifikat, Produkte, Produktions-UI | | `falukantUpdateDebt` | Bank, Overview, House, Branch, ggf. Family | ## 7. Sonderfälle | Fall | Verhalten | |------|-----------| | NPC ohne `user_id` | Keine nutzerbezogenen Socket-Events | | Mehrere Events kurz hintereinander | Normal; UI sollte damit robust umgehen | | Nur `falukantUpdateStatus` ohne Fach-Event | Kann von anderen Falukant-Workern kommen |