/**
 * SpendSnapper - Website Stylesheet
 *
 * The variables, navigation, button, card and footer rules are carried over from the app's
 * spendsnapper.css so the website and the app read as one product.
 */

/* -----------------------------
 * CSS Variables (from the app)
 * ----------------------------- */
:root {
    /* Color Palette */
    --primary: #45515d;
    --secondary: #6699ac;
    --secondary-light: #8aafbf;
    --secondary-ultra-light: #eaf2f6;
    --danger: #e97b7c;
    --danger-light: #fce4e5;
    --muted: #6c757d;
    --muted-light: #e9ecef;
    --success: #317b52;
    --success-mid: #8dc49a;
    --success-dark: #276843;
    --success-light: #e5f5ec;

    /* Logo facets, used by the hero animation */
    --facet-blue-dark: #2f6e7d;
    --facet-blue: #639eae;
    --facet-blue-light: #a2c8d2;
    --facet-green: #4d9358;
    --facet-green-mid: #83bb79;
    --facet-green-light: #bcd795;
    --facet-red: #e86766;
    --facet-red-light: #f28d8d;

    /* UI Elements */
    --border-color: #e6edf2;
    --background: #f5f7f9;
    --table-header-bg: #d3dde6;
    --table-header-text: #54626f;
    --card-shadow: 0 6px 16px rgba(0, 0, 0, 0.08);

    /* The app's review table */
    --grid-border: #ddd;
    --tip-border: #ccc;
    --skeleton: #eef1f4;
    --skeleton-shine: #e2e7ec;

    /* Common Transitions */
    --transition: all 0.2s ease-in-out;

    /* Spacing & Sizing */
    --border-radius-sm: 6px;
    --border-radius: 8px;
    --border-radius-lg: 12px;
    --badge-radius: 20px;
    --spacing-sm: 0.5rem;
    --spacing-md: 1rem;
    --spacing-lg: 1.75rem;
}

/* -----------------------------
 * Base Elements
 * ----------------------------- */
html {
    scroll-behavior: smooth;
    /* Anchored sections stop below the sticky navbar */
    scroll-padding-top: 80px;
}

/* The body and html both carry the footer's slate, so the colour Safari samples for the strip beneath the
   page is the one the footer already has, however it is scrolled */
html {
    background-color: var(--primary);
}

body {
    background-color: var(--primary);
    font-family: 'Quicksand', sans-serif;
    color: var(--primary);
    font-weight: 500;
    min-height: 100vh;
    display: flex;
    flex-direction: column;
    font-size: 16px;
}

b, strong {
    font-weight: 700;
}

h1, h2, h3 {
    font-weight: 700;
    color: var(--primary);
}

a {
    color: var(--primary);
    transition: color 0.2s ease-in-out;
    text-underline-offset: 2px;
}

a:hover {
    color: var(--primary);
    text-decoration-color: #61aa75;
    text-decoration-thickness: 2px;
}

footer {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    justify-content: center;
    padding: 0.9rem 0.75rem;
    font-size: 0.8rem;
    color: rgba(255, 255, 255, 0.7);
    width: 100%;
    background-color: var(--primary);
}

footer a {
    color: rgba(255, 255, 255, 0.7);
    text-decoration: none;
}

footer a:hover {
    color: #fff;
    text-decoration: underline;
}

.footer-dot {
    margin: 0 0.6rem;
    color: rgba(255, 255, 255, 0.4);
}

/* The links stay together on one line where there's room. On a narrow screen they wrap between links, never
   within one. */
.footer-links {
    white-space: nowrap;
}

.footer-links a {
    white-space: nowrap;
}

/* The LinkedIn icon is drawn in the link colour, so it matches the text links and brightens with them on hover */
.footer-social svg {
    width: 1.1em;
    height: 1.1em;
    vertical-align: -0.2em;
}

@media (max-width: 575.98px) {
    .footer-links {
        white-space: normal;
        text-align: center;
    }
}

/* -----------------------------
 * Layout
 * ----------------------------- */
.main-container {
    background-color: var(--secondary);
    padding: var(--spacing-lg);
    flex: 1;
    width: 100%;
    display: flex;
    flex-direction: column;
    gap: var(--spacing-lg);
    /* The diagrams' moving layers can reach past the side of the screen mid-animation. Trimming them here
       keeps the page from ever growing wider than the screen. Clip, unlike hidden, leaves sticky bars working. */
    overflow-x: clip;
}

/* The website's panels stop growing on very wide screens and sit centred */
.main-container > .card {
    width: 100%;
    max-width: 1240px;
    margin-left: auto;
    margin-right: auto;
}

/* -----------------------------
 * Navigation (from the app)
 * ----------------------------- */
.navbar {
    background-color: var(--primary);
    /* The logo row is pinned to the top rather than centred in the minimum height, so it stays put when
       the burger menu opens and the bar grows */
    padding: 9.5px var(--spacing-lg) var(--spacing-sm);
    min-height: 65px;
    align-items: flex-start;
    box-shadow: 0 2px 10px rgba(0, 0, 0, 0.1);
    position: sticky;
    top: 0;
    z-index: 1000;
}

