:root {
    --motion-duration-default: 300ms;
}

/* Collapse: wrap the content in .app-collapse > .app-collapse-inner, toggle .app-collapse-closed. */
.app-collapse {
    display: grid;
    grid-template-rows: 1fr;
    opacity: 1;
    transition:
        grid-template-rows var(--motion-duration-default) ease-in-out,
        opacity var(--motion-duration-default) ease-in-out;
}

.app-collapse > .app-collapse-inner {
    min-height: 0;
    overflow: hidden;
}

.app-collapse.app-collapse-closed {
    grid-template-rows: 0fr;
    opacity: 0;
    visibility: hidden;
    transition:
        grid-template-rows var(--motion-duration-default) ease-in-out,
        opacity var(--motion-duration-default) ease-in-out,
        visibility 0s var(--motion-duration-default);
}

@media (prefers-reduced-motion: reduce) {
    .app-collapse,
    .app-collapse.app-collapse-closed {
        transition: none;
    }
}

/* Side panel reveal: set --app-panel-width (and optionally --app-panel-gap) on .app-panel-reveal, toggle
   .app-panel-reveal-open. Its direct child keeps the full width, so it is uncovered instead of reflowing. */
.app-panel-reveal {
    box-sizing: border-box;
    width: 0;
    padding-left: 0;
    overflow: hidden;
    opacity: 0;
    visibility: hidden;
    transition:
        width var(--motion-duration-default) ease-in-out,
        padding-left var(--motion-duration-default) ease-in-out,
        opacity var(--motion-duration-default) ease-in-out,
        visibility 0s var(--motion-duration-default);
}

.app-panel-reveal > * {
    width: var(--app-panel-width);
}

.app-panel-reveal.app-panel-reveal-open {
    width: calc(var(--app-panel-width) + var(--app-panel-gap, 0px));
    padding-left: var(--app-panel-gap, 0px);
    opacity: 1;
    visibility: visible;
    transition:
        width var(--motion-duration-default) ease-in-out,
        padding-left var(--motion-duration-default) ease-in-out,
        opacity var(--motion-duration-default) ease-in-out;
}

@media (prefers-reduced-motion: reduce) {
    .app-panel-reveal,
    .app-panel-reveal.app-panel-reveal-open {
        transition: none;
    }
}

/* Typing indicator: three dots that pulse in turn. Markup: .app-typing-dots containing three empty <span>s. */
.app-typing-dots {
    display: inline-flex;
    gap: 4px;
}

.app-typing-dots > span {
    width: 6px;
    height: 6px;
    border-radius: 50%;
    background-color: var(--text-muted);
    animation: app-typing-dot 1.2s ease-in-out infinite;
}

.app-typing-dots > span:nth-child(2) {
    animation-delay: 0.15s;
}

.app-typing-dots > span:nth-child(3) {
    animation-delay: 0.3s;
}

@keyframes app-typing-dot {
    0%,
    80%,
    100% {
        opacity: 0.3;
        transform: translateY(0);
    }

    40% {
        opacity: 1;
        transform: translateY(-3px);
    }
}

@media (prefers-reduced-motion: reduce) {
    .app-typing-dots > span {
        animation: none;
        opacity: 0.6;
    }
}

