/* ==========================================================================
   Utilities
   --------------------------------------------------------------------------
   Tailwind-familiar class names mapped onto our own tokens, so markup reads
   the way you'd expect without pulling in a framework or a build step. This
   layer stays intentionally small: layout, spacing, type and colour only.
   Anything with state, pseudo-elements or more than a few declarations
   becomes a component in components.css instead.

   Responsive variants use the `md:` and `lg:` prefixes at 768px and 1080px.
   ========================================================================== */

/* --- Shell / container -------------------------------------------------- */

.af-shell {
	width: 100%;
	max-width: var(--af-shell);
	margin-inline: auto;
	padding-inline: var(--af-gutter);
}

.af-shell-narrow { max-width: var(--af-shell-narrow); }
.af-shell-wide { max-width: var(--af-shell-wide); }

.af-section {
	position: relative;
	padding-block: var(--af-section-y);
}

.af-section-lg { padding-block: var(--af-section-y-lg); }
.af-section-tight { padding-block: clamp(2rem, 4vw, 3.5rem); }

/* --- Display ----------------------------------------------------------- */

.block { display: block; }
.inline-block { display: inline-block; }
.inline { display: inline; }
.flex { display: flex; }
.inline-flex { display: inline-flex; }
.grid { display: grid; }
.contents { display: contents; }
.hidden { display: none; }

/* --- Flex & grid ------------------------------------------------------- */

.flex-col { flex-direction: column; }
.flex-row { flex-direction: row; }
.flex-wrap { flex-wrap: wrap; }
.flex-nowrap { flex-wrap: nowrap; }
.flex-1 { flex: 1 1 0%; }
.flex-auto { flex: 1 1 auto; }
.flex-none { flex: none; }
.shrink-0 { flex-shrink: 0; }
.grow { flex-grow: 1; }

.items-start { align-items: flex-start; }
.items-center { align-items: center; }
.items-end { align-items: flex-end; }
.items-baseline { align-items: baseline; }
.items-stretch { align-items: stretch; }

.justify-start { justify-content: flex-start; }
.justify-center { justify-content: center; }
.justify-end { justify-content: flex-end; }
.justify-between { justify-content: space-between; }

.self-start { align-self: flex-start; }
.self-center { align-self: center; }
.self-end { align-self: flex-end; }

.grid-cols-1 { grid-template-columns: repeat(1, minmax(0, 1fr)); }
.grid-cols-2 { grid-template-columns: repeat(2, minmax(0, 1fr)); }
.grid-cols-3 { grid-template-columns: repeat(3, minmax(0, 1fr)); }
.grid-cols-4 { grid-template-columns: repeat(4, minmax(0, 1fr)); }
.grid-cols-5 { grid-template-columns: repeat(5, minmax(0, 1fr)); }
.grid-cols-6 { grid-template-columns: repeat(6, minmax(0, 1fr)); }

.col-span-2 { grid-column: span 2 / span 2; }
.col-span-3 { grid-column: span 3 / span 3; }
.col-span-full { grid-column: 1 / -1; }
.row-span-2 { grid-row: span 2 / span 2; }

/* Auto-fit grids for product and category collections. The min track is the
   knob that controls density at every breakpoint without media queries. */
.af-autogrid { display: grid; gap: var(--af-space-4); grid-template-columns: repeat(auto-fill, minmax(var(--af-min, 160px), 1fr)); }
.af-autogrid-sm { --af-min: 132px; }
.af-autogrid-md { --af-min: 184px; }
.af-autogrid-lg { --af-min: 240px; }
.af-autogrid-xl { --af-min: 300px; }

/* --- Gap --------------------------------------------------------------- */

.gap-0 { gap: 0; }
.gap-1 { gap: var(--af-space-1); }
.gap-2 { gap: var(--af-space-2); }
.gap-3 { gap: var(--af-space-3); }
.gap-4 { gap: var(--af-space-4); }
.gap-5 { gap: var(--af-space-5); }
.gap-6 { gap: var(--af-space-6); }
.gap-7 { gap: var(--af-space-7); }
.gap-8 { gap: var(--af-space-8); }
.gap-9 { gap: var(--af-space-9); }
.gap-10 { gap: var(--af-space-10); }

