a
    w^i>                     @   sv   d Z ddlZddlZdd Zdd ZdddZd	d
 Zdd Zdd ZdddZ	dd Z
dddZdd Zdd ZdS )a,  
Messaging Style System

This module provides dynamic, personality-driven messaging styles for NPC conversations.
Characters have base messaging traits that are modified per-relationship and by mood states.

See docs/plans/2025-11-13-dynamic-messaging-styles-design.md for full design documentation.
    Nc                   C   sV   t ddt ddt ddt ddt ddt ddt ddt dd	d
S )z
    Generate random base messaging traits for a new character.

    Returns:
        dict: Base messaging traits (0-100 scale)
       F      P   (   <   
   Z   U   )	verbosityinquisitivenessexpressivenessresponsivenessopennessemoji_usage	formalityresponse_timing)randomrandint r   r   0/var/www/lichun.app/lichun/ws/messaging_style.pyinitialize_messaging_traits   s    







r   c                   C   s(   t g dt ddt g ddS )z
    Generate random messaging patterns for a new character.

    Returns:
        dict: Messaging patterns (time preferences, typing style, etc.)
    )morningnightneutralr   r	   )ZpropercasualZchaotic)Ztime_of_day_preferenceZweekend_availabilityZtyping_style)r   choicer   r   r   r   r   initialize_messaging_patterns!   s    
r   c                 C   s   ddddddddddd
}|rt |dr|jr|jd  }|dv rv|d  d7  < |d  d	8  < |d
  d8  < nb|dv r|d  d	7  < |d  d7  < |d
  d7  < n(|dv r|d  d	8  < |d
  d7  < |S )aW  
    Initialize messaging modifiers for a new relationship.
    Can apply relationship-type-specific starting modifiers.

    Args:
        relationship: relationshipClass instance (optional)
        character: personClass instance (optional, needed for relationship-type modifiers)

    Returns:
        dict: Initial messaging modifiers
    r   r   )
r   r   r   r   r   r   r   r   
mood_statecurrent_topic_engagementrelationships)bossteachercoworkerr   r   r      r   r   )partnerZ
girlfriendZ	boyfriendZspouser   )motherfathersibling   )hasattrr    lower)relationship	character	modifiersZprimary_relationshipr   r   r   !initialize_relationship_modifiers/   s2    r/   c           
      C   s   t | dst S | j}i }i }d}|rBt |drB|j}|dd}| D ]Z}t||dttfrp||dnd}t	| ||}|| | | }	t
dtd|	||< qJ|S )a6  
    Calculate final trait values: base + relationship modifier + mood modifier.

    Args:
        character: personClass instance with messaging_traits
        relationship: relationshipClass instance with messaging_modifiers (or None)

    Returns:
        dict: Effective trait values (0-100, clamped)
    messaging_traitsr   messaging_modifiersr   r   d   )r*   r   r0   r1   getkeys
isinstanceintfloatget_mood_modifiermaxmin)
r-   r,   base	effectiveZrel_modsr   traitZrelationship_modifierZmood_modifierZeffective_valuer   r   r   calculate_effective_traitsc   s    
&r>   c                 C   sD   ddddddddddddd	dddd
i d}| |i  |dS )a  
    Get temporary mood-based adjustment for a specific trait.

    Args:
        character: personClass instance
        mood_state: str - 'great', 'bad', 'stressed', or 'neutral'
        trait: str - trait name

    Returns:
        int: Modifier value (-50 to +50)
    r$   r   r   )r   r   r   r   r   )r   r   r   r   r   )r   r   r   r   )greatbadstressedr   r   )r3   )r-   r   r=   Zmood_effectsr   r   r   r8      s(    r8   c                 C   s  t | |}g }|d dk r&|d n|d dkr<|d |d dk rT|d n|d dkrj|d |d	 dk r|d
 n|d	 dkr|d |d dk r|d n|d dkr|d |d dk r|d n|d dkr|d |d dk r|d nDd|d   kr*dk r:n n|d n|d dkrR|d |d dk rl|d n|d dkr|d d|S )a:  
    Generate natural language style instructions for AI prompt based on calculated traits.

    Args:
        character: personClass instance
        relationship: relationshipClass instance (or None)
        player: playerClass instance

    Returns:
        str: Natural language instructions for AI prompt
    r   r   zQKeep responses extremely brief - 1-2 short sentences max, often just a few words.r   zQYou tend to ramble and share lots of details. Don't hold back - elaborate freely.r   zPYou rarely ask questions. Just respond without pushing the conversation forward.zXYou're naturally curious - frequently ask follow-up questions and show genuine interest.r   z=Keep tone neutral and understated. No excitement or emphasis.zTBe animated and enthusiastic! Use exclamation marks, show excitement, be expressive.r   zKGive minimal effort responses. Don't build on topics or match their energy.zKEngage fully with what they say. Build on their points, match their energy.r   zDStay surface-level. Avoid sharing personal details or deep thoughts.zXFeel free to share personal details, thoughts, and feelings openly - even TMI sometimes.r   r   zNever use emojis.r   z9Use an emoji occasionally when it fits (0-1 per message).zNUse emojis frequently to express yourself (2-4 per message is normal for you).r   zMText casually - lowercase, abbreviations (lol, idk, ur), minimal punctuation.zQUse proper grammar, spelling, and punctuation. Text like you're writing an email. )r>   appendjoin)r-   r,   playereffective_traitsinstructionsr   r   r   get_messaging_style_prompt   sB    





 

