/* --------------------------------------------------------------------------
   Fabric selection.

   The row on the product page reuses the master tile, so a fabric reads the
   same as a board or a leg profile. The sheet reuses the quote drawer: a
   right hand panel on desktop, a bottom sheet on phones, the same easing and
   the same close behaviour, so it feels like one piece of furniture.
   -------------------------------------------------------------------------- */

/* --------------------------------------------------------------------------
   The two action tiles: the door to the library, and the own fabric path.
   Same footprint as a swatch, with the label under the face rather than over
   it, so neither shouts louder than the fabrics they sit beside.
   -------------------------------------------------------------------------- */
/* The action tiles are taller than a swatch, so the row hangs from the top. */
.config-group--fabric .config-tiles {
	align-items: flex-start;
}

/* The row ancestor is here on purpose: product.css sizes every tile later in
   the cascade, and the action tiles need to grow past that for their label. */
.config-group--fabric .config-tile--action {
	height: auto;
}

.config-group--fabric .config-tile--action .config-tile__face {
	height: 88px;
}

.config-tile__caption {
	display: block;
	padding-top: 0.3rem;
	font-family: var(--font-heading);
	font-size: 0.75rem;
	line-height: 1.2;
	letter-spacing: 0.02em;
	font-variant-caps: all-small-caps;
	text-align: center;
	color: var(--color-ink);
}

.config-tile__caption-main {
	display: block;
	font-weight: 500;
}

.config-tile__caption-sub {
	display: block;
	margin-top: 1px;
	font-family: var(--font-mono);
	font-size: 0.7rem;
	letter-spacing: 0.06em;
	color: var(--color-muted);
}

/* The count is part of the invitation, so it carries the ink weight. COM
   stays small type, as a trade note rather than a headline. */
.config-tile--mosaic .config-tile__caption-sub {
	font-size: 0.7rem;
	color: var(--color-ink);
}

/* Four quiet quarters, nothing written across them. */
.config-tile__mosaic {
	position: absolute;
	inset: 0;
	display: grid;
	grid-template-columns: 1fr 1fr;
	grid-template-rows: 1fr 1fr;
}

.config-tile__mosaic-cell {
	background-size: cover;
	background-position: center;
	opacity: 0.88;
}

.config-tile--mosaic:hover .config-tile__mosaic-cell {
	opacity: 1;
}

/* Once a fabric is chosen this tile becomes that fabric, edge to edge, with
   its name inside the bottom edge like every other swatch. */
.config-tile__chosen {
	position: absolute;
	inset: 0;
	background-size: cover;
	background-position: center;
}

.config-tile__chosen[hidden] {
	display: none;
}

.config-tile__mosaic[hidden] {
	display: none;
}

/* Own material is words, not a colour, so it stays the quieter of the two. */
.config-tile--own .config-tile__face {
	background: var(--color-card);
	border-color: var(--color-line);
}

.config-tile--own .config-tile__own {
	display: block;
	width: 100%;
	padding: 0.25rem 0.15rem;
	font-family: var(--font-heading);
	font-size: 0.7rem;
	line-height: 1.25;
	letter-spacing: 0.01em;
	color: var(--color-muted);
	text-align: center;
	overflow-wrap: anywhere;
}

.config-tile--own:hover .config-tile__own,
.config-tile--own.is-selected .config-tile__own {
	color: var(--color-ink);
}

/* --------------------------------------------------------------------------
   Armrests, base and mechanism: three visible rows under Fabric, nothing
   collapsed. Mechanism has no pictures in the pricelist, so its chips take
   the same footprint and spacing as the tiles beside them.
   -------------------------------------------------------------------------- */
.config-group--upgrade .config-tiles {
	align-items: flex-start;
}

/* A text tile is a tile that happens to hold words. Same footprint, same
   ground, same border, same ring and badge, so a row with no picture for one
   option still reads as one set rather than as a set with a hole in it. */

.config-tile__words {
	display: block;
	padding: 0.3rem 0.25rem;
	font-family: var(--font-heading);
	font-size: 12px;
	font-weight: 500;
	line-height: 1.2;
	letter-spacing: 0.02em;
	font-variant-caps: all-small-caps;
	color: var(--color-ink);
	text-align: center;
}