.gap-x-2 { column-gap: var(--af-space-2); }
.gap-x-4 { column-gap: var(--af-space-4); }
.gap-x-6 { column-gap: var(--af-space-6); }
.gap-y-2 { row-gap: var(--af-space-2); }
.gap-y-4 { row-gap: var(--af-space-4); }
.gap-y-6 { row-gap: var(--af-space-6); }
.gap-y-8 { row-gap: var(--af-space-8); }

/* --- Margin / padding -------------------------------------------------- */

.m-0 { margin: 0; }
.mx-auto { margin-inline: auto; }

.mt-1 { margin-top: var(--af-space-1); }
.mt-2 { margin-top: var(--af-space-2); }
.mt-3 { margin-top: var(--af-space-3); }
.mt-4 { margin-top: var(--af-space-4); }
.mt-5 { margin-top: var(--af-space-5); }
.mt-6 { margin-top: var(--af-space-6); }
.mt-7 { margin-top: var(--af-space-7); }
.mt-8 { margin-top: var(--af-space-8); }
.mt-9 { margin-top: var(--af-space-9); }
.mt-10 { margin-top: var(--af-space-10); }

.mb-0 { margin-bottom: 0; }
.mb-1 { margin-bottom: var(--af-space-1); }
.mb-2 { margin-bottom: var(--af-space-2); }
.mb-3 { margin-bottom: var(--af-space-3); }
.mb-4 { margin-bottom: var(--af-space-4); }
.mb-6 { margin-bottom: var(--af-space-6); }
.mb-8 { margin-bottom: var(--af-space-8); }

.p-0 { padding: 0; }
.p-2 { padding: var(--af-space-2); }
.p-3 { padding: var(--af-space-3); }
.p-4 { padding: var(--af-space-4); }
.p-5 { padding: var(--af-space-5); }
.p-6 { padding: var(--af-space-6); }
.p-7 { padding: var(--af-space-7); }
.p-8 { padding: var(--af-space-8); }

.px-3 { padding-inline: var(--af-space-3); }
.px-4 { padding-inline: var(--af-space-4); }
.px-5 { padding-inline: var(--af-space-5); }
.px-6 { padding-inline: var(--af-space-6); }
.py-1 { padding-block: var(--af-space-1); }
.py-2 { padding-block: var(--af-space-2); }
.py-3 { padding-block: var(--af-space-3); }
.py-4 { padding-block: var(--af-space-4); }
.py-6 { padding-block: var(--af-space-6); }
.py-8 { padding-block: var(--af-space-8); }

/* --- Sizing ------------------------------------------------------------ */

.w-full { width: 100%; }
.w-auto { width: auto; }
.h-full { height: 100%; }
.min-h-0 { min-height: 0; }
.max-w-none { max-width: none; }
.max-w-xs { max-width: 20rem; }
.max-w-sm { max-width: 26rem; }
.max-w-md { max-width: 34rem; }
.max-w-lg { max-width: 42rem; }
.max-w-xl { max-width: 52rem; }

.aspect-square { aspect-ratio: 1 / 1; }
.aspect-video { aspect-ratio: 16 / 9; }
.aspect-portrait { aspect-ratio: 4 / 5; }

/* --- Position ---------------------------------------------------------- */

.relative { position: relative; }
.absolute { position: absolute; }
.fixed { position: fixed; }
.sticky { position: sticky; }
.inset-0 { inset: 0; }
.top-0 { top: 0; }
.right-0 { right: 0; }
.bottom-0 { bottom: 0; }
.left-0 { left: 0; }

.overflow-hidden { overflow: hidden; }
.overflow-x-auto { overflow-x: auto; }
.overflow-y-auto { overflow-y: auto; }

.z-10 { z-index: 10; }
.z-20 { z-index: 20; }

/* --- Typography -------------------------------------------------------- */

.font-display { font-family: var(--af-font-display); }
.font-ui { font-family: var(--af-font-ui); }

.text-2xs { font-size: var(--af-text-2xs); }
.text-xs { font-size: var(--af-text-xs); }
.text-sm { font-size: var(--af-text-sm); }
.text-base { font-size: var(--af-text-base); }
.text-md { font-size: var(--af-text-md); }
.text-lg { font-size: var(--af-text-lg); }
.text-xl { font-size: var(--af-text-xl); }
.text-2xl { font-size: var(--af-text-2xl); }
.text-3xl { font-size: var(--af-text-3xl); }
.text-4xl { font-size: var(--af-text-4xl); }
.text-5xl { font-size: var(--af-text-5xl); }