/* A touch of frosted glass: the bar is slightly translucent, so what scrolls beneath it shows through blurred
   and a little richer in colour, with a fine highlight along its top edge like light catching glass */
@supports (backdrop-filter: blur(1px)) or (-webkit-backdrop-filter: blur(1px)) {
    .navbar {
        background-color: rgba(69, 81, 93, 0.9);
        -webkit-backdrop-filter: blur(18px) saturate(160%);
        backdrop-filter: blur(18px) saturate(160%);
        box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.14), inset 0 -1px 0 rgba(255, 255, 255, 0.05),
                    0 2px 10px rgba(0, 0, 0, 0.1);
    }
}

.navbar-brand {
    display: flex;
    align-items: center;
    padding: 0;
    margin: 0 var(--spacing-md) 0 0;
}

.navbar-brand img {
    height: 50px;
    margin-top: -4px;
    display: block;
    /* The logo SVG carries ~13px of transparent padding inside its viewBox */
    margin-left: -13px;
}

.navbar .container-fluid {
    padding: 0;
}

/* Lift the links so their text sits on the same baseline as the wordmark in the logo. Below 768px the links
   fold into the burger menu. */
@media (min-width: 768px) {
    .navbar-nav {
        position: relative;
        top: -1px;
    }

    /* Room between the links, and between the logo and the first link. Bootstrap's own padding here is
       more specific than a plain .nav-link rule, so this matches it. */
    .navbar-expand-md .navbar-nav .nav-link {
        padding-left: 1rem;
        padding-right: 1rem;
    }

    .navbar-brand {
        margin-right: 1.5rem;
    }
}

/* Between a tablet and a laptop the links sit a little closer, so the whole bar still fits across */
@media (min-width: 768px) and (max-width: 991.98px) {
    .navbar-expand-md .navbar-nav .nav-link {
        padding-left: 0.55rem;
        padding-right: 0.55rem;
    }

    .navbar-brand {
        margin-right: 0.75rem;
    }
}

.nav-link {
    color: rgba(255, 255, 255, 0.85);
    font-weight: 500;
    padding: var(--spacing-sm) 0.75rem;
    border-radius: var(--border-radius-sm);
    font-size: 0.9rem;
    display: inline-flex;
    align-items: center;
    gap: 8px;
    transition: var(--transition);
}

.nav-link i {
    font-size: 0.9rem;
}

.nav-link:hover,
.nav-link:focus {
    color: white;
    background-color: rgba(255, 255, 255, 0.1);
}

.nav-link.active {
    color: white;
}

.nav-link.active i {
    color: var(--secondary-light);
}

/* The country picker: a flag beside the country's name, and the same in its menu */
.country-picker .nav-link {
    border: none;
    background: none;
}

.country-flag {
    width: 1.25em;
    border-radius: 2px;
    text-align: center;
}

.country-picker .dropdown-item {
    display: flex;
    align-items: center;
    gap: 0.6rem;
    font-size: 0.9rem;
}

/* On phones the picker sits in the bar beside the menu button: just the flag, pushed to the right */
.country-picker-bar {
    margin-left: auto;
    margin-right: 0.5rem;
}

.country-picker-bar .country-name {
    display: none;
}

/* Between a tablet and a laptop the bar is tight, so the picker shows just the flag. The name shrinks to nothing
   rather than going, so the button keeps its line height and lines up with the links beside it. */
@media (min-width: 768px) and (max-width: 991.98px) {
    .country-name {
        width: 0;
        margin-left: -8px;
        overflow: hidden;
    }
}

.navbar-toggler {
    padding: 0.25rem;
    border: none;
    color: rgba(255, 255, 255, 0.85);
}

.navbar-toggler:focus {
    box-shadow: none;
}

/* -----------------------------
 * Cards
 * ----------------------------- */
.card {
    background: #fff;
    border: none;
    border-radius: var(--border-radius-lg);
    box-shadow: var(--card-shadow);
}

.section-card {
    padding: 2.5rem var(--spacing-lg);
}

.section-title {
    font-size: 1.75rem;
    margin-bottom: 0.35rem;
}

/* The heading card at the top of the pages in the nav bar (Features, Pricing, About and Contact) */
.page-intro {
    text-align: center;
}

.page-intro h1 {
    font-size: clamp(2rem, 5vw, 3.25rem);
    letter-spacing: -0.02em;
    margin-bottom: 0;
}

.page-intro h1 span {
    color: var(--secondary);
}

.section-lead {
    color: var(--muted);
    max-width: 640px;
    margin-bottom: 2rem;
}

/* The link from the line coding panel to the Features page, beneath its lead */
.features-link {
    margin: 1.25rem 0 0;
}

/* -----------------------------
 * Buttons (from the app)
 * ----------------------------- */
.btn-icon {
    height: 36px;
    padding: 0 24px;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    gap: 8px;
    border: none;
    border-radius: 20px;
    font-size: 0.925rem;
    font-weight: 500;
    color: white !important;
    text-decoration: none;
    box-shadow: 0 2px 5px rgba(0, 0, 0, 0.1);
    transition: var(--transition);
}

