Spaces:
Runtime error
Runtime error
🥚 Initial DigiPal deployment to HuggingFace Spaces🤖 Generated with [Claude Code](https://claude.ai/code)Co-Authored-By: Claude <noreply@anthropic.com>
4399e64 | """ | |
| Core data models for DigiPal application. | |
| """ | |
| from dataclasses import dataclass, field | |
| from datetime import datetime | |
| from typing import Dict, List, Optional, Set, Any | |
| import json | |
| import uuid | |
| from .enums import EggType, LifeStage, CareActionType, AttributeType, CommandType, InteractionResult | |
| class DigiPal: | |
| """ | |
| Core DigiPal model representing a digital pet with all attributes and lifecycle properties. | |
| """ | |
| # Identity and Basic Info | |
| id: str = field(default_factory=lambda: str(uuid.uuid4())) | |
| user_id: str = "" | |
| name: str = "DigiPal" | |
| egg_type: EggType = EggType.RED | |
| life_stage: LifeStage = LifeStage.EGG | |
| generation: int = 1 | |
| # Primary Attributes (Digimon World 1 inspired) | |
| hp: int = 100 | |
| mp: int = 50 | |
| offense: int = 10 | |
| defense: int = 10 | |
| speed: int = 10 | |
| brains: int = 10 | |
| # Secondary Attributes | |
| discipline: int = 0 | |
| happiness: int = 50 | |
| weight: int = 20 | |
| care_mistakes: int = 0 | |
| energy: int = 100 | |
| # Lifecycle Management | |
| birth_time: datetime = field(default_factory=datetime.now) | |
| last_interaction: datetime = field(default_factory=datetime.now) | |
| evolution_timer: float = 0.0 # Hours until next evolution check | |
| # Memory and Context | |
| conversation_history: List['Interaction'] = field(default_factory=list) | |
| learned_commands: Set[str] = field(default_factory=set) | |
| personality_traits: Dict[str, float] = field(default_factory=dict) | |
| # Visual Representation | |
| current_image_path: str = "" | |
| image_generation_prompt: str = "" | |
| def __post_init__(self): | |
| """Initialize DigiPal with egg-type specific attributes.""" | |
| if self.life_stage == LifeStage.EGG: | |
| self._initialize_egg_attributes() | |
| # Initialize basic learned commands for baby stage | |
| if self.life_stage == LifeStage.BABY: | |
| self.learned_commands = {"eat", "sleep", "good", "bad"} | |
| def _initialize_egg_attributes(self): | |
| """Set initial attributes based on egg type.""" | |
| base_attributes = { | |
| EggType.RED: { | |
| 'offense': 15, | |
| 'defense': 8, | |
| 'speed': 12, | |
| 'brains': 8, | |
| 'hp': 90, | |
| 'mp': 40 | |
| }, | |
| EggType.BLUE: { | |
| 'offense': 8, | |
| 'defense': 15, | |
| 'speed': 8, | |
| 'brains': 12, | |
| 'hp': 110, | |
| 'mp': 60 | |
| }, | |
| EggType.GREEN: { | |
| 'offense': 10, | |
| 'defense': 12, | |
| 'speed': 10, | |
| 'brains': 10, | |
| 'hp': 120, | |
| 'mp': 50 | |
| } | |
| } | |
| if self.egg_type in base_attributes: | |
| attrs = base_attributes[self.egg_type] | |
| for attr, value in attrs.items(): | |
| setattr(self, attr, value) | |
| def get_age_hours(self) -> float: | |
| """Calculate age in hours since birth.""" | |
| return (datetime.now() - self.birth_time).total_seconds() / 3600 | |
| def get_attribute(self, attribute: AttributeType) -> int: | |
| """Get attribute value by type.""" | |
| return getattr(self, attribute.value, 0) | |
| def set_attribute(self, attribute: AttributeType, value: int): | |
| """Set attribute value with bounds checking.""" | |
| # Define attribute bounds | |
| bounds = { | |
| AttributeType.HP: (1, 999), | |
| AttributeType.MP: (0, 999), | |
| AttributeType.OFFENSE: (0, 999), | |
| AttributeType.DEFENSE: (0, 999), | |
| AttributeType.SPEED: (0, 999), | |
| AttributeType.BRAINS: (0, 999), | |
| AttributeType.DISCIPLINE: (0, 100), | |
| AttributeType.HAPPINESS: (0, 100), | |
| AttributeType.WEIGHT: (1, 99), | |
| AttributeType.CARE_MISTAKES: (0, 999), | |
| AttributeType.ENERGY: (0, 100) | |
| } | |
| min_val, max_val = bounds.get(attribute, (0, 999)) | |
| clamped_value = max(min_val, min(max_val, value)) | |
| setattr(self, attribute.value, clamped_value) | |
| def modify_attribute(self, attribute: AttributeType, change: int): | |
| """Modify attribute by a delta amount.""" | |
| current_value = self.get_attribute(attribute) | |
| self.set_attribute(attribute, current_value + change) | |
| def can_understand_command(self, command: str) -> bool: | |
| """Check if DigiPal can understand a command based on life stage.""" | |
| stage_commands = { | |
| LifeStage.EGG: set(), | |
| LifeStage.BABY: {"eat", "sleep", "good", "bad"}, | |
| LifeStage.CHILD: {"eat", "sleep", "good", "bad", "play", "train"}, | |
| LifeStage.TEEN: {"eat", "sleep", "good", "bad", "play", "train", "status", "talk"}, | |
| LifeStage.YOUNG_ADULT: {"eat", "sleep", "good", "bad", "play", "train", "status", "talk", "battle"}, | |
| LifeStage.ADULT: {"eat", "sleep", "good", "bad", "play", "train", "status", "talk", "battle", "teach"}, | |
| LifeStage.ELDERLY: {"eat", "sleep", "good", "bad", "play", "train", "status", "talk", "battle", "teach", "wisdom"} | |
| } | |
| available_commands = stage_commands.get(self.life_stage, set()) | |
| return command.lower() in available_commands or command.lower() in self.learned_commands | |
| def to_dict(self) -> Dict[str, Any]: | |
| """Convert DigiPal to dictionary for serialization.""" | |
| return { | |
| 'id': self.id, | |
| 'user_id': self.user_id, | |
| 'name': self.name, | |
| 'egg_type': self.egg_type.value, | |
| 'life_stage': self.life_stage.value, | |
| 'generation': self.generation, | |
| 'hp': self.hp, | |
| 'mp': self.mp, | |
| 'offense': self.offense, | |
| 'defense': self.defense, | |
| 'speed': self.speed, | |
| 'brains': self.brains, | |
| 'discipline': self.discipline, | |
| 'happiness': self.happiness, | |
| 'weight': self.weight, | |
| 'care_mistakes': self.care_mistakes, | |
| 'energy': self.energy, | |
| 'birth_time': self.birth_time.isoformat(), | |
| 'last_interaction': self.last_interaction.isoformat(), | |
| 'evolution_timer': self.evolution_timer, | |
| 'conversation_history': [interaction.to_dict() for interaction in self.conversation_history], | |
| 'learned_commands': list(self.learned_commands), | |
| 'personality_traits': self.personality_traits, | |
| 'current_image_path': self.current_image_path, | |
| 'image_generation_prompt': self.image_generation_prompt | |
| } | |
| def from_dict(cls, data: Dict[str, Any]) -> 'DigiPal': | |
| """Create DigiPal from dictionary.""" | |
| # Convert string enums back to enum objects | |
| data['egg_type'] = EggType(data['egg_type']) | |
| data['life_stage'] = LifeStage(data['life_stage']) | |
| # Convert ISO strings back to datetime objects | |
| data['birth_time'] = datetime.fromisoformat(data['birth_time']) | |
| data['last_interaction'] = datetime.fromisoformat(data['last_interaction']) | |
| # Convert conversation history | |
| data['conversation_history'] = [ | |
| Interaction.from_dict(interaction_data) | |
| for interaction_data in data.get('conversation_history', []) | |
| ] | |
| # Convert learned commands to set | |
| data['learned_commands'] = set(data.get('learned_commands', [])) | |
| return cls(**data) | |
| class Interaction: | |
| """Represents a single interaction between user and DigiPal.""" | |
| timestamp: datetime = field(default_factory=datetime.now) | |
| user_input: str = "" | |
| interpreted_command: str = "" | |
| pet_response: str = "" | |
| attribute_changes: Dict[str, int] = field(default_factory=dict) | |
| success: bool = True | |
| result: InteractionResult = InteractionResult.SUCCESS | |
| def to_dict(self) -> Dict[str, Any]: | |
| """Convert Interaction to dictionary.""" | |
| return { | |
| 'timestamp': self.timestamp.isoformat(), | |
| 'user_input': self.user_input, | |
| 'interpreted_command': self.interpreted_command, | |
| 'pet_response': self.pet_response, | |
| 'attribute_changes': self.attribute_changes, | |
| 'success': self.success, | |
| 'result': self.result.value | |
| } | |
| def from_dict(cls, data: Dict[str, Any]) -> 'Interaction': | |
| """Create Interaction from dictionary.""" | |
| data['timestamp'] = datetime.fromisoformat(data['timestamp']) | |
| data['result'] = InteractionResult(data['result']) | |
| return cls(**data) | |
| class Command: | |
| """Represents a parsed command from user input.""" | |
| action: str = "" | |
| parameters: Dict[str, Any] = field(default_factory=dict) | |
| stage_appropriate: bool = True | |
| energy_required: int = 0 | |
| command_type: CommandType = CommandType.UNKNOWN | |
| def to_dict(self) -> Dict[str, Any]: | |
| """Convert Command to dictionary.""" | |
| return { | |
| 'action': self.action, | |
| 'parameters': self.parameters, | |
| 'stage_appropriate': self.stage_appropriate, | |
| 'energy_required': self.energy_required, | |
| 'command_type': self.command_type.value | |
| } | |
| def from_dict(cls, data: Dict[str, Any]) -> 'Command': | |
| """Create Command from dictionary.""" | |
| data['command_type'] = CommandType(data['command_type']) | |
| return cls(**data) | |
| class AttributeModifier: | |
| """Represents a modification to DigiPal attributes.""" | |
| attribute: AttributeType | |
| change: int | |
| conditions: List[str] = field(default_factory=list) | |
| def to_dict(self) -> Dict[str, Any]: | |
| """Convert AttributeModifier to dictionary.""" | |
| return { | |
| 'attribute': self.attribute.value, | |
| 'change': self.change, | |
| 'conditions': self.conditions | |
| } | |
| def from_dict(cls, data: Dict[str, Any]) -> 'AttributeModifier': | |
| """Create AttributeModifier from dictionary.""" | |
| data['attribute'] = AttributeType(data['attribute']) | |
| return cls(**data) | |
| class CareAction: | |
| """Represents a care action that can be performed on DigiPal.""" | |
| name: str | |
| action_type: CareActionType | |
| energy_cost: int | |
| happiness_change: int | |
| attribute_modifiers: List[AttributeModifier] = field(default_factory=list) | |
| success_conditions: List[str] = field(default_factory=list) | |
| failure_effects: List[AttributeModifier] = field(default_factory=list) | |
| def to_dict(self) -> Dict[str, Any]: | |
| """Convert CareAction to dictionary.""" | |
| return { | |
| 'name': self.name, | |
| 'action_type': self.action_type.value, | |
| 'energy_cost': self.energy_cost, | |
| 'happiness_change': self.happiness_change, | |
| 'attribute_modifiers': [mod.to_dict() for mod in self.attribute_modifiers], | |
| 'success_conditions': self.success_conditions, | |
| 'failure_effects': [mod.to_dict() for mod in self.failure_effects] | |
| } | |
| def from_dict(cls, data: Dict[str, Any]) -> 'CareAction': | |
| """Create CareAction from dictionary.""" | |
| data['action_type'] = CareActionType(data['action_type']) | |
| data['attribute_modifiers'] = [ | |
| AttributeModifier.from_dict(mod_data) | |
| for mod_data in data.get('attribute_modifiers', []) | |
| ] | |
| data['failure_effects'] = [ | |
| AttributeModifier.from_dict(mod_data) | |
| for mod_data in data.get('failure_effects', []) | |
| ] | |
| return cls(**data) |