/* Own fabric: one optional line, never a gate. */
.config-fabric__own-note {
	margin-top: 0.8rem;
	padding: 0.8rem 0.9rem;
	border: 1px solid var(--color-line);
	background: var(--color-card);
}

.config-fabric__own-note[hidden] {
	display: none;
}

.config-fabric__own-line {
	margin: 0 0 0.6rem;
	font-size: 0.84rem;
	color: var(--color-muted);
}

.config-fabric__own-label {
	display: block;
	margin-bottom: 0.35rem;
	font-family: var(--font-mono);
	font-size: 0.7rem;
	letter-spacing: 0.1em;
	text-transform: uppercase;
	color: var(--color-muted);
}

.config-fabric__own-input {
	width: 100%;
}

/* --------------------------------------------------------------------------
   The sheet
   -------------------------------------------------------------------------- */
.fabric-sheet {
	position: fixed;
	inset: 0;
	z-index: 210;
	pointer-events: none;
}

.fabric-sheet__scrim {
	position: absolute;
	inset: 0;
	background: rgba(38, 38, 38, 0.32);
	opacity: 0;
	transition: opacity 320ms var(--ease-out-soft);
}

.fabric-sheet__panel {
	position: absolute;
	top: 0;
	right: 0;
	bottom: 0;
	width: min(60rem, 100%);
	display: flex;
	flex-direction: column;
	background: var(--color-base);
	border-left: 1px solid var(--color-line);
	transform: translateX(100%);
	transition: transform 420ms cubic-bezier(0.16, 1, 0.3, 1);
	outline: none;
}

.fabric-sheet.is-open {
	pointer-events: auto;
}

.fabric-sheet.is-open .fabric-sheet__scrim {
	opacity: 1;
}

.fabric-sheet.is-open .fabric-sheet__panel {
	transform: translateX(0);
}

.fabric-sheet__handle {
	display: none;
}

.fabric-sheet__head {
	display: flex;
	align-items: flex-start;
	justify-content: space-between;
	gap: var(--space-3);
	padding: clamp(1.2rem, 2vw, 1.6rem) clamp(1.2rem, 2vw, 1.6rem) 1rem;
	border-bottom: 1px solid var(--color-line);
}

.fabric-sheet__title {
	margin: 0;
	font-size: clamp(1.2rem, 2vw, 1.5rem);
}

.fabric-sheet__note {
	margin: 0.3rem 0 0;
	font-size: 0.86rem;
	color: var(--color-muted);
}

.fabric-sheet__close {
	flex: 0 0 auto;
	width: 2.2rem;
	height: 2.2rem;
	border: 1px solid var(--color-line);
	background: none;
	font-size: 1.2rem;
	line-height: 1;
	color: var(--color-ink);
	cursor: pointer;
	transition: border-color 220ms var(--ease-out-soft), color 220ms var(--ease-out-soft);
}

.fabric-sheet__close:hover,
.fabric-sheet__close:focus-visible {
	border-color: var(--color-ink);
	color: var(--color-accent-deep);
}

.fabric-sheet__filters {
	display: flex;
	align-items: center;
	gap: 0.4rem;
	padding: 0.8rem clamp(1.2rem, 2vw, 1.6rem);
	border-bottom: 1px solid var(--color-line);
	overflow-x: auto;
	scrollbar-width: none;
}

.fabric-sheet__filters::-webkit-scrollbar {
	display: none;
}

.fabric-sheet__filter-sep {
	flex: 0 0 1px;
	align-self: stretch;
	margin: 0 0.3rem;
	background: var(--color-line);
}

.fabric-chip {
	flex: 0 0 auto;
	padding: 0.4rem 0.8rem;
	border: 1px solid var(--color-line);
	background: none;
	font-family: var(--font-mono);
	font-size: 0.7rem;
	letter-spacing: 0.06em;
	text-transform: uppercase;
	color: var(--color-muted);
	white-space: nowrap;
	cursor: pointer;
	transition: border-color 220ms var(--ease-out-soft), color 220ms var(--ease-out-soft), background-color 220ms var(--ease-out-soft);
}