.btn-icon:active {
    transform: scale(0.98);
}

.btn-icon-lg {
    height: 46px;
    padding: 0 30px;
    border-radius: 23px;
    font-size: 1.05rem;
}

.btn-icon.btn-primary {
    background-color: var(--secondary);
}

/* Darkens on hover, as the green button does */
.btn-icon.btn-primary:hover {
    background-color: color-mix(in srgb, var(--secondary), var(--primary) 30%);
}

.btn-icon.btn-success {
    background-color: var(--success);
}

.btn-icon.btn-success:hover {
    background-color: var(--success-dark);
}

.btn-icon.btn-secondary {
    background-color: #ffffff;
    color: var(--primary) !important;
    border: 1px solid var(--border-color);
    box-shadow: none;
}

.btn-icon.btn-secondary:hover {
    background-color: var(--secondary-ultra-light);
}

/* -----------------------------
 * Hero
 * ----------------------------- */
.hero {
    padding: 2.5rem var(--spacing-lg) 0;
    text-align: center;
    overflow: hidden;
}

/* The lower part of the card: a pale band, edge to edge, for the diagram to sit on */
.hero-stage {
    margin: 1.25rem calc(-1 * var(--spacing-lg)) 0;
    padding: 0.75rem var(--spacing-lg) 0.5rem;
    background-color: var(--secondary-ultra-light);
}

.hero h1 {
    font-size: clamp(2rem, 5vw, 3.25rem);
    letter-spacing: -0.02em;
    margin-bottom: 1rem;
}

/* Headings carry a second beat in sea-glass blue, as the hero headline does */
.hero h1 span,
.section-title span {
    color: var(--secondary);
}

.hero-lead {
    font-size: 1.15rem;
    color: var(--muted);
    max-width: 620px;
    margin: 0 auto 1.75rem;
}

.hero-actions {
    display: flex;
    flex-wrap: wrap;
    gap: 0.75rem;
    justify-content: center;
}

.hero-note {
    margin-top: 0.9rem;
    font-size: 0.85rem;
    color: var(--muted);
}

.flow {
    display: block;
    width: 100%;
    max-width: 980px;
    height: auto;
    margin: 1.5rem auto 0;
}

.flow text {
    font-family: 'Quicksand', sans-serif;
    font-weight: 700;
    fill: var(--primary);
}

.flow .flow-caption {
    font-weight: 500;
    fill: var(--muted);
}

.flow .track {
    fill: none;
    stroke: var(--table-header-bg);
    stroke-width: 2;
    stroke-dasharray: 3 7;
    stroke-linecap: round;
}

/* The document glyphs are drawn through <use>, whose copies sit outside .flow for selector matching */
.flow-paper {
    fill: #fff;
    stroke: var(--secondary-light);
    stroke-width: 2;
    stroke-linejoin: round;
}

.flow-ink {
    stroke: var(--table-header-bg);
    stroke-width: 3;
    stroke-linecap: round;
}

.flow-ink-strong {
    stroke: var(--secondary);
    stroke-width: 3;
    stroke-linecap: round;
}

.flow .pill {
    fill: #fff;
    stroke: var(--border-color);
    stroke-width: 2;
}

.flow .pill-lit {
    fill: var(--success-light);
    stroke: var(--success-mid);
    stroke-width: 2;
}

.flow .tick {
    fill: var(--success);
}

/* -----------------------------
 * Line coding
 * ----------------------------- */
/* An abstract document in the same style as the hero's invoice, not a picture of the app */
.coding {
    max-width: 460px;
    margin: 0 auto;
    padding: 0.6rem 1.25rem 3rem;
    border: 2px solid var(--secondary-light);
    border-radius: var(--border-radius-lg);
    background: #fff;
}

.coding-line {
    display: grid;
    grid-template-columns: 1fr auto;
    align-items: center;
    gap: 1rem;
    margin: 0 -0.6rem;
    padding: 0.7rem 0.6rem;
    border-top: 1px solid var(--border-color);
    border-radius: var(--border-radius-sm);
}

.coding-line:first-child {
    border-top: none;
}

/* The supplier's shorthand and the clear description share one spot and swap when the line is coded */
.coding-desc {
    display: grid;
    align-items: center;
}

.coding-raw,
.coding-clear {
    grid-area: 1 / 1;
    font-size: 0.875rem;
}

.coding-raw {
    font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
    font-size: 0.75rem;
    letter-spacing: 0.04em;
    color: var(--muted);
    opacity: 0;
}

.coding-clear {
    font-weight: 700;
}

.coding-chips {
    position: relative;
    display: flex;
    gap: 0.35rem;
}

.coding-chip {
    padding: 2px 11px;
    border: 1px solid var(--secondary-light);
    border-radius: var(--badge-radius);
    background-color: #fff;
    font-size: 0.8rem;
    font-weight: 700;
    white-space: nowrap;
}

.coding-chip.is-tax {
    border-color: var(--success-mid);
    background-color: var(--success-light);
    color: var(--success);
}