rL   c                 C   sn  | rt | dsdS tdtd|}|dkrb| jd  d7  < | jd  d7  < | jd	  d7  < nR|d
kr| jd	  d8  < | jd  d8  < | jd  d8  < n| jd	  d7  < |dkr| jd  d7  < | jd  d8  < | jd  d7  < |dkr | jd  d8  < | jd  d7  < || jd< | jD ]8}t| j| ttfr0tdtd| j| | j|< q0dS )a  
    Update messaging modifiers based on conversation dynamics.
    Called after each AI response to evolve the relationship's messaging style.

    Args:
        relationship: relationshipClass instance
        sentiment: str - 'positive', 'negative', or 'neutral'
        conversation_length: int - total messages in conversation
        topic_engagement: int - optional, -30 to +30 for current topic interest
    r1   Nr   positiver      r   r   negative            ?r   r   r   2   r   r   )r*   r9   r:   r1   r5   r6   r7   )r,   	sentimentconversation_lengthZtopic_engagementkeyr   r   r   'update_conversation_messaging_modifiers   s.    


rY   c                 C   s   ddl }|t}h d}||vr8|d| d d}ddlm} ||| j}|rt|dr||jd	< t	d
| j
 d| d dS )a  
    Set character's mood state across all their relationships.
    Mood affects all conversations with this character.

    Args:
        character: personClass instance
        player: playerClass instance
        mood: str - 'great', 'bad', 'stressed', or 'neutral'
    r   N>   r   rC   rE   rD   zInvalid mood state 'z', defaulting to 'neutral'r   )get_relationshipr1   r   zSet z's mood to '')logging	getLogger__name__warning	functionsrZ   idr*   r1   print	firstname)r-   rI   moodr\   loggerZVALID_MOODSrZ   r,   r   r   r   set_mood_state#  s    


rf   皙?c                 C   sj   t | dsdS | jD ]P}t| j| ttfr| j| }|d|  | j|< t| j| dk rd| j|< qdS )a  
    Gradually return messaging modifiers toward neutral (0).
    Called periodically (weekly recommended) to prevent permanent extremes.

    Args:
        relationship: relationshipClass instance
        decay_rate: float - how much to decay (0.1 = 10% toward 0 each call)
    r1   NrO   rS   r   )r*   r1   r5   r6   r7   abs)r,   Z
decay_rater=   currentr   r   r   decay_messaging_modifiers?  s    	


rj   c              
   C   s*  ddl }|t}| r t| ds$dS dddddddd	d
ddddddd
ddddddiddidddddddd}||vr|d| d dS || }| D ].\}}|dkr|| j|< q| j|  |7  < q| jD ]4}t| j| tt	frt
dtd| j| | j|< qtd| d|  dS )z
    Apply messaging modifier changes for major relationship/life events.

    Args:
        relationship: relationshipClass instance
        event_type: str - type of event triggering modifiers
    r   Nr1   r$   r   )r   r   r   r   rU   rM   r?   rB   )r   r   r   r   r   r@   )r   r   r   r   rA   r)   )r   r   r   r   r   rC   rE   rD   )r   r   r   )r   r   )start_datingbreakupZbecome_best_friendsZmajor_fightZgot_promotedZlost_jobZparent_diedZhad_babyzUnknown event type 'z' for messaging modifiersr   z	Applied 'z' messaging modifiers: )r\   r]   r^   r*   r_   itemsr1   r5   r6   r7   r9   r:   rb   )r,   
event_typer\   re   Zevent_effectsZeffectsrX   valuer   r   r   apply_event_modifiersW  s`    
	-
rp   c              	   C   sn   t | dr| jni }|r(t |dr(|jni }t| |}| j d| j ||||r\|ddndt| |ddS )a  
    Get detailed debug information about a character's messaging style.
    Useful for testing and debugging.

    Args:
        character: personClass instance
        relationship: relationshipClass instance (or None)

    Returns:
        dict: Debug information
    r0   r1   rF   r   r   N)Zcharacter_nameZbase_traitsZrelationship_modifiersrJ   r   Zprompt_instructions)r*   r0   r1   r>   rc   lastnamer3   rL   )r-   r,   r;   Zmodsr<   r   r   r   get_debug_messaging_info  s    

rr   )NN)r   )rg   )__doc__r   jsonr   r   r/   r>   r8   rL   rY   rf   rj   rp   rr   r   r   r   r   <module>   s   	
4%'>
6
N