.fabric-chip:hover,
.fabric-chip:focus-visible {
	border-color: var(--color-ink);
	color: var(--color-ink);
}

.fabric-chip.is-active {
	border-color: var(--color-ink);
	background: var(--color-ink);
	color: var(--color-warm-white);
}

/* A finger needs more than 27 px: on touch every filter chip stands
   at least 40 px tall, the row scrolling on its own as before. */
@media (hover: none), (pointer: coarse) {
	.fabric-chip {
		min-height: 40px;
		display: inline-flex;
		align-items: center;
	}
}

.fabric-sheet__body {
	flex: 1 1 auto;
	overflow-y: auto;
	overscroll-behavior: contain;
	padding: clamp(1.2rem, 2vw, 1.6rem);
}

.fabric-group + .fabric-group {
	margin-top: var(--space-4);
}

.fabric-group[hidden] {
	display: none;
}

.fabric-group__title {
	margin: 0;
	font-size: 1rem;
	font-weight: 500;
}

.fabric-group__line {
	margin: 0.2rem 0 0.9rem;
	font-size: 0.82rem;
	color: var(--color-muted);
}

.fabric-group__effect {
	color: var(--color-ink);
}

.fabric-group__grid {
	display: grid;
	grid-template-columns: repeat(auto-fill, 120px);
	gap: 0.8rem;
}

.fabric-sheet__empty {
	margin: var(--space-4) 0 0;
	color: var(--color-muted);
}

.fabric-sheet__empty[hidden] {
	display: none;
}

/* One tile. Fixed size, so lazy images cannot shift the grid. */
.fabric-tile {
	position: relative;
	display: block;
	width: 120px;
	cursor: pointer;
}

.fabric-tile[hidden] {
	display: none;
}

.fabric-tile input {
	position: absolute;
	opacity: 0;
	width: 1px;
	height: 1px;
}

.fabric-tile__face {
	position: relative;
	display: block;
	width: 120px;
	height: 120px;
	overflow: hidden;
	border: 1px solid rgba(38, 38, 38, 0.1);
	background-size: cover;
	transition: border-color 220ms var(--ease-out-soft);
}

.fabric-tile__img {
	position: absolute;
	inset: 0;
	width: 100%;
	height: 100%;
	object-fit: cover;
	display: block;
}

.fabric-tile__name {
	position: absolute;
	left: 0;
	right: 0;
	bottom: 0;
	padding: 0.24rem 0.3rem;
	background: rgba(250, 249, 246, 0.92);
	font-family: var(--font-mono);
	font-size: 0.75rem;
	line-height: 1.25;
	letter-spacing: 0.02em;
	text-transform: uppercase;
	color: var(--color-ink);
	text-align: center;
	white-space: nowrap;
	overflow: hidden;
	text-overflow: ellipsis;
}

.fabric-tile--dark .fabric-tile__name {
	background: rgba(38, 38, 38, 0.78);
	color: var(--color-warm-white);
}

.fabric-tile:hover .fabric-tile__face,
.fabric-tile input:focus-visible + .fabric-tile__face {
	border-color: var(--color-ink);
}

/* Chosen: the same ink ring and check badge as every other control. */
.fabric-tile.is-selected .fabric-tile__face {
	outline: 2px solid var(--color-ink);
	outline-offset: 2px;
	border-color: rgba(38, 38, 38, 0.16);
}

.fabric-tile.is-selected::after {
	content: "";
	position: absolute;
	z-index: 2;
	top: -7px;
	right: -7px;
	width: 16px;
	height: 16px;
	border-radius: 50%;
	background-color: var(--color-ink);
	background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 12 12'%3E%3Cpath d='M2.5 6.4 4.7 8.6 9.5 3.8' fill='none' stroke='%23faf9f6' stroke-width='1.7' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E");
	background-repeat: no-repeat;
	background-position: center;
	background-size: 12px 12px;
	box-shadow: 0 0 0 2px var(--color-base);
	pointer-events: none;
}

.fabric-group__grid:hover .fabric-tile:not(.is-selected):not(:hover) {
	opacity: 0.85;
}