/* The reason, shown as the tooltip it is in the app */
.coding-tip {
    position: absolute;
    top: calc(100% + 9px);
    right: 0;
    z-index: 1;
    padding: 5px 12px;
    border-radius: var(--border-radius-sm);
    background-color: var(--primary);
    color: #fff;
    font-size: 0.8rem;
    white-space: nowrap;
    opacity: 0;
}

.coding-tip::before {
    content: '';
    position: absolute;
    bottom: 100%;
    right: 28px;
    border: 6px solid transparent;
    border-bottom-color: var(--primary);
}

.coding-tip i {
    margin-right: 5px;
    color: var(--facet-blue-light);
}

.coding-line:last-child .coding-tip {
    opacity: 1;
}

@media (max-width: 575.98px) {
    /* Room beneath each line for its reason, so it never covers the next line */
    .coding-line {
        grid-template-columns: 1fr;
        gap: 0.4rem;
        padding-bottom: 2.9rem;
    }

    .coding {
        padding-bottom: 0.75rem;
    }

    .coding-chips {
        justify-self: start;
    }

    .coding-tip {
        right: auto;
        left: 0;
    }

    .coding-tip::before {
        right: auto;
        left: 28px;
    }
}

@media (prefers-reduced-motion: no-preference) {
    .coding-line:nth-child(1) { animation: coding-active-1 12s linear infinite; }
    .coding-line:nth-child(2) { animation: coding-active-2 12s linear infinite; }
    .coding-line:nth-child(3) { animation: coding-active-3 12s linear infinite; }

    .coding-line:nth-child(1) :is(.coding-chip, .coding-clear) { animation: coding-chips-1 12s ease-out infinite; }
    .coding-line:nth-child(2) :is(.coding-chip, .coding-clear) { animation: coding-chips-2 12s ease-out infinite; }
    .coding-line:nth-child(3) :is(.coding-chip, .coding-clear) { animation: coding-chips-3 12s ease-out infinite; }

    .coding-line:nth-child(1) .coding-raw { animation: coding-raw-1 12s linear infinite; }
    .coding-line:nth-child(2) .coding-raw { animation: coding-raw-2 12s linear infinite; }
    .coding-line:nth-child(3) .coding-raw { animation: coding-raw-3 12s linear infinite; }

    .coding-line:nth-child(1) .coding-tip { animation: coding-tip-1 12s linear infinite; }
    .coding-line:nth-child(2) .coding-tip { animation: coding-tip-2 12s linear infinite; }
    .coding-line:nth-child(3) .coding-tip { animation: coding-tip-3 12s linear infinite; }
}