.font-normal { font-weight: 450; }
.font-medium { font-weight: 500; }
.font-semibold { font-weight: 600; }
.font-bold { font-weight: 700; }
.font-extrabold { font-weight: 800; }

.italic { font-style: italic; }
.uppercase { text-transform: uppercase; }
.capitalize { text-transform: capitalize; }
.normal-case { text-transform: none; }

.leading-tight { line-height: var(--af-leading-tight); }
.leading-snug { line-height: var(--af-leading-snug); }
.leading-normal { line-height: var(--af-leading-normal); }
.leading-relaxed { line-height: var(--af-leading-relaxed); }

.tracking-tight { letter-spacing: var(--af-track-tight); }
.tracking-normal { letter-spacing: var(--af-track-normal); }
.tracking-wide { letter-spacing: var(--af-track-wide); }
.tracking-caps { letter-spacing: var(--af-track-caps); }

.text-left { text-align: left; }
.text-center { text-align: center; }
.text-right { text-align: right; }

.no-underline { text-decoration: none; }
.line-through { text-decoration: line-through; }
.tabular { font-variant-numeric: tabular-nums; }

.text-balance { text-wrap: balance; }
.text-pretty { text-wrap: pretty; }

/* Line clamping for product titles, which vary wildly in length. */
.clamp-1,
.clamp-2,
.clamp-3 {
	display: -webkit-box;
	-webkit-box-orient: vertical;
	overflow: hidden;
}
.clamp-1 { -webkit-line-clamp: 1; line-clamp: 1; }
.clamp-2 { -webkit-line-clamp: 2; line-clamp: 2; }
.clamp-3 { -webkit-line-clamp: 3; line-clamp: 3; }

/* --- Colour ------------------------------------------------------------ */

.text-ink { color: var(--af-ink); }
.text-soft { color: var(--af-ink-soft); }
.text-muted { color: var(--af-ink-muted); }
.text-faint { color: var(--af-ink-faint); }
.text-cream { color: var(--af-cream); }
.text-white { color: var(--af-white); }
.text-cocoa { color: var(--af-cocoa-700); }
.text-clay { color: var(--af-clay-400); }
.text-caramel { color: var(--af-caramel); }
.text-terracotta { color: var(--af-terracotta); }
.text-leaf { color: var(--af-leaf); }
.text-chili { color: var(--af-chili); }

.bg-transparent { background-color: transparent; }
.bg-white { background-color: var(--af-white); }
.bg-cream { background-color: var(--af-cream); }
.bg-cream-warm { background-color: var(--af-cream-warm); }
.bg-sand { background-color: var(--af-sand); }
.bg-sand-deep { background-color: var(--af-sand-deep); }
.bg-caramel { background-color: var(--af-caramel); }
.bg-caramel-soft { background-color: var(--af-caramel-soft); }
.bg-cocoa { background-color: var(--af-cocoa-700); }
.bg-cocoa-900 { background-color: var(--af-cocoa-900); }
.bg-espresso { background-color: var(--af-espresso); }
.bg-terracotta { background-color: var(--af-terracotta); }
.bg-terracotta-soft { background-color: var(--af-terracotta-soft); }
.bg-leaf { background-color: var(--af-leaf); }
.bg-leaf-soft { background-color: var(--af-leaf-soft); }
.bg-honey-soft { background-color: var(--af-honey-soft); }

/* --- Border ------------------------------------------------------------ */

.border { border: 1px solid var(--af-line); }
.border-2 { border: 2px solid var(--af-line); }
.border-0 { border: 0; }
.border-t { border-top: 1px solid var(--af-line); }
.border-b { border-bottom: 1px solid var(--af-line); }
.border-dashed { border-style: dashed; }
.border-soft { border-color: var(--af-line-soft); }
.border-strong { border-color: var(--af-line-strong); }
.border-caramel { border-color: var(--af-caramel); }
.border-leaf { border-color: var(--af-leaf); }

.rounded-none { border-radius: 0; }
.rounded-xs { border-radius: var(--af-r-xs); }
.rounded-sm { border-radius: var(--af-r-sm); }
.rounded-md { border-radius: var(--af-r-md); }
.rounded-lg { border-radius: var(--af-r-lg); }
.rounded-xl { border-radius: var(--af-r-xl); }
.rounded-2xl { border-radius: var(--af-r-2xl); }
.rounded-full { border-radius: var(--af-r-pill); }
.rounded-tile { border-radius: var(--af-r-tile); }
.rounded-tile-alt { border-radius: var(--af-r-tile-alt); }

