Fixed SD RPG
This commit is contained in:
@@ -0,0 +1,53 @@
|
||||
"""Shared context blocks for RPG narrator / plot LLM calls."""
|
||||
|
||||
from services.rpg_plot import count_active_quests
|
||||
|
||||
|
||||
def format_narrator_context(
|
||||
arc: dict | None,
|
||||
quests: list | None,
|
||||
status_quo: str = "",
|
||||
) -> str:
|
||||
parts: list[str] = []
|
||||
arc = arc or {}
|
||||
beats = arc.get("beats") or []
|
||||
if not isinstance(beats, list):
|
||||
beats = []
|
||||
|
||||
parts.append(f"Plot phase: {arc.get('phase', 'opening')}. Scripted beats left: {len(beats)}.")
|
||||
if not beats:
|
||||
parts.append(
|
||||
"IMPORTANT: Scripted beats are EXHAUSTED (quests may already be done). "
|
||||
"The story must CONTINUE — do not stall. "
|
||||
"Always return 2-4 meaningful choices for the player's next actions. "
|
||||
"You may add quest_updates with status 'active' for NEW optional threads. "
|
||||
"Do NOT re-activate quests the player already completed unless they explicitly revisit that thread."
|
||||
)
|
||||
elif count_active_quests(quests) == 0:
|
||||
pending = [
|
||||
(b.get("title") or b.get("id") or "beat")
|
||||
for b in beats[:3]
|
||||
if isinstance(b, dict)
|
||||
]
|
||||
parts.append(
|
||||
"IMPORTANT: No active quests but scripted beats remain — arc was likely desynced. "
|
||||
"The engine will inject the next beat; prefer choices that fit pending beats: "
|
||||
+ ", ".join(pending)
|
||||
+ ". Do NOT treat the arc as finished."
|
||||
)
|
||||
hint = (arc.get("next_beat_hint") or "").strip()
|
||||
if hint:
|
||||
parts.append(f"Arc hint: {hint}")
|
||||
|
||||
if quests:
|
||||
parts.append("Quest log:")
|
||||
for q in quests:
|
||||
parts.append(f" [{q.get('status', 'active')}] {q.get('title', '')}")
|
||||
else:
|
||||
parts.append("Quest log: (empty)")
|
||||
|
||||
sq = (status_quo or "").strip()
|
||||
if sq:
|
||||
parts.append(f"Status quo: {sq[:400]}")
|
||||
|
||||
return "\n".join(parts)
|
||||
Reference in New Issue
Block a user