/* Each line is lit for its third of the cycle */
@keyframes coding-active-1 {
    0%, 31% { background-color: var(--secondary-ultra-light); }
    33%, 100% { background-color: #fff; }
}

@keyframes coding-active-2 {
    0%, 33% { background-color: #fff; }
    35%, 64% { background-color: var(--secondary-ultra-light); }
    66%, 100% { background-color: #fff; }
}

@keyframes coding-active-3 {
    0%, 66% { background-color: #fff; }
    68%, 96% { background-color: var(--secondary-ultra-light); }
    100% { background-color: #fff; }
}

/* The codes arrive when their line is reached and stay until the cycle ends */
@keyframes coding-chips-1 {
    0% { opacity: 0; transform: translateX(-8px); }
    4%, 96% { opacity: 1; transform: translateX(0); }
    100% { opacity: 0; transform: translateX(0); }
}

@keyframes coding-chips-2 {
    0%, 34% { opacity: 0; transform: translateX(-8px); }
    38%, 96% { opacity: 1; transform: translateX(0); }
    100% { opacity: 0; transform: translateX(0); }
}

@keyframes coding-chips-3 {
    0%, 67% { opacity: 0; transform: translateX(-8px); }
    71%, 96% { opacity: 1; transform: translateX(0); }
    100% { opacity: 0; transform: translateX(0); }
}

/* The shorthand is there until its line is reached, then makes way for the clear description */
@keyframes coding-raw-1 {
    0% { opacity: 1; }
    3%, 97% { opacity: 0; }
    100% { opacity: 1; }
}

@keyframes coding-raw-2 {
    0%, 34% { opacity: 1; }
    37%, 97% { opacity: 0; }
    100% { opacity: 1; }
}

@keyframes coding-raw-3 {
    0%, 67% { opacity: 1; }
    70%, 97% { opacity: 0; }
    100% { opacity: 1; }
}

@keyframes coding-tip-1 {
    0%, 8% { opacity: 0; }
    12%, 30% { opacity: 1; }
    33%, 100% { opacity: 0; }
}

@keyframes coding-tip-2 {
    0%, 41% { opacity: 0; }
    45%, 63% { opacity: 1; }
    66%, 100% { opacity: 0; }
}

@keyframes coding-tip-3 {
    0%, 74% { opacity: 0; }
    78%, 95% { opacity: 1; }
    98%, 100% { opacity: 0; }
}

#coding .section-lead {
    margin-bottom: 0;
}

/* A small caption above an example from the app, eg. whose list or invoice it is */
.demo-caption {
    margin: 0 0 0.6rem;
    font-size: 0.9rem;
    color: var(--muted);
}

/* The name stands out by weight alone, in the same soft grey */
.demo-caption strong {
    font-weight: 700;
}

/* On a phone the caption sits snugly above its example */
@media (max-width: 575.98px) {
    .demo-caption {
        margin-bottom: 0.3rem;
    }
}

/* -----------------------------
 * Line coding: the app's review table
 * ----------------------------- */
.review {
    max-width: 700px;
    margin: 0 auto;
}

.review-table {
    width: 100%;
    font-size: 0.85rem;
    border-collapse: collapse;
    background: #fff;
}

.review-table thead {
    background: var(--table-header-bg);
}

.review-table th,
.review-table td {
    padding: 6px 8px;
    border: 1px solid var(--grid-border);
    vertical-align: top;
    text-align: left;
}

/* The heading matches the app's tables */
.review-table th {
    border-color: var(--table-header-bg);
    color: var(--table-header-text);
    font-weight: 500;
    letter-spacing: 0.05em;
    white-space: nowrap;
}

/* An amount never breaks between its currency symbol and the figure */
.review-vat,
.review-total {
    white-space: nowrap;
}

/* The supplier's shorthand and the clear description share one spot and swap when the line is coded */
.review-desc {
    display: grid;
}

.review-raw,
.review-clear {
    grid-area: 1 / 1;
}

.review-raw {
    color: var(--muted);
    opacity: 0;
}

.review-pick {
    position: relative;
}

/* A cell's placeholder and its value share one spot */
.review-cell {
    display: grid;
}

.review-cell > * {
    grid-area: 1 / 1;
}

/* The shimmer the app shows in a cell whose value has not arrived yet */
.review-skeleton {
    width: 80%;
    height: 1.1em;
    margin-top: 0.2em;
    border-radius: 4px;
    background: linear-gradient(90deg, var(--skeleton) 25%, var(--skeleton-shine) 37%, var(--skeleton) 63%);
    background-size: 400% 100%;
    opacity: 0;
}

@keyframes review-shimmer {
    0% { background-position: 100% 50%; }
    100% { background-position: 0 50%; }
}

.review-value,
.review-clear {
    display: inline-block;
}

/* The reason, as the app shows it when you hover over an account code or tax rate */
.review-tip {
    position: absolute;
    bottom: calc(100% + 8px);
    left: 50%;
    z-index: 1;
    width: max-content;
    max-width: 280px;
    padding: 8px 12px;
    border: 1px solid var(--tip-border);
    border-radius: var(--border-radius-sm);
    background: #fff;
    box-shadow: 0 2px 8px rgba(0, 0, 0, 0.08);
    font-size: 0.82rem;
    line-height: 1.5;
    transform: translateX(-50%);
    opacity: 0;
}

.review-tip::before,
.review-tip::after {
    content: '';
    position: absolute;
    left: 50%;
    transform: translateX(-50%);
    border-left: 8px solid transparent;
    border-right: 8px solid transparent;
}

.review-tip::before {
    bottom: -8px;
    border-top: 8px solid var(--tip-border);
}

.review-tip::after {
    bottom: -6px;
    border-left-width: 7px;
    border-right-width: 7px;
    border-top: 7px solid #fff;
}

.review-table tr:first-child .review-tip {
    opacity: 1;
}

/* The first line's reason opens beneath its cell, as there's a caption above the table rather than room */
.review-table tbody tr:first-child .review-tip {
    top: calc(100% + 8px);
    bottom: auto;
}

.review-table tbody tr:first-child .review-tip::before {
    top: -8px;
    bottom: auto;
    border-top: none;
    border-bottom: 8px solid var(--tip-border);
}

.review-table tbody tr:first-child .review-tip::after {
    top: -6px;
    bottom: auto;
    border-top: none;
    border-bottom: 7px solid #fff;
}

@media (max-width: 575.98px) {
    .review-table {
        font-size: 0.75rem;
    }

    .review-table th,
    .review-table td {
        padding: 5px 6px;
    }

    .review-num,
    .review-vat {
        display: none;
    }

    .review-tip {
        max-width: 200px;
    }
}

@media (prefers-reduced-motion: no-preference) {
    /* The 20 second cycle opens with two seconds of the supplier's own wording, so it can be read before the
       first line is rewritten. Each line then gets about five and a half seconds, four of them with its reason.
       As in the app, waiting cells shimmer and arriving values write in from left to right, column by column.
       A value is both clipped away and transparent on either side of the restart. Browsers can update those two
       properties a frame apart, and with only one of them hiding the text it flashed up as the cycle reset. */
    .review-table td:nth-child(3) .review-value { animation-delay: 0.05s; }
    .review-table td:nth-child(4) .review-value { animation-delay: 0.1s; }
    .review-table td:nth-child(5) .review-value { animation-delay: 0.15s; }

    .review-table tbody tr:nth-child(1) :is(.review-value, .review-clear) { animation-name: review-fill-1; animation-duration: 20s; animation-timing-function: ease; animation-iteration-count: infinite; }
    .review-table tbody tr:nth-child(1) .review-raw { animation: review-raw-1 20s linear infinite; }
    .review-table tbody tr:nth-child(1) .review-skeleton { animation: review-shimmer 1.4s ease infinite, review-wait-1 20s linear infinite; }
    .review-table tbody tr:nth-child(1) .review-tip { animation: review-tip-1 20s linear infinite; }
    .review-table tbody tr:nth-child(1) .has-tip { animation: review-explain-1 20s linear infinite; }

    .review-table tbody tr:nth-child(2) :is(.review-value, .review-clear) { animation-name: review-fill-2; animation-duration: 20s; animation-timing-function: ease; animation-iteration-count: infinite; }
    .review-table tbody tr:nth-child(2) .review-raw { animation: review-raw-2 20s linear infinite; }
    .review-table tbody tr:nth-child(2) .review-skeleton { animation: review-shimmer 1.4s ease infinite, review-wait-2 20s linear infinite; }
    .review-table tbody tr:nth-child(2) .review-tip { animation: review-tip-2 20s linear infinite; }
    .review-table tbody tr:nth-child(2) .has-tip { animation: review-explain-2 20s linear infinite; }

    .review-table tbody tr:nth-child(3) :is(.review-value, .review-clear) { animation-name: review-fill-3; animation-duration: 20s; animation-timing-function: ease; animation-iteration-count: infinite; }
    .review-table tbody tr:nth-child(3) .review-raw { animation: review-raw-3 20s linear infinite; }
    .review-table tbody tr:nth-child(3) .review-skeleton { animation: review-shimmer 1.4s ease infinite, review-wait-3 20s linear infinite; }
    .review-table tbody tr:nth-child(3) .review-tip { animation: review-tip-3 20s linear infinite; }
    .review-table tbody tr:nth-child(3) .has-tip { animation: review-explain-3 20s linear infinite; }
}

/* Line 1: filled in at 10%, reason on screen from 16% to 36% */
@keyframes review-fill-1 {
    0% { clip-path: inset(0 100% 0 0); opacity: 0; }
    1%, 10% { clip-path: inset(0 100% 0 0); opacity: 1; }
    12.5%, 97% { clip-path: inset(0 0 0 0); opacity: 1; }
    99% { clip-path: inset(0 0 0 0); opacity: 0; }
    100% { clip-path: inset(0 100% 0 0); opacity: 0; }
}

@keyframes review-raw-1 {
    0%, 9% { opacity: 1; }
    10%, 98% { opacity: 0; }
    100% { opacity: 1; }
}

@keyframes review-wait-1 {
    0%, 10% { opacity: 1; }
    11%, 98% { opacity: 0; }
    100% { opacity: 1; }
}

@keyframes review-tip-1 {
    0%, 14% { opacity: 0; }
    16%, 36% { opacity: 1; }
    38%, 100% { opacity: 0; }
}

@keyframes review-explain-1 {
    0%, 14% { background-color: #fff; }
    16%, 36% { background-color: var(--secondary-ultra-light); }
    38%, 100% { background-color: #fff; }
}

/* Line 2: filled in at 38%, reason on screen from 44% to 64% */
@keyframes review-fill-2 {
    0% { clip-path: inset(0 100% 0 0); opacity: 0; }
    1%, 38% { clip-path: inset(0 100% 0 0); opacity: 1; }
    40.5%, 97% { clip-path: inset(0 0 0 0); opacity: 1; }
    99% { clip-path: inset(0 0 0 0); opacity: 0; }
    100% { clip-path: inset(0 100% 0 0); opacity: 0; }
}

@keyframes review-raw-2 {
    0%, 37% { opacity: 1; }
    38%, 98% { opacity: 0; }
    100% { opacity: 1; }
}

@keyframes review-wait-2 {
    0%, 38% { opacity: 1; }
    39%, 98% { opacity: 0; }
    100% { opacity: 1; }
}

@keyframes review-tip-2 {
    0%, 42% { opacity: 0; }
    44%, 64% { opacity: 1; }
    66%, 100% { opacity: 0; }
}

@keyframes review-explain-2 {
    0%, 42% { background-color: #fff; }
    44%, 64% { background-color: var(--secondary-ultra-light); }
    66%, 100% { background-color: #fff; }
}

/* Line 3: filled in at 66%, reason on screen from 72% to 92% */
@keyframes review-fill-3 {
    0% { clip-path: inset(0 100% 0 0); opacity: 0; }
    1%, 66% { clip-path: inset(0 100% 0 0); opacity: 1; }
    68.5%, 97% { clip-path: inset(0 0 0 0); opacity: 1; }
    99% { clip-path: inset(0 0 0 0); opacity: 0; }
    100% { clip-path: inset(0 100% 0 0); opacity: 0; }
}

@keyframes review-raw-3 {
    0%, 65% { opacity: 1; }
    66%, 98% { opacity: 0; }
    100% { opacity: 1; }
}

@keyframes review-wait-3 {
    0%, 66% { opacity: 1; }
    67%, 98% { opacity: 0; }
    100% { opacity: 1; }
}

@keyframes review-tip-3 {
    0%, 70% { opacity: 0; }
    72%, 92% { opacity: 1; }
    94%, 100% { opacity: 0; }
}

@keyframes review-explain-3 {
    0%, 70% { background-color: #fff; }
    72%, 92% { background-color: var(--secondary-ultra-light); }
    94%, 100% { background-color: #fff; }
}

/* -----------------------------
 * Products
 * ----------------------------- */
.step {
    height: 100%;
    padding: 1.5rem;
    border: 1px solid var(--border-color);
    border-radius: var(--border-radius-lg);
    background: var(--background);
}

.step-icon {
    width: 48px;
    height: 48px;
    border-radius: 50%;
    display: flex;
    align-items: center;
    justify-content: center;
    margin-bottom: 1rem;
    color: #fff;
    font-size: 1.1rem;
    background-color: var(--secondary);
}

.step-icon.is-green {
    background-color: var(--success);
}

.step-icon.is-red {
    background-color: var(--danger);
}

.step h3 {
    font-size: 1.15rem;
    margin-bottom: 0.4rem;
}

.step p {
    margin: 0;
    color: var(--muted);
    font-size: 0.95rem;
}

.feature-list {
    list-style: none;
    padding: 0;
    margin: 2rem 0 0;
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(260px, 1fr));
    gap: 0.75rem 2rem;
}

.feature-list li {
    display: flex;
    gap: 0.75rem;
    align-items: baseline;
    font-size: 0.95rem;
    color: var(--muted);
}

.feature-list i {
    color: var(--success);
}

.connects {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: 0.6rem;
    margin-top: 2rem;
    padding-top: 1.5rem;
    border-top: 1px solid var(--border-color);
    color: var(--muted);
    font-size: 0.95rem;
}

.connect-badge {
    padding: 4px 14px;
    border-radius: var(--badge-radius);
    background-color: var(--secondary-ultra-light);
    color: var(--primary);
    font-weight: 700;
    font-size: 0.875rem;
}

/* -----------------------------
 * Prices
 * ----------------------------- */
.price-head {
    display: flex;
    flex-wrap: wrap;
    justify-content: space-between;
    align-items: flex-end;
    gap: 1rem;
    margin-bottom: 2rem;
}

/* The heading and lead take all the room */
.price-head > div {
    flex: 1 1 22rem;
    min-width: 0;
}

.price-head .section-lead {
    max-width: none;
    margin-bottom: 0;
}

.plan {
    height: 100%;
    padding: 1.5rem 1.25rem;
    text-align: center;
    border: 1px solid var(--border-color);
    border-radius: var(--border-radius-lg);
    background: var(--secondary-ultra-light);
    display: flex;
    flex-direction: column;
    align-items: center;
}

.plan-credits {
    font-size: 2rem;
    font-weight: 700;
    line-height: 1;
}

.plan-credits-label {
    color: var(--muted);
    font-size: 0.85rem;
    margin-bottom: 0.4rem;
}

.plan-fee {
    font-size: 1.5rem;
    font-weight: 700;
    color: var(--success);
}

.plan-fee small {
    font-size: 0.8rem;
    font-weight: 500;
    color: var(--muted);
}

.price-notes {
    margin: 1.75rem 0 0;
    color: var(--muted);
    font-size: 0.9rem;
}

.price-notes + .price-notes {
    margin-top: 0.6rem;
}

/* -----------------------------
 * Legal pages
 * ----------------------------- */
/* Full width like the front page panels, with the text held to a comfortable measure, centred, inside */
/* Full width up to 900px. The card is a flex column, where a centred block would otherwise shrink to fit a
   short page's text. */
.legal-inner {
    width: 100%;
    max-width: 900px;
    margin: 0 auto;
}

.legal h1 {
    font-size: 1.75rem;
    margin-bottom: 0.2rem;
}

.legal-date {
    color: var(--muted);
    font-size: 0.85rem;
    margin-bottom: 1.25rem;
}

.legal h2 {
    font-size: 1.05rem;
    margin: 1.25rem 0 0.3rem;
}

/* Running text in the softer grey the rest of the site uses, headings stay slate */
.legal p,
.legal li {
    color: var(--muted);
    font-size: 0.95rem;
    line-height: 1.5;
}

.legal p {
    margin-bottom: 0.7rem;
}

.legal strong {
    color: var(--primary);
}

.legal ul {
    padding-left: 1.25rem;
}

.legal li {
    margin-bottom: 0.25rem;
}

.about h1 span {
    color: var(--secondary);
}

/* Accounting and software meeting in the cube. The animation is in diagrams.css. */
.meet {
    width: 100%;
    max-width: 520px;
    margin: 1.25rem auto 1rem;
}

@media (max-width: 479.98px) {
    /* Once the diagram has shrunk to phone size, the labels are enlarged to stay readable */
    .meet text {
        font-size: 24px;
    }
}

/* On a phone the narrow column needs more air between lines, paragraphs and around the diagram */
@media (max-width: 575.98px) {
    .legal p,
    .legal li {
        line-height: 1.6;
    }

    .legal p {
        margin-bottom: 1rem;
    }

    .legal h2 {
        margin-top: 1.25rem;
    }

    .meet {
        margin: 1.75rem auto 1.5rem;
    }

    .legal {
        padding-left: 1.25rem;
        padding-right: 1.25rem;
    }
}

/* The About page's panel uses its full width as two columns, stacking on narrower screens */
.about-columns {
    display: grid;
    grid-template-columns: repeat(2, minmax(0, 1fr));
    gap: 1rem 3rem;
}

.about-columns p:last-child {
    margin-bottom: 0;
}

/* The founders sit beneath the story, in the same panel */
.about-people {
    margin-top: 2rem;
}

/* The company details close the panel, beneath the founders */
.about-company {
    margin-top: 2rem;
}

.about p:last-child {
    margin-bottom: 0;
}

/* A heading that opens a panel sits at the top of its card */
.about > h2:first-child {
    margin-top: 0;
}

/* The story's paragraph sits level with the diagram beside it */
.about-story {
    align-items: center;
}

.about-story .meet {
    margin: 0 auto;
}

@media (max-width: 767.98px) {
    .about-columns {
        grid-template-columns: 1fr;
        gap: 1.25rem;
    }
}

/* On a phone the button rows on the About and Contact pages (press kit, email) sit centred */
@media (max-width: 575.98px) {
    .about .about-actions {
        justify-content: center;
    }
}

/* A row of buttons in the page's text column */
.about-actions {
    display: flex;
    flex-wrap: wrap;
    gap: 0.75rem;
}

.about-photo img {
    display: block;
    width: 100%;
    height: auto;
    border-radius: var(--border-radius-lg);
}

.about-photo figcaption {
    margin-top: 0.5rem;
    font-size: 0.85rem;
    color: var(--muted);
    text-align: center;
}

/* -----------------------------
 * Closing band
 * ----------------------------- */
.closing {
    background-color: var(--primary);
    color: #fff;
    text-align: center;
    padding: 1.75rem var(--spacing-lg) 2rem;
}

.closing h2 {
    color: #fff;
    font-size: 1.75rem;
}

.closing p {
    color: rgba(255, 255, 255, 0.75);
    margin-bottom: 1.1rem;
}

/* The cube is its own image so the browser can float it smoothly between pixels */
.closing-mark {
    align-self: center;
    margin-bottom: 1rem;
    filter: drop-shadow(0 10px 14px rgba(20, 28, 36, 0.38));
    will-change: transform;
}

@media (prefers-reduced-motion: no-preference) {
    .closing-mark {
        animation: floaty 6s ease-in-out infinite;
    }
}

@keyframes floaty {
    0%, 100% { transform: translateY(0); }
    50% { transform: translateY(-7px); }
}

/* -----------------------------
 * Small screens
 * ----------------------------- */
@media (max-width: 575.98px) {
    .main-container {
        padding: var(--spacing-md);
        gap: var(--spacing-md);
    }

    .navbar {
        padding: 9.5px var(--spacing-md) var(--spacing-sm);
    }

    /* Less headroom in each panel on a phone, where the desktop padding reads as empty space */
    .section-card,
    .hero {
        padding: 1.75rem var(--spacing-md);
    }

    .hero {
        padding-bottom: 0;
    }

    .closing {
        padding: 1.5rem var(--spacing-md);
    }

    /* Stacked on a phone, the coding and pricing panels' headings and leads read better centred */
    #coding .section-title,
    #coding .section-lead,
    #prices .section-title,
    #prices .section-lead {
        text-align: center;
        margin-left: auto;
        margin-right: auto;
    }

    #prices .price-head {
        justify-content: center;
    }

    #coding .features-link {
        text-align: center;
    }

    .hero-lead {
        font-size: 1.05rem;
    }

    /* The links come first and the copyright takes a line of its own beneath them, so the links sit clear of the
       rounded corners at the bottom of a phone screen */
    footer {
        flex-direction: column;
        gap: 0.3rem;
    }

    footer > span:first-child {
        order: 1;
    }

    footer > .footer-dot {
        display: none;
    }

    /* The volume pricing note is centred with the question on its own line */
    .price-notes {
        text-align: center;
    }

    .price-notes-q {
        display: block;
    }

    /* Slimmer large buttons so See Prices and Get Started fit side by side on a phone */
    .btn-icon-lg {
        padding: 0 20px;
        font-size: 1rem;
    }

    .hero-actions {
        gap: 0.6rem;
    }

    /* The portrait diagram has less built-in headroom than the wide one, so the band gives it some */
    .hero-stage {
        margin-left: calc(-1 * var(--spacing-md));
        margin-right: calc(-1 * var(--spacing-md));
        padding: 1.5rem var(--spacing-md) 1.25rem;
    }

}

/* The burger menu's links, below the width where the nav bar folds */
@media (max-width: 767.98px) {
    .navbar-collapse {
        padding: var(--spacing-sm) 0;
    }
}

@media (prefers-reduced-motion: reduce) {
    html {
        scroll-behavior: auto;
    }
}