/* --- Elevation --------------------------------------------------------- */

.shadow-none { box-shadow: none; }
.shadow-xs { box-shadow: var(--af-shadow-xs); }
.shadow-sm { box-shadow: var(--af-shadow-sm); }
.shadow-md { box-shadow: var(--af-shadow-md); }
.shadow-lg { box-shadow: var(--af-shadow-lg); }
.shadow-xl { box-shadow: var(--af-shadow-xl); }

/* --- Misc -------------------------------------------------------------- */

.cursor-pointer { cursor: pointer; }
.pointer-events-none { pointer-events: none; }
.select-none { user-select: none; }
.opacity-0 { opacity: 0; }
.opacity-60 { opacity: 0.6; }
.opacity-100 { opacity: 1; }
.object-cover { object-fit: cover; }
.object-contain { object-fit: contain; }
.list-none { list-style: none; padding-left: 0; }
.list-none > li + li { margin-top: 0; }

/* Horizontal scroll rails (category strips, related products) with the
   scrollbar hidden and snap points so they feel native on touch. */
.af-rail {
	display: flex;
	gap: var(--af-space-4);
	overflow-x: auto;
	scroll-snap-type: x mandatory;
	scrollbar-width: none;
	-ms-overflow-style: none;
	padding-bottom: var(--af-space-2);
}

.af-rail::-webkit-scrollbar { display: none; }
.af-rail > * { scroll-snap-align: start; flex: 0 0 auto; }

/* Bleed a rail to the viewport edge so items are cut off rather than boxed,
   which signals scrollability without an affordance. */
.af-rail-bleed {
	margin-inline: calc(var(--af-gutter) * -1);
	padding-inline: var(--af-gutter);
}

/* --- Responsive variants ----------------------------------------------- */

@media (min-width: 768px) {
	.md\:block { display: block; }
	.md\:inline-block { display: inline-block; }
	.md\:flex { display: flex; }
	.md\:inline-flex { display: inline-flex; }
	.md\:grid { display: grid; }
	.md\:hidden { display: none; }
	.md\:flex-row { flex-direction: row; }
	.md\:flex-col { flex-direction: column; }
	.md\:items-center { align-items: center; }
	.md\:items-end { align-items: flex-end; }
	.md\:justify-between { justify-content: space-between; }
	.md\:text-left { text-align: left; }
	.md\:text-center { text-align: center; }
	.md\:grid-cols-2 { grid-template-columns: repeat(2, minmax(0, 1fr)); }
	.md\:grid-cols-3 { grid-template-columns: repeat(3, minmax(0, 1fr)); }
	.md\:grid-cols-4 { grid-template-columns: repeat(4, minmax(0, 1fr)); }
	.md\:col-span-2 { grid-column: span 2 / span 2; }
	.md\:gap-6 { gap: var(--af-space-6); }
	.md\:gap-8 { gap: var(--af-space-8); }
	.md\:gap-10 { gap: var(--af-space-10); }
	.md\:p-8 { padding: var(--af-space-8); }
	.md\:mt-0 { margin-top: 0; }
	.md\:w-auto { width: auto; }
	.md\:text-4xl { font-size: var(--af-text-4xl); }
	.md\:text-5xl { font-size: var(--af-text-5xl); }
}

@media (min-width: 1080px) {
	.lg\:block { display: block; }
	.lg\:flex { display: flex; }
	.lg\:grid { display: grid; }
	.lg\:hidden { display: none; }
	.lg\:grid-cols-2 { grid-template-columns: repeat(2, minmax(0, 1fr)); }
	.lg\:grid-cols-3 { grid-template-columns: repeat(3, minmax(0, 1fr)); }
	.lg\:grid-cols-4 { grid-template-columns: repeat(4, minmax(0, 1fr)); }
	.lg\:grid-cols-5 { grid-template-columns: repeat(5, minmax(0, 1fr)); }
	.lg\:col-span-2 { grid-column: span 2 / span 2; }
	.lg\:gap-10 { gap: var(--af-space-10); }
}

/* Touch-only and pointer-only helpers, used for the mobile dock and hover
   affordances respectively. */
@media (hover: none) {
	.no-touch { display: none !important; }
}

@media (hover: hover) {
	.touch-only { display: none !important; }
}
