/*
 * Runtime Web – Unified Serverless Framework for Full-Stack TypeScript Applications
 * Documentation: https://runtimeweb.com/docs/getting-started
 *
 * @template: ai-chat
 */

/**
 * Animation System
 *
 * CSS keyframe animations for the AI Chat UI.
 * All animations use design tokens for consistent timing.
 * Respects prefers-reduced-motion for accessibility.
 *
 * @requirements 2.4, 3.2, 4.5, 8.1, 8.2, 8.6
 */

/* ============================================
 * MESSAGE ENTRANCE ANIMATION
 * Fade-in + slide-up for new messages
 * Validates: Requirement 2.4
 * ============================================ */

@keyframes message-enter {
    from {
        opacity: 0;
        transform: translateY(8px);
    }

    to {
        opacity: 1;
        transform: translateY(0);
    }
}

.message-enter {
    animation: message-enter var(--duration-normal, 250ms) var(--ease-out, cubic-bezier(0, 0, 0.2, 1)) forwards;
}


/* ============================================
 * TYPING INDICATOR ANIMATION
 * Pulsing dots for AI thinking state
 * Validates: Requirement 3.2
 * ============================================ */

@keyframes typing-pulse {

    0%,
    60%,
    100% {
        transform: translateY(0);
        opacity: 0.4;
    }

    30% {
        transform: translateY(-4px);
        opacity: 1;
    }
}

.typing-indicator__dot {
    animation: typing-pulse 1.4s var(--ease-in-out, cubic-bezier(0.4, 0, 0.2, 1)) infinite;
}

.typing-indicator__dot:nth-child(1) {
    animation-delay: 0ms;
}

.typing-indicator__dot:nth-child(2) {
    animation-delay: 160ms;
}

.typing-indicator__dot:nth-child(3) {
    animation-delay: 320ms;
}


/* ============================================
 * BUTTON PRESS ANIMATION
 * Tactile feedback for send button
 * Validates: Requirement 4.5
 * ============================================ */

@keyframes button-press {
    0% {
        transform: scale(1);
    }

    50% {
        transform: scale(0.95);
    }

    100% {
        transform: scale(1);
    }
}

.button-press {
    animation: button-press var(--duration-fast, 150ms) var(--ease-out, cubic-bezier(0, 0, 0.2, 1));
}


/* ============================================
 * CURSOR BLINK ANIMATION
 * Blinking cursor for streaming text
 * Validates: Requirement 8.1
 * ============================================ */

@keyframes cursor-blink {

    0%,
    50% {
        opacity: 1;
    }

    51%,
    100% {
        opacity: 0;
    }
}

.cursor-blink {
    animation: cursor-blink 1s step-end infinite;
}


/* ============================================
 * LOADING SPINNER ANIMATION
 * Rotation for loading states
 * Validates: Requirement 8.1
 * ============================================ */

@keyframes spin {
    from {
        transform: rotate(0deg);
    }

    to {
        transform: rotate(360deg);
    }
}

.spin {
    animation: spin 1s linear infinite;
}


/* ============================================
 * FADE IN ANIMATION
 * Simple opacity transition
 * Validates: Requirement 8.1
 * ============================================ */

@keyframes fade-in {
    from {
        opacity: 0;
    }

    to {
        opacity: 1;
    }
}

.fade-in {
    animation: fade-in var(--duration-normal, 250ms) var(--ease-out, cubic-bezier(0, 0, 0.2, 1)) forwards;
}


/* ============================================
 * SLIDE UP FADE ANIMATION
 * Combined slide and fade for larger elements
 * Validates: Requirement 8.1
 * ============================================ */

@keyframes slide-up-fade {
    from {
        opacity: 0;
        transform: translateY(16px);
    }

    to {
        opacity: 1;
        transform: translateY(0);
    }
}

.slide-up-fade {
    animation: slide-up-fade var(--duration-slow, 350ms) var(--ease-out, cubic-bezier(0, 0, 0.2, 1)) forwards;
}


/* ============================================
 * SLIDE DOWN FADE ANIMATION
 * Exit animation for dismissing elements
 * Validates: Requirement 8.2
 * ============================================ */

@keyframes slide-down-fade {
    from {
        opacity: 1;
        transform: translateY(0);
    }

    to {
        opacity: 0;
        transform: translateY(8px);
    }
}

.slide-down-fade {
    animation: slide-down-fade var(--duration-normal, 250ms) var(--ease-in, cubic-bezier(0.4, 0, 1, 1)) forwards;
}


/* ============================================
 * SCALE IN ANIMATION
 * Pop-in effect for modals/tooltips
 * Validates: Requirement 8.1
 * ============================================ */

@keyframes scale-in {
    from {
        opacity: 0;
        transform: scale(0.95);
    }

    to {
        opacity: 1;
        transform: scale(1);
    }
}

.scale-in {
    animation: scale-in var(--duration-normal, 250ms) var(--ease-out, cubic-bezier(0, 0, 0.2, 1)) forwards;
}


/* ============================================
 * PULSE ANIMATION
 * Subtle attention-grabbing pulse
 * Validates: Requirement 8.1
 * ============================================ */

@keyframes pulse {

    0%,
    100% {
        opacity: 1;
    }

    50% {
        opacity: 0.7;
    }
}

.pulse {
    animation: pulse 2s var(--ease-in-out, cubic-bezier(0.4, 0, 0.2, 1)) infinite;
}


/* ============================================
 * REDUCED MOTION PREFERENCES
 * Disables non-essential animations for accessibility
 * Validates: Requirement 8.6
 * ============================================ */

@media (prefers-reduced-motion: reduce) {

    *,
    *::before,
    *::after {
        animation-duration: 0.01ms !important;
        animation-iteration-count: 1 !important;
        transition-duration: 0.01ms !important;
        scroll-behavior: auto !important;
    }

    /* Preserve essential feedback with minimal motion */
    .typing-indicator__dot {
        animation: none !important;
        opacity: 0.6;
    }

    .typing-indicator__dot:nth-child(2) {
        opacity: 0.8;
    }

    .typing-indicator__dot:nth-child(3) {
        opacity: 1;
    }

    /* Cursor remains visible without blinking */
    .cursor-blink {
        animation: none !important;
        opacity: 1;
    }

    /* Spinner still indicates loading but without rotation */
    .spin {
        animation: none !important;
    }
}