/* The weave, close up, on hover or long press. */
.fabric-tile__preview {
	position: absolute;
	left: 50%;
	bottom: calc(100% + 8px);
	z-index: 30;
	width: 240px;
	transform: translate(-50%, 4px);
	padding: 0.5rem;
	border: 1px solid var(--color-line);
	background: var(--color-base);
	box-shadow: 0 18px 40px rgba(38, 38, 38, 0.14);
	opacity: 0;
	visibility: hidden;
	transition: opacity 220ms var(--ease-out-soft), transform 220ms var(--ease-out-soft), visibility 0s linear 220ms;
	pointer-events: none;
}

.fabric-tile.is-previewing .fabric-tile__preview {
	opacity: 1;
	visibility: visible;
	transform: translate(-50%, 0);
	transition-delay: 0s;
}

.fabric-tile__preview img {
	display: block;
	width: 100%;
	height: auto;
	aspect-ratio: 1;
	object-fit: cover;
}

.fabric-tile__preview-name {
	display: block;
	margin-top: 0.45rem;
	font-size: 0.8rem;
	color: var(--color-ink);
}

.fabric-tile__preview-spec {
	display: block;
	margin-top: 0.15rem;
	font-family: var(--font-mono);
	font-size: 0.7rem;
	letter-spacing: 0.04em;
	color: var(--color-muted);
}

.fabric-sheet__foot {
	display: flex;
	align-items: center;
	gap: var(--space-3);
	padding: clamp(0.9rem, 1.6vw, 1.2rem) clamp(1.2rem, 2vw, 1.6rem) calc(clamp(0.9rem, 1.6vw, 1.2rem) + env(safe-area-inset-bottom));
	border-top: 1px solid var(--color-line);
	background: var(--color-base);
}

.fabric-sheet__chosen {
	flex: 1 1 auto;
	min-width: 0;
	display: flex;
	flex-direction: column;
	gap: 0.1rem;
}

.fabric-sheet__chosen-label,
.fabric-sheet__price-label {
	font-family: var(--font-mono);
	font-size: 0.7rem;
	letter-spacing: 0.1em;
	text-transform: uppercase;
	color: var(--color-muted);
}

.fabric-sheet__chosen-name {
	font-size: 0.92rem;
	color: var(--color-ink);
	overflow: hidden;
	text-overflow: ellipsis;
	white-space: nowrap;
}

.fabric-sheet__price {
	flex: 0 0 auto;
	display: flex;
	flex-direction: column;
	gap: 0.1rem;
	text-align: right;
}

.fabric-sheet__price-value {
	font-family: var(--font-heading);
	font-size: 1.05rem;
	font-weight: 500;
	color: var(--color-ink);
	white-space: nowrap;
}

.fabric-sheet__use {
	flex: 0 0 auto;
}

@media (max-width: 720px) {
	.config-group--fabric .config-tile--action .config-tile__face {
		height: 76px;
	}

	.fabric-sheet__panel {
		top: auto;
		left: 0;
		right: 0;
		bottom: 0;
		width: 100%;
		height: 92vh;
		border-left: 0;
		border-top: 1px solid var(--color-line);
		transform: translateY(100%);
	}

	.fabric-sheet.is-open .fabric-sheet__panel {
		transform: translateY(0);
	}

	.fabric-sheet__handle {
		display: block;
		width: 2.4rem;
		height: 3px;
		margin: 0.6rem auto 0;
		border-radius: 999px;
		background: var(--color-line);
	}

	.fabric-group__grid {
		grid-template-columns: repeat(auto-fill, 96px);
		gap: 0.6rem;
	}

	.fabric-tile,
	.fabric-tile__face {
		width: 96px;
	}

	.fabric-tile__face {
		height: 96px;
	}

	.fabric-tile__preview {
		width: 200px;
	}

	.fabric-sheet__foot {
		flex-wrap: wrap;
	}

	.fabric-sheet__use {
		flex: 1 1 100%;
		justify-content: center;
	}
}

