RetroGame / dialogue_system.py
Lukeetah's picture
Create dialogue_system.py
8f846af verified
# dialogue_system.py
from dataclasses import dataclass
from typing import Dict, List
import random
from game_engine import GauchoCharacter
@dataclass
class DialogNode:
id: str
text: str
options: List[Dict[str, str]]
cultural_requirement: str = None
crystal_trigger: str = None
class DynamicNarrative:
"""Sistema de diálogos que se adapta a los valores recolectados"""
def __init__(self):
self.dialog_tree = self._build_cultural_dialog_tree()
self.current_node = "root"
def _build_cultural_dialog_tree(self) -> Dict[str, DialogNode]:
return {
"root": DialogNode(
id="root",
text="¡Che, ¿viste lo que pasa con estos algoritmos?¡Están desdibujando nuestra esencia!",
options=[
{"text": "Voy a recuperar los cristales", "target": "mision_principal"},
{"text": "¿Tenés algún dato útil?", "target": "pistas_culturales"},
{"text": "Hablemos de nuestra identidad", "target": "reflexion_filosofica"}
]
),
"mision_principal": DialogNode(
id="mision_principal",
text="Cada cristal que recuperés fortalecerá nuestra resistencia cultural. ¿Por cuál querés empezar?",
options=[
{"text": "Solidaridad", "target": "solidaridad_quest"},
{"text": "Creatividad", "target": "creatividad_quest"},
{"text": "Volver", "target": "root"}
],
cultural_requirement="basic"
),
"solidaridad_quest": DialogNode(
id="solidaridad_quest",
text="Para recuperar la Solidaridad, necesitás ayudar a tres comunidades diferentes. ¿Listo para el desafío?",
options=[
{"text": "Acepto el reto", "target": "solidaridad_1"},
{"text": "Necesito prepararme", "target": "mision_principal"}
],
crystal_trigger="Solidaridad"
)
}
def get_current_dialog(self, player: GauchoCharacter) -> DialogNode:
node = self.dialog_tree[self.current_node]
return self._filter_options(node, player)
def _filter_options(self, node: DialogNode, player: GauchoCharacter) -> DialogNode:
"""Filtra opciones basadas en progreso del jugador"""
filtered_options = []
for option in node.options:
target_node = self.dialog_tree.get(option['target'], None)
if target_node:
if target_node.cultural_requirement == "basic" and not any(player.inventory['cristales'].values()):
continue
if target_node.crystal_trigger and not player.inventory['cristales'][target_node.crystal_trigger]:
continue
filtered_options.append(option)
return DialogNode(
id=node.id,
text=node.text,
options=filtered_options,
cultural_requirement=node.cultural_requirement,
crystal_trigger=node.crystal_trigger
)
def select_option(self, option_index: int, player: GauchoCharacter) -> str:
current_node = self.get_current_dialog(player)
if 0 <= option_index < len(current_node.options):
self.current_node = current_node.options[option_index]['target']
return self.get_current_dialog(player).text
return current_node.text