@media (prefers-reduced-motion: reduce) {
	.fabric-sheet__panel,
	.fabric-sheet__scrim,
	.fabric-tile__preview {
		transition-duration: 1ms;
	}
}

/* --------------------------------------------------------------------------
   The four rows as one set.

   Every tile on a chair shares the same interior tone, so a picture tile, a
   words tile and a swatch all sit on the same ground. The price line lives
   under the tile rather than over the picture, and the magnifier moves off
   the subject to the corner of the caption strip.
   -------------------------------------------------------------------------- */
.config-group--fabric .config-tile__face,
.config-group--upgrade .config-tile__face {
	background-color: var(--color-card);
}

/* A chosen fabric or a mosaic still covers its own face edge to edge. */
.config-group--fabric .config-tile__a,
.config-group--fabric .config-tile__chosen,
.config-group--fabric .config-tile__mosaic {
	background-color: transparent;
}

/* The group ancestor is here on purpose: product.css fixes every tile at a
   square later in the cascade, and a captioned tile has to grow past that or
   its price line lands on the row below. */
.config-group--fabric .config-tile--captioned,
.config-group--upgrade .config-tile--captioned {
	height: auto;
}

.config-group--fabric .config-tile--captioned .config-tile__face,
.config-group--upgrade .config-tile--captioned .config-tile__face {
	height: 88px;
}

.config-tile__caption-price {
	display: block;
	padding-top: 0.28rem;
	font-family: var(--font-mono);
	font-size: 12px;
	line-height: 1.2;
	letter-spacing: normal;
	font-variant-caps: normal;
	color: var(--color-muted);
	text-align: center;
	white-space: nowrap;
}

.config-tile.is-selected .config-tile__caption-price {
	color: var(--color-ink);
}

/* One plain line under a tile, saying what the thing is. It is read rather
   than hovered, because it exists to answer the question people telephone
   about, and a tooltip answers nobody who has not already guessed. */
.config-tile__note {
	display: block;
	padding-top: 0.24rem;
	font-size: 0.72rem;
	line-height: 1.35;
	letter-spacing: 0;
	font-variant-caps: normal;
	text-align: center;
	text-wrap: pretty;
	color: var(--color-muted);
}

.config-tile.is-selected .config-tile__note {
	color: var(--color-ink);
}

/* A tile with words under it needs the room for them, and the row needs to
   stop squeezing four of them into a line. */
.config-tiles:has(.config-tile__note) .config-tile {
	width: clamp(9rem, 30%, 12rem);
}

/* The glyph sat on top of the subject. It now hangs off the top left corner
   clear of the picture. */
.config-group--fabric .config-tile__zoom,
.config-group--upgrade .config-tile__zoom {
	top: -6px;
	left: -6px;
	width: 15px;
	height: 15px;
	border-radius: 50%;
	background: var(--color-base);
	box-shadow: 0 0 0 1px var(--color-line);
	color: var(--color-muted);
}

.config-group--fabric .config-tile:hover .config-tile__zoom,
.config-group--upgrade .config-tile:hover .config-tile__zoom {
	color: var(--color-ink);
}

@media (max-width: 720px) {
	.config-group--fabric .config-tile--captioned .config-tile__face,
	.config-group--upgrade .config-tile--captioned .config-tile__face {
		height: 76px;
	}
}

/* These pictures come out of the pricelist at about 145 DPI, so the tile
   scales them down rather than up and nothing is stretched. */
.config-group--upgrade .config-tile__a {
	background-size: contain;
	background-repeat: no-repeat;
	background-position: center;
	image-rendering: auto;
}

/* --------------------------------------------------------------------------
   The quiet line under an option tile: the base diameter the print states, or
   whether an armrest adjusts. It sits below the price in the same caption
   block, a step down in weight so the money still leads.
   -------------------------------------------------------------------------- */
.config-tile__caption-note {
	display: block;
	margin-top: 1px;
	font-family: var(--font-mono);
	font-size: 8px;
	line-height: 1.2;
	letter-spacing: 0.04em;
	color: var(--color-muted);
	text-align: center;
	white-space: nowrap;
}

.config-tile.is-selected .config-tile__caption-note {
	color: var(--color-ink);
}
