/* Kavita Booking — front-end wizard. Light theme with orange accent. */

.kavita-wrap {
	--zy-bg: #ffffff;
	--zy-card: #ffffff;
	--zy-line: #e5e7eb;
	--zy-text: #1f2937;
	--zy-muted: #6b7280;
	--zy-accent: #ea580c;
	--zy-accent-hover: #9a3412;
	/* CONTRAST. #ea580c is 3.6:1 on white — it fails WCAG AA (4.5:1) both as
	   text and as a button background carrying white text, so before 0.34.0
	   every price, every active step and every primary button was below the
	   legal threshold in the markets this is sold into.
	   #c2410c is 5.2:1 and reads as the same orange. The bright shade is kept
	   for hovers and large decorative fills, where the rule is 3:1. */
	--zy-accent-text: #c2410c;
	/* Words sitting ON the accent, and the wash behind a chosen slot. Both
	   were hard-coded until the accent became something a practice picks:
	   white text is unreadable on a yellow brand colour, and an orange
	   selection tint under a blue accent is exactly the detail a preset
	   gallery leaves behind. Kavita_Appearance derives both. */
	--zy-accent-fg: #ffffff;
	/* TEXT AND BUTTONS ARE NOT THE SAME RULE. Text needs 4.5:1 against the
	   page; a button is a block, and 3:1 is the bar for it -- so a pale brand
	   colour keeps more of itself as a button ground than it could as a word,
	   and gets dark ink instead of being darkened into something else. */
	--zy-accent-btn: #c2410c;
	--zy-accent-soft: rgba(232,89,12,.12);
	--zy-focus: #1d4ed8;
	max-width: 1240px;
	margin: 0 auto;
	padding: 24px 16px 48px;
	color: var(--zy-text);
	background: var(--zy-bg);
	/* System stack: no webfont is fetched, so no visitor IP reaches a third
	   party and nothing blocks the first paint of the booking form. */
	font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
	box-sizing: border-box;
}
.kavita-wrap * { box-sizing: border-box; }

.kavita-title { text-align: center; font-size: 24px; font-weight: 500; margin: 8px 0 24px; }
.kavita-title + .kavita-intro { margin-top: -14px; }
.kavita-intro { text-align: center; color: var(--zy-muted); font-size: 19px; line-height: 1.5; margin: 0 auto 26px; max-width: 60ch; }

/* Stepper */
.kavita-steps {
	display: flex; gap: 8px; flex-wrap: wrap;
	border: 1px solid var(--zy-line); border-radius: 10px;
	padding: 14px 16px; margin-bottom: 20px;
}
.kavita-step {
	display: flex; align-items: center; gap: 8px;
	color: var(--zy-muted); font-weight: 500; cursor: pointer;
	padding: 6px 10px; border-radius: 8px; white-space: nowrap;
}
.kavita-step .zy-ico {
	display: inline-flex; width: 30px; height: 30px; align-items: center; justify-content: center;
	background: #f3f4f6; border-radius: 7px; color: var(--zy-muted);
}
.kavita-step.is-active { color: var(--zy-accent); }
.kavita-step.is-active .zy-ico { background: var(--zy-accent); color: var(--zy-accent-fg); }

/* Card */
.zy-card { border: 1px solid var(--zy-line); border-radius: 12px; padding: 22px 24px; }
.zy-h { font-size: 16px; font-weight: 500; margin: 4px 0 14px; }
.zy-muted { color: var(--zy-muted); }
.zy-strong { font-weight: 500; }
.zy-price { color: var(--zy-accent); font-weight: 500; }
.zy-error { color: #dc2626; margin: 8px 0; min-height: 18px; }

/* Category chips */
.zy-chips { display: flex; gap: 10px; flex-wrap: wrap; margin-bottom: 20px; }
.zy-chip {
	background: var(--zy-card); color: var(--zy-muted); border: 1px solid var(--zy-line);
	border-radius: 8px; padding: 8px 16px; font-weight: 500; cursor: pointer; letter-spacing: .3px;
}
.zy-chip.is-on { color: var(--zy-text); border-color: var(--zy-accent); position: relative; }
.zy-chip.is-on::after {
	content: "✓"; margin-left: 8px; background: var(--zy-accent); color: var(--zy-accent-fg);
	border-radius: 50%; padding: 0 5px; font-size: 11px;
}

/* Services */
.zy-services { display: grid; grid-template-columns: 1fr 1fr; gap: 20px; }
.zy-service {
	display: flex; align-items: center; gap: 18px;
	border: 1px solid var(--zy-line); border-radius: 10px; padding: 22px 24px; cursor: pointer;
	transition: border-color .15s, transform .05s;
}
.zy-service:hover { border-color: var(--zy-accent); }
.zy-service:active { transform: scale(.998); }
.zy-service-ico { font-size: 34px; width: 40px; height: 40px; color: var(--zy-muted); }
.zy-service-name { font-weight: 500; margin-bottom: 6px; }
.zy-service-format { display: block; color: var(--zy-muted); font-size: 12px; letter-spacing: .04em; text-transform: uppercase; margin: -2px 0 6px; }
.zy-service-about { display: block; color: var(--zy-muted); font-size: 14px; line-height: 1.45; margin-bottom: 8px; }
.zy-service-wrap { display: flex; flex-direction: column; }
.zy-service-wrap.has-more .zy-service { border-radius: 10px 10px 0 0; }
.zy-service--soon { cursor: default; opacity: .62; }
.zy-service--soon:hover { border-color: var(--zy-line); }
.zy-soon { display: inline-block; vertical-align: middle; margin-left: 8px; padding: 2px 7px; border-radius: 99px; font-size: 10.5px; font-weight: 600; letter-spacing: .04em; text-transform: uppercase; color: #8a6d0a; background: rgba(201,162,39,.16); border: 1px solid rgba(201,162,39,.4); }
.zy-notify { margin: 8px 0 0; } .zy-notify a { color: var(--zy-accent-text); font-weight: 500; text-decoration: none; }
.zy-service-more { border: 1px solid var(--zy-line); border-top: 0; border-radius: 0 0 10px 10px; padding: 10px 24px 12px; font-size: 14px; line-height: 1.5; color: var(--zy-muted); background: var(--zy-card); }
.zy-service-more summary { cursor: pointer; color: var(--zy-text); font-size: 13px; }
.zy-service-more p { margin: 8px 0 0; }
.zy-chips + .zy-chips--fmt { margin-top: -10px; }
.zy-chips-l { flex: 0 0 auto; align-self: center; min-width: 76px; color: var(--zy-muted); font-size: 12px; letter-spacing: .06em; text-transform: uppercase; }
.zy-service-price { color: var(--zy-muted); font-size: 14px; }
.zy-service-price .zy-price {
	background: var(--zy-accent); color: var(--zy-accent-fg); padding: 3px 9px; border-radius: 6px; margin-left: 4px;
}

/* Date & time */
.zy-dt { display: grid; grid-template-columns: 1fr 1fr; gap: 24px; }
.zy-cal-head { display: flex; align-items: center; justify-content: space-between; padding: 10px 6px; font-weight: 500; }
.zy-cal-nav { background: none; border: none; color: var(--zy-muted); font-size: 22px; cursor: pointer; padding: 0 8px; }
.zy-cal-grid { display: grid; grid-template-columns: repeat(7, 1fr); }
.zy-cal-dow { color: var(--zy-muted); font-size: 13px; padding: 6px 0; text-align: center; }
.zy-cal-cell {
	aspect-ratio: 1 / 1; display: flex; align-items: center; justify-content: center;
	border: 1px solid var(--zy-line); font-size: 14px; cursor: pointer;
}
.zy-cal-cell.is-empty { border: none; cursor: default; }
.zy-cal-cell.is-past { color: #c0c4cc; cursor: not-allowed; }
.zy-cal-cell.is-today { font-weight: 500; color: var(--zy-text); }
.zy-cal-cell.is-sel { background: var(--zy-accent); color: var(--zy-accent-fg); font-weight: 500; }
.zy-cal-cell:not(.is-empty):not(.is-past):not(.is-blocked):not(.is-sel):hover { background: #f3f4f6; }

.zy-period { font-weight: 500; margin: 16px 0 8px; }
.zy-slot-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 10px; }
.zy-slot {
	border: 1px solid var(--zy-line); background: var(--zy-card); color: var(--zy-text);
	border-radius: 8px; padding: 12px; cursor: pointer; text-align: left; font-size: 14px;
}
.zy-slot:hover { border-color: var(--zy-accent); }
.zy-slot.is-on { border-color: var(--zy-accent); background: var(--zy-accent-soft); }

/* Cart */
.zy-cart-head { display: flex; align-items: center; justify-content: space-between; margin-bottom: 12px; }
.zy-badge { background: #f3f4f6; color: #374151; font-size: 12px; padding: 3px 10px; border-radius: 6px; margin-left: 8px; font-weight: 600; }
/*
 * NO COLUMN COUNT, BECAUSE THE MARKUP AND THE CSS KEPT DISAGREEING ABOUT ONE.
 *
 * This was a six-column grid, and three different rows were put through it: a
 * booked item emits up to EIGHT children (icon, name, date, time, provider,
 * seats, price, remove), while an extra or a package emits THREE. The booked
 * row therefore pushed its remove button onto a second line, and -- far worse
 * -- an extra's name landed in the 40px icon column, where "Six-session
 * recovery plan" wrapped to one word per line and a package row grew to the
 * height of a paragraph.
 *
 * A flex row has no count to get wrong. The name takes what is left with
 * min-width:0 so it can actually shrink, and price and remove are pushed to the
 * far edge by a single auto margin, so a row of three and a row of eight both
 * come out aligned.
 */
.zy-cart-row {
	display: flex; align-items: center; flex-wrap: wrap; gap: 6px 12px;
	padding: 16px 0; border-bottom: 1px solid var(--zy-line);
}
.zy-service-ico, .zy-cart-del, .zy-cart-seats { flex: 0 0 auto; }
/* min-width:0 is the whole fix: without it a flex item refuses to shrink below
   its longest word, which is how a name ends up one word per line. */
.zy-cart-name { flex: 1 1 180px; min-width: 0; font-weight: 500; }
.zy-cart-date, .zy-cart-time, .zy-cart-staff { flex: 0 1 auto; min-width: 0; }
/* Everything from here sits hard right, whatever came before it. */
.zy-cart-price { margin-inline-start: auto; }
.zy-cart-row select, .zy-cart-row .zy-btn-ghost { flex: 0 0 auto; }

/*
 * OPTIONAL THINGS, SET LIKE OPTIONAL THINGS.
 *
 * Extras and packages were rendered in the same 16px rows as the appointment
 * being bought, each with its description on a second line -- so three extras
 * and three packages took several times the height of the booking itself and
 * pushed the Next button off the screen. They are offers, not the order.
 *
 * Denser, quieter, and one line each: the description trails the name rather
 * than sitting under it, and wraps with it when there is no room. The control
 * keeps a real target size, because a thumb does not get smaller just because
 * the row did.
 */
.zy-cart-row--offer {
	padding: 8px 0;
	gap: 4px 10px;
	font-size: 13.5px;
	border-bottom-color: color-mix(in srgb, var(--zy-line) 60%, transparent);
}
.zy-cart-row--offer:last-child { border-bottom: 0; }
.zy-cart-row--offer .zy-cart-name { flex: 1 1 150px; font-weight: 500; line-height: 1.35; }
/* Inline, so it reads as a continuation of the name and costs no extra line. */
.zy-cart-sub { color: var(--zy-muted); font-size: 12px; font-weight: 400; }
.zy-cart-about { display: block; color: var(--zy-muted); font-size: 13px; font-weight: 400; line-height: 1.4; margin-top: 4px; }
.zy-cart-more { font-size: 13px; font-weight: 400; color: var(--zy-muted); line-height: 1.45; margin-top: 4px; }
.zy-cart-more summary { cursor: pointer; color: var(--zy-text); font-size: 12px; }
.zy-cart-more p { margin: 6px 0 0; }
.zy-cart-row--offer .zy-cart-price { font-size: 13.5px; white-space: nowrap; }
.zy-cart-row--offer .zy-btn-ghost { padding: 6px 10px; }
/*
 * select.zy-qty, NOT .zy-qty. .zy-input carries width:100% and is defined
 * further down this file, so a bare class of equal specificity lost and the
 * quantity dropdown stretched the whole width of the row -- which is what made
 * an "extra" occupy two lines and look broken. An element+class selector wins
 * on specificity rather than on source order, so this cannot be undone by
 * moving code around later.
 */
select.zy-qty { width: 62px; padding: 6px 8px; min-height: 34px; }

/* ---------------- The cart step, in two columns ---------------- */
/*
 * Left is the order, right is the offers. Stacked, three extras and three
 * packages pushed the total and the Next button below the fold on a laptop, so
 * the two things a person came to look at were the two they could not see.
 *
 * This wrapper also owns the spacing between the step's blocks. Nothing else in
 * this stylesheet gives a .zy-card a margin, so a step that wants its cards
 * apart has to say so itself.
 */
.zy-stack { display: grid; gap: 16px; }

.zy-cart-cols {
	display: grid;
	/* minmax(0,…) on both tracks, or a long service name refuses to shrink and
	   pushes the right column off the edge. */
	grid-template-columns: minmax(0, 1.6fr) minmax(0, 1fr);
	gap: 16px;
	/* Not stretch: the offers column is shorter than the order and should not
	   grow a tall empty box to match it. */
	align-items: start;
}
.zy-cart-main, .zy-cart-side { display: grid; gap: 16px; min-width: 0; }

/* Figures line up down the column, which is most of what makes a bill read as
   designed rather than typed. */
.zy-cart-price, .zy-price, .zy-cart-total { font-variant-numeric: tabular-nums; }

@media (max-width: 900px) {
	/* One column, order first -- on a phone the offers belong after the thing
	   being bought, which is the same priority the columns express side by side. */
	.zy-cart-cols { grid-template-columns: 1fr; }
}

/* And the box around them. Two offers each carrying a full card's padding, a
   16px heading and a paragraph of explanation put more chrome on the page than
   the booking they are offered against. */
.zy-card--offers { padding: 14px 16px; }
.zy-card--offers .zy-h { font-size: 14px; margin: 0 0 2px; }
.zy-card--offers .zy-note { font-size: 12px; margin: 0 0 8px; }
.zy-cart-date, .zy-cart-time { color: var(--zy-muted); }
.zy-cart-price { text-align: right; }
.zy-cart-del { background: none; border: none; color: var(--zy-muted); font-size: 20px; cursor: pointer; }
.zy-cart-del:hover { color: #dc2626; }
.zy-cart-total { display: flex; justify-content: space-between; align-items: center; padding-top: 16px; font-weight: 500; font-size: 16px; }

/* Forms */
.zy-label { display: block; font-weight: 500; margin: 16px 0 8px; font-size: 14px; }
.zy-req { color: #dc2626; }
.zy-input {
	width: 100%; background: var(--zy-card); border: 1px solid var(--zy-line); border-radius: 8px;
	padding: 12px 14px; color: var(--zy-text); font-size: 14px;
}
.zy-input:focus { outline: none; border-color: var(--zy-accent); }
/* A THEME'S SELECT IS NOT OURS. Flatsome, Astra and friends give every
   <select> a fixed em height and a matching line-height; add this file's
   padding and the text sits below the box and is clipped -- "Any day" shown
   as its top half. So the box is sized here, the native arrow is dropped and
   drawn back, and the theme's height is overruled by name. */
.kavita-wrap select.zy-input {
	height: auto; min-height: 0; line-height: 1.3; margin: 0;
	-webkit-appearance: none; appearance: none; padding-right: 36px;
	background-image: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='12' height='8' viewBox='0 0 12 8'><path d='M1 1l5 5 5-5' fill='none' stroke='%23888' stroke-width='1.8'/></svg>");
	background-repeat: no-repeat; background-position: right 14px center; background-size: 12px 8px;
}
.kavita-wrap .iti { width: 100%; display: block; }
.kavita-wrap .iti .zy-input { width: 100%; }
textarea.zy-input { resize: vertical; }

/* Summary */
.zy-summary { max-width: 760px; margin: 0 auto; }
.zy-sum-cust { text-align: center; margin: 16px 0; }
.zy-sum-line { display: flex; gap: 40px; justify-content: center; padding: 12px 0; }
.zy-sum-line > div { min-width: 180px; }

.zy-success { text-align: center; padding: 48px 24px; }
.zy-success .zy-thanks { font-size: 15px; margin: 0 0 16px; color: var(--zy-text); }
.zy-success-ico { font-size: 56px; width: 56px; height: 56px; color: #1a7f37; margin: 0 auto 8px; }

/* Nav / buttons */
.zy-nav { display: flex; justify-content: space-between; align-items: center; margin-top: 24px; padding-top: 20px; border-top: 1px solid var(--zy-line); }
.zy-btn {
	background: var(--zy-accent); color: var(--zy-accent-fg); border: none; border-radius: 8px;
	padding: 12px 22px; font-weight: 500; cursor: pointer;
}
.zy-btn:hover { background: var(--zy-accent-hover); }
.zy-btn:disabled { opacity: .6; cursor: default; }
.zy-btn-ghost { background: none; border: none; color: var(--zy-text); font-weight: 500; cursor: pointer; padding: 12px 8px; }
.zy-btn-ghost:hover { color: var(--zy-accent); }

.kavita-loading { color: var(--zy-muted); padding: 40px; text-align: center; }

@media (max-width: 820px) {
	.zy-services, .zy-dt, .zy-slot-grid { grid-template-columns: 1fr; }
	.zy-cart-date, .zy-cart-time { display: none; }
	.zy-sum-line { flex-direction: column; gap: 8px; }
}

/* --- Mobile pass (v0.4.76) --- */
@media (max-width: 640px) {
	.kavita-wrap { padding-left: 0; padding-right: 0; }
	.kavita-title { font-size: 20px; }
	.kavita-intro { font-size: 16px; }

	/* Stepper: one horizontal scrollable strip instead of a tall vertical stack. */
	.kavita-steps {
		flex-wrap: nowrap; overflow-x: auto; gap: 4px;
		padding: 10px; -webkit-overflow-scrolling: touch;
		scrollbar-width: none;
	}
	.kavita-steps::-webkit-scrollbar { display: none; }
	.kavita-step { padding: 6px 8px; font-size: 13px; flex: 0 0 auto; }
	.kavita-step .zy-ico { width: 26px; height: 26px; }

	/* Cards: less inner padding so content isn't squeezed. */
	.zy-card { padding: 16px 14px; }

	/* Calendar: collapse double borders into one clean grid (kills the stray
	   right-edge vertical line) and give cells room to breathe. The DOW header
	   and day cells are separate grids, so frame only the day grid. */
	.zy-cal-grid:not(.zy-cal-dow) {
		border-top: 1px solid var(--zy-line);
		border-left: 1px solid var(--zy-line);
		border-radius: 10px; overflow: hidden;
	}
	.zy-cal-grid:not(.zy-cal-dow) .zy-cal-cell {
		border: none;
		border-right: 1px solid var(--zy-line);
		border-bottom: 1px solid var(--zy-line);
		font-size: 15px; aspect-ratio: auto; min-height: 44px;
	}
	.zy-cal-note { font-size: 12px; padding: 0 4px; }
}

/* --- v0.3.0: timezone labels, tax rows, success links, my-bookings --- */
.zy-tznote{margin:0 0 12px;font-size:12px}
.zy-slot{display:flex;flex-direction:column;align-items:center;gap:2px}
.zy-slot-local{font-size:10px;opacity:.7;font-weight:400}
.zy-sum-row{display:flex;justify-content:space-between;padding:6px 0;font-size:14px}
.zy-success-links{margin-top:16px;display:flex;gap:10px;flex-wrap:wrap;justify-content:center}
.zy-btn-ghost{background:none;border:1px solid var(--zy-line,#3a3a3a);color:inherit;border-radius:8px;padding:9px 14px;text-decoration:none;display:inline-block;font-size:13px;cursor:pointer}
.zy-input{width:100%;background:var(--zy-card);border:1px solid var(--zy-line);border-radius:8px;color:var(--zy-text);padding:11px 13px;font-size:14px}

/* v0.4.7: blocked / holiday dates in the wizard calendar */
/* Unavailable dates: plain grey, no strike-through (most of the calendar is
   simply "not open yet", so a slash would read as noise/damage). */
.zy-cal-cell.is-blocked { color: #c0c4cc; cursor: not-allowed; position: relative; }
/* Exceptional closures inside the bookable range (holiday / weekly off) get a
   small dot so they're distinguishable from "not open yet". */
.zy-cal-cell.is-closed { color: #9a3412; opacity: .75; }
.zy-cal-cell.is-closed::after {
	content: ""; position: absolute; left: 50%; bottom: 6px; width: 4px; height: 4px;
	margin-left: -2px; border-radius: 50%; background: var(--zy-accent-text);
}
.zy-cal-note { margin: 10px 2px 0; font-size: 12.5px; color: var(--zy-muted); line-height: 1.5; }
.zy-cal-note strong { color: var(--zy-text); font-weight: 500; }

/* v0.5.0: provider (staff) step */
/* The stepper chip is hidden rather than removed, so a clinic that adds a
   second provider gets the step without a template change. */
.kavita-step.is-hidden { display: none; }

.zy-staff-list { display: grid; grid-template-columns: repeat(auto-fill, minmax(240px, 1fr)); gap: 12px; }
.zy-staff {
	display: flex; align-items: center; gap: 12px; cursor: pointer;
	border: 1px solid var(--zy-line); border-radius: 10px; padding: 14px;
	background: var(--zy-card); transition: border-color .15s, box-shadow .15s;
}
.zy-staff:hover { border-color: var(--zy-accent, #ea580c); }
.zy-staff.is-on { border-color: var(--zy-accent, #ea580c); box-shadow: 0 0 0 1px var(--zy-accent, #ea580c) inset; }
.zy-staff-ico { font-size: 34px; width: 34px; height: 34px; color: var(--zy-accent, #ea580c); flex: 0 0 auto; }
.zy-staff-photo { width: 44px; height: 44px; border-radius: 50%; object-fit: cover; flex: 0 0 auto; }
.zy-staff-body { min-width: 0; }
.zy-staff-name { font-weight: 500; }
.zy-staff-body .zy-muted { font-size: 12.5px; line-height: 1.4; }
.zy-cart-staff { font-size: 12.5px; color: var(--zy-muted); }

@media (max-width: 640px) {
	.zy-staff-list { grid-template-columns: 1fr; }
	.zy-staff { padding: 12px; }
}
.zy-provider { margin: 4px 0 2px; font-size: 15px; }
.zy-staff-price { font-weight: 500; margin-top: 2px; }

/* ---- Repeating course (cart step) ------------------------------------- */
/* Framed as an offer rather than a required choice: the default is a single
   appointment, and the block only appears when the cart holds one item. */
.zy-course {
	border: 1px solid var(--zy-line); border-radius: 10px;
	padding: 14px; margin: 14px 0; background: #fafafa;
}
.zy-course-head { font-weight: 500; margin-bottom: 8px; }
.zy-course-controls { display: flex; gap: 8px; flex-wrap: wrap; }
.zy-course-controls select {
	padding: 8px 10px; border: 1px solid var(--zy-line); border-radius: 8px;
	background: var(--zy-card); font: inherit;
}
.zy-course-out { margin-top: 10px; }
.zy-course-list { list-style: none; margin: 6px 0 0; padding: 0; }
.zy-course-list li { padding: 4px 0; font-size: 13.5px; border-bottom: 1px dashed var(--zy-line); }
.zy-course-list li:last-child { border-bottom: 0; }
/* Skipped dates stay visible. Hiding them would make the course look like it
   simply ran to a different date, with no way to see the clinic was closed. */
.zy-course-skip { color: var(--zy-muted); }
.zy-course-ok::before { content: "\2713"; color: #1a7f37; margin-right: 6px; }
.zy-course-skip::before { content: "\2013"; margin-right: 6px; }

@media (max-width: 640px) {
	.zy-course-controls { flex-direction: column; }
	.zy-course-controls select { width: 100%; }
}

/* ---- Consent line (details step) --------------------------------------- */
/* Rendered only when the clinic has written one, so it never appears as an
   empty legal-looking tickbox nobody chose the wording for. */
.zy-consent {
	display: flex; align-items: flex-start; gap: 9px;
	margin: 12px 0 4px; font-size: 13.5px; line-height: 1.45;
	color: var(--zy-muted);
}
.zy-consent input { margin-top: 2px; flex: 0 0 auto; }
.zy-consent .zy-req { color: #b32d2e; }

/* ---- Deposit / pay-in-full choice (summary step) ----------------------- */
/* Only rendered when a deposit applies, so a clinic that takes full payment
   never shows an option with one answer. */
.zy-paymode { display: grid; gap: 10px; margin: 14px 0 4px; }
.zy-paymode-opt {
	display: flex; gap: 10px; align-items: flex-start; cursor: pointer;
	border: 1px solid var(--zy-line); border-radius: 10px; padding: 12px 14px;
	background: var(--zy-card); transition: border-color .15s, box-shadow .15s;
}
.zy-paymode-opt:hover { border-color: var(--zy-accent, #ea580c); }
.zy-paymode-opt input { margin-top: 3px; flex: 0 0 auto; }
.zy-paymode-opt:has(input:checked) {
	border-color: var(--zy-accent, #ea580c);
	box-shadow: 0 0 0 1px var(--zy-accent, #ea580c) inset;
}
.zy-paymode-opt .zy-muted { font-size: 12.5px; }

/* ---- Coupon (summary step) --------------------------------------------- */
/* Only rendered when a live coupon exists, and it disappears once applied —
   the discount then lives in the totals, where the money is. */
.zy-coupon { display: flex; gap: 8px; flex-wrap: wrap; margin: 14px 0 4px; }
.zy-coupon .zy-input { flex: 1 1 180px; text-transform: uppercase; }
.zy-coupon-err { flex: 1 1 100%; color: #b32d2e; font-size: 13px; }
.zy-sum-disc { color: #1a7f37; font-weight: 500; }
.zy-coupon-x {
	background: none; border: 0; cursor: pointer; color: var(--zy-muted);
	font-size: 16px; line-height: 1; padding: 0 2px; margin-left: 4px;
}
.zy-coupon-x:hover { color: #b32d2e; }

/* ---- Intake questions (details step) ----------------------------------- */
/* On Details rather than a seventh step: it is more of what the customer is
   already doing, and a step that only some services need would make the
   stepper lie. */
.zy-intake { margin-top: 14px; padding-top: 12px; border-top: 1px dashed var(--zy-line); }
.zy-intake-h { font-weight: 500; margin-bottom: 8px; }
.zy-help { font-size: 12.5px; margin: -2px 0 6px; }
.zy-req { color: #b32d2e; }

/* ======================================================================
   v0.34.0 — ACCESSIBILITY PASS, and the four new customer-facing steps.
   ====================================================================== */

/* ---- Focus ------------------------------------------------------------
   There was no focus style at all: a keyboard user could not see where they
   were. :focus-visible rather than :focus so a mouse click does not leave a
   ring behind, which is the reason focus outlines get removed in the first
   place. A separate blue is used rather than the brand orange because the
   ring must be visible ON an orange button too. */
.kavita-wrap :focus-visible {
	outline: 3px solid var(--zy-focus);
	outline-offset: 2px;
	border-radius: 4px;
}
/* Windows High Contrast Mode paints its own colours and drops backgrounds,
   so selected states signalled only by background disappear. */
@media (forced-colors: active) {
	.kavita-wrap :focus-visible { outline: 3px solid Highlight; }
	.zy-slot.is-on, .zy-staff.is-on, .zy-chip.is-on, .zy-cal-cell.is-sel {
		outline: 2px solid Highlight;
	}
}

/* ---- Buttons that used to be divs -------------------------------------
   These carry the layout the divs had, so nothing moves; they simply became
   focusable and announceable. */
.kavita-step, .zy-service, .zy-staff, .zy-cal-cell {
	font: inherit; text-align: inherit; color: inherit;
	background: none; border: none; margin: 0;
}
.kavita-step { background: none; }
.zy-service, .zy-staff { width: 100%; }
.zy-service { border: 1px solid var(--zy-line); background: var(--zy-card); }
.zy-cal-cell { border: 1px solid var(--zy-line); padding: 0; }
.zy-service-body, .zy-staff-body { display: block; text-align: left; }
.zy-service-name, .zy-service-price, .zy-staff-name, .zy-staff-price { display: block; }
.zy-staff-body .zy-muted { display: block; }

/* A step you cannot reach yet stays focusable — so it can be discovered —
   but must not look like a live control. */
.kavita-step.is-locked { opacity: .55; cursor: default; }

/* ---- Contrast repairs -------------------------------------------------- */
.zy-price, .kavita-step.is-active { color: var(--zy-accent-text); }
.zy-btn { background: var(--zy-accent-btn); }
.zy-btn:hover { background: var(--zy-accent-hover); }
/* A THEME'S BUTTON IS NOT OURS EITHER: a 2.4em line-height, a min-height, an
   uppercase transform and a bottom margin made "Soonest available" twice the
   height of the selects beside it. Sized here, so the row lines up anywhere. */
.kavita-wrap .zy-btn {
	line-height: 1.25; min-height: 0; margin: 0; text-transform: none; letter-spacing: normal;
	font-size: 14px; font-family: inherit; box-shadow: none;
}
.zy-service-price .zy-price { background: var(--zy-accent-btn); color: var(--zy-accent-fg); }
.kavita-step.is-active .zy-ico { background: var(--zy-accent-btn); }
.zy-cal-cell.is-sel { background: var(--zy-accent-btn); }
.zy-btn-ghost:hover { color: var(--zy-accent-text); }
/* Disabled dates are exempt from the contrast rule, but #c0c4cc at 2:1 was
   unreadable rather than merely muted. #767676 is 4.5:1 and still reads as
   "not available". */
.zy-cal-cell.is-past, .zy-cal-cell.is-blocked { color: #767676; }
.zy-slot-local { opacity: 1; color: var(--zy-muted); }
.zy-error { color: #b32d2e; }

/* ---- Screen-reader-only ------------------------------------------------
   For labels that would be visual noise but are needed as accessible names.
   Not display:none, which removes them from the accessibility tree too. */
.zy-sr-only {
	position: absolute !important; width: 1px; height: 1px;
	padding: 0; margin: -1px; overflow: hidden;
	clip: rect(0, 0, 0, 0); white-space: nowrap; border: 0;
}

/* ---- Reduced motion ---------------------------------------------------- */
@media (prefers-reduced-motion: reduce) {
	.kavita-wrap *, .kavita-wrap *::before, .kavita-wrap *::after {
		animation-duration: .01ms !important;
		transition-duration: .01ms !important;
	}
	.zy-service:active { transform: none; }
}

/* ---- Touch targets -----------------------------------------------------
   WCAG 2.2 asks for 24x24 CSS px minimum. The calendar cells and the small
   remove buttons were under it. */
.zy-cal-cell { min-width: 32px; min-height: 32px; }
.zy-cart-del, .zy-coupon-x { min-width: 32px; min-height: 32px; }

/* ---- Locations (step 2) ------------------------------------------------ */
.zy-loc .zy-staff-body .zy-muted { font-size: 12.5px; }

/* ---- Group seats on a slot --------------------------------------------- */
/* Only rendered for a service with capacity above 1, so a clinic that never
   runs a class sees exactly the slot button it always saw. */
.zy-slot-seats { font-size: 11px; color: var(--zy-accent-text); font-weight: 600; }

/* ---- Package credit (summary) -----------------------------------------
   Above the total, not below it: this changes what is owed, and a customer
   must never read a price before being told they have already paid it. */
.zy-credit {
	border: 1px solid #1a7f37; border-radius: 10px; padding: 10px 12px;
	margin: 12px 0 4px; background: #f2fbf4; font-size: 13.5px;
}
.zy-credit strong { color: #14532d; }

/* ---- Gift card (summary) ----------------------------------------------
   Styled as settlement rather than as a discount, because that is what it
   is — the money was already paid by whoever bought the card. */
.zy-sum-gift { color: #14532d; font-weight: 500; }
.zy-gift-left { font-size: 12.5px; margin: 2px 0 0; text-align: right; }
.zy-gift .zy-input { text-transform: uppercase; }

/* ---- Waitlist (date & time) -------------------------------------------- */
.zy-wl {
	border: 1px dashed var(--zy-line); border-radius: 10px;
	padding: 12px 14px; margin-top: 16px; background: #fafafa;
}
.zy-wl-head { font-weight: 500; margin-bottom: 4px; }
.zy-wl .zy-muted { font-size: 12.5px; line-height: 1.45; margin: 0 0 10px; }
.zy-wl-fields { display: grid; gap: 8px; }
.zy-wl-done { color: #14532d; font-weight: 500; margin-top: 16px; }

@media (max-width: 640px) {
	/* Hit targets get bigger, not smaller, on the device most bookings come
	   from. 44px is the platform guidance on both iOS and Android. */
	.zy-cal-grid:not(.zy-cal-dow) .zy-cal-cell { min-height: 44px; }
	.zy-slot { min-height: 44px; }
	.zy-btn, .zy-btn-ghost { min-height: 44px; }
}

/* ======================================================================
   v0.35.0 — RIGHT-TO-LEFT.
   ======================================================================
   Written as logical properties rather than a mirrored stylesheet. WordPress
   convention is a separate -rtl.css generated by flipping left/right, which
   means two files that drift. `margin-inline-start` already means "left in
   English, right in Arabic", so one rule covers both and there is nothing to
   keep in sync.
   Baseline support for logical properties is universal in browsers new enough
   to run the rest of this wizard, so this is not a progressive enhancement. */

[dir="rtl"] .kavita-wrap,
.kavita-wrap[dir="rtl"] { text-align: right; }

/* Arrows are DIRECTIONAL GLYPHS, not decoration. In an RTL layout "back" points
   right, so the ← in the nav has to turn round or it points at the next step. */
[dir="rtl"] .zy-nav .zy-btn-ghost,
[dir="rtl"] .zy-nav .zy-btn { unicode-bidi: plaintext; }
[dir="rtl"] .zy-cal-nav { transform: scaleX(-1); }

/* Anything positioned with a physical side gets its logical equivalent. */
[dir="rtl"] .zy-service-price .zy-price { margin-left: 0; margin-inline-start: 4px; }
[dir="rtl"] .zy-badge { margin-left: 0; margin-inline-start: 8px; }
[dir="rtl"] .zy-chip.is-on::after { margin-left: 0; margin-inline-start: 8px; }
[dir="rtl"] .zy-coupon-x { margin-left: 0; margin-inline-start: 4px; }
[dir="rtl"] .zy-course-ok::before,
[dir="rtl"] .zy-course-skip::before { margin-right: 0; margin-inline-end: 6px; }
[dir="rtl"] .zy-cart-price,
[dir="rtl"] .zy-gift-left { text-align: left; }

/* The mobile calendar frames one edge of the grid; in RTL that edge is the
   other one, or the border lands inside the table. */
@media (max-width: 640px) {
	[dir="rtl"] .zy-cal-grid:not(.zy-cal-dow) {
		border-left: 0; border-right: 1px solid var(--zy-line);
	}
	[dir="rtl"] .zy-cal-grid:not(.zy-cal-dow) .zy-cal-cell {
		border-right: 0; border-left: 1px solid var(--zy-line);
	}
}

/* The phone widget is a third-party stylesheet and does not know about any of
   this; its flag column has to move by hand. */
[dir="rtl"] .kavita-wrap .iti--separate-dial-code .iti__selected-flag { border-radius: 0 8px 8px 0; }

/* ======================================================================
   v0.36.0 — EVENTS.
   ======================================================================
   Reuses the wizard's tokens, buttons, inputs and focus rules rather than
   introducing a second visual language. An event card is a card. */

.zy-events { display: grid; gap: 18px; }
.zy-event {
	display: grid; grid-template-columns: 200px 1fr; gap: 18px;
	border: 1px solid var(--zy-line); border-radius: 12px; padding: 18px;
}
.zy-event.is-out { opacity: .72; }
.zy-event-img { width: 100%; height: 100%; max-height: 180px; object-fit: cover; border-radius: 10px; }
.zy-event-body { min-width: 0; }
.zy-event-title { font-size: 17px; font-weight: 600; margin: 0 0 4px; }
.zy-event-when { font-weight: 500; margin: 0 0 6px; }
.zy-event-desc { font-size: 14px; line-height: 1.5; margin: 8px 0; }
.zy-event-meta { margin: 10px 0 14px; display: flex; align-items: center; gap: 10px; flex-wrap: wrap; }
.zy-event-places {
	font-size: 12px; font-weight: 600; padding: 3px 10px; border-radius: 6px;
	background: #f3f4f6; color: #374151;
}
/* Sold out is stated plainly rather than by graying the card into ambiguity. */
.zy-event-places.is-out { background: #fee2e2; color: #991b1b; }
.zy-early {
	font-size: 11px; font-weight: 700; text-transform: uppercase; letter-spacing: .4px;
	color: #14532d; background: #dcfce7; padding: 2px 8px; border-radius: 5px;
}

/* An event with no image should not leave a 200px hole. */
.zy-event:not(:has(.zy-event-img)) { grid-template-columns: 1fr; }

.zy-event-form { margin-top: 16px; padding-top: 14px; border-top: 1px dashed var(--zy-line); }
.zy-att-row {
	display: grid; grid-template-columns: auto 1fr 32px; gap: 8px;
	align-items: center; margin-bottom: 8px;
}
.zy-att-row:has(select) { grid-template-columns: minmax(140px, 1fr) 1fr 32px; }

@media (max-width: 640px) {
	.zy-event { grid-template-columns: 1fr; }
	.zy-event-img { max-height: 160px; }
	.zy-att-row, .zy-att-row:has(select) { grid-template-columns: 1fr; }
	.zy-att-row .zy-cart-del { justify-self: end; }
}

[dir="rtl"] .zy-event-meta { flex-direction: row-reverse; justify-content: flex-end; }

/* ======================================================================
   v0.39.0 — finding a time, and the shortcuts.
   ====================================================================== */

/* The finder answers the two questions the calendar could not: "soonest" and
   "Saturday mornings". Above the calendar rather than inside it, because it
   replaces the calendar for the people who use it. */
.zy-finder {
	display: flex; gap: 10px; flex-wrap: wrap; align-items: center;
	margin-bottom: 14px; padding-bottom: 14px;
	border-bottom: 1px dashed var(--zy-line);
}
.zy-finder-sel { width: auto; min-width: 130px; }
.zy-finder-out:not(:empty) { margin-bottom: 16px; }
.zy-found { display: grid; grid-template-columns: repeat(auto-fill, minmax(180px, 1fr)); gap: 10px; }
.zy-found .zy-slot { align-items: flex-start; font-weight: 500; }

/* "Book X again?" — shown only when we already know who they are, so it is a
   shortcut rather than a question asked of everybody. */
.zy-repeat {
	display: flex; gap: 14px; align-items: center; justify-content: space-between;
	flex-wrap: wrap; margin-bottom: 18px; padding: 14px 16px;
	border: 1px solid var(--zy-accent-text); border-radius: 10px;
	background: #fff7ed;
}

.zy-events-link { margin: 0 0 14px; font-size: 14px; }
.zy-events-link a { color: var(--zy-accent-text); font-weight: 500; }

@media (max-width: 640px) {
	.zy-finder { flex-direction: column; align-items: stretch; }
	.zy-finder-sel { width: 100%; }
	.zy-repeat { flex-direction: column; align-items: stretch; }
	.zy-repeat .zy-btn { width: 100%; }
}

/* ======================================================================
   v0.40.0 — the assistant.
   ======================================================================
   Styled as a SEARCH FIELD, not a chat bubble. The bottom-right bubble is
   trained as support, so it invites the questions this deliberately refuses;
   a search box promises what it actually does. */

.zy-ask { margin-bottom: 18px; }
/* THE BOX IS NAMED NOW. It was a magnifying glass and a placeholder, which
   reads as "narrow the list down" -- so the one thing on this form no
   competitor has was also the thing nobody tried. Small and quiet: it is a
   signpost to an optional shortcut, not a headline above the booking form. */
.zy-ask-name {
	display: block;
	margin: 0 2px 6px;
	font-size: 12px;
	font-weight: 600;
	letter-spacing: .04em;
	text-transform: uppercase;
	color: var(--zy-muted, #6b7280);
}
.zy-ask-row { display: flex; gap: 8px; align-items: center; position: relative; }
.zy-ask-ico {
	position: absolute; left: 12px; color: var(--zy-muted);
	font-size: 18px; width: 18px; height: 18px; pointer-events: none;
}
.zy-ask-row .zy-input { padding-left: 38px; }
.zy-ask-out:empty { display: none; }
.zy-ask-out { margin: 8px 2px 0; font-size: 14px; }

/* The clinic's own words, presented as a notice rather than as something the
   assistant said — because no model was involved in producing it. */
.zy-ask-urgent {
	border: 1px solid #b32d2e; border-radius: 10px; padding: 12px 14px;
	background: #fef2f2; color: #7f1d1d; font-weight: 500;
}

@media (max-width: 640px) {
	.zy-ask-row { flex-wrap: wrap; }
	.zy-ask-row .zy-input { flex: 1 1 100%; }
	.zy-ask-row .zy-btn { width: 100%; }
}

/* ---------------------------------------------------------------------------
   Rail layouts (0.56.0)

   ONE MARKUP, TWO ARRANGEMENTS. .is-rail-top is what shipped before this and
   is unchanged below 820px in both, because a phone has no room for a sidebar
   at any setting. 820 is arithmetic, not taste: the rail needs ~220px for an
   icon beside "Operating Hours" without wrapping, and the panel needs ~600px
   for a week of slots that can be read.
   -------------------------------------------------------------------------*/
.kavita-rail-toggle { display: none; }

@media (min-width: 820px) {
	.kavita-wrap.is-rail-side { display: grid; grid-template-columns: 230px minmax(0, 1fr); gap: 24px; align-items: start; }
	.kavita-wrap.is-rail-side .kavita-title, .kavita-wrap.is-rail-side .kavita-intro { grid-column: 1 / -1; }

	.is-rail-side .kavita-steps {
		flex-direction: column; flex-wrap: nowrap; gap: 2px;
		margin-bottom: 0; padding: 12px; position: sticky; top: 20px;
	}
	.is-rail-side .kavita-step { width: 100%; justify-content: flex-start; padding: 9px 10px; }
	.is-rail-side .kavita-step.is-active { background: #fff7ed; }

	/* The collapse control. Between about 820 and 1100 the rail fits but costs
	   the calendar width somebody would rather have, so it folds to icons. */
	.is-rail-side .kavita-rail-toggle {
		display: flex; align-items: center; gap: 8px; width: 100%;
		margin-top: 10px; padding: 8px 10px; border: 0; border-radius: 8px;
		background: transparent; color: var(--zy-muted); cursor: pointer;
		font: inherit; font-size: 13px; border-top: 1px solid var(--zy-line);
	}
	.is-rail-side .kavita-rail-toggle:hover { color: var(--zy-text); }

	.kavita-wrap.is-rail-side.is-rail-collapsed { grid-template-columns: 64px minmax(0, 1fr); }
	.is-rail-side.is-rail-collapsed .kavita-step { justify-content: center; padding: 9px 0; }
	.is-rail-side.is-rail-collapsed .kavita-step > span:not(.zy-ico),
	.is-rail-side.is-rail-collapsed .kavita-rail-toggle-t { display: none; }
	.is-rail-side.is-rail-collapsed .kavita-rail-toggle { justify-content: center; }
	.is-rail-side.is-rail-collapsed .kavita-rail-toggle .zy-ico { transform: scaleX(-1); }
}

/* RTL: the rail belongs on the right, and the fold arrow points the other way. */
[dir="rtl"] .is-rail-side .kavita-rail-toggle .zy-ico { transform: scaleX(-1); }
[dir="rtl"] .is-rail-side.is-rail-collapsed .kavita-rail-toggle .zy-ico { transform: none; }

/* ---------------------------------------------------------------------------
   Motion (0.57.0)

   ONE PIPELINE, TWO SPEEDS. Everything below is scoped to .is-motion-smooth,
   so "Plain" is not a second code path -- it is this with nothing switched on.
   transform and opacity ONLY: a booking form that janks on a mid-range Android
   is worse than one that snaps cleanly, and those two are the only properties
   the compositor can animate without touching layout.

   The visitor's own reduced-motion setting overrides the clinic at the bottom
   of this file. It is an accessibility preference they already made in their
   operating system, often for migraine or a vestibular condition.
   -------------------------------------------------------------------------*/
@keyframes zy-rise { from { opacity: 0; transform: translateY(8px); } to { opacity: 1; transform: none; } }
@keyframes zy-shimmer { from { background-position: -420px 0; } to { background-position: 420px 0; } }

/* The step that just arrived. The panel's height is animated from JS, which is
   the half that stops the page lurching between a short step and a tall one. */
.is-motion-smooth .kavita-panel { transition: height .24s ease; overflow: hidden; }
.is-motion-smooth .kavita-panel.is-entering > * { animation: zy-rise .24s ease-out both; }

/* Slot times arrive in a quick stagger. Pure CSS -- nth-child rather than a
   per-node delay set in JS, so nothing has to know how many slots there are. */
.is-motion-smooth .zy-slot-grid .zy-slot { animation: zy-rise .2s ease-out both; }
.is-motion-smooth .zy-slot-grid .zy-slot:nth-child(1)  { animation-delay: 0ms; }
.is-motion-smooth .zy-slot-grid .zy-slot:nth-child(2)  { animation-delay: 20ms; }
.is-motion-smooth .zy-slot-grid .zy-slot:nth-child(3)  { animation-delay: 40ms; }
.is-motion-smooth .zy-slot-grid .zy-slot:nth-child(4)  { animation-delay: 60ms; }
.is-motion-smooth .zy-slot-grid .zy-slot:nth-child(5)  { animation-delay: 80ms; }
.is-motion-smooth .zy-slot-grid .zy-slot:nth-child(6)  { animation-delay: 100ms; }
.is-motion-smooth .zy-slot-grid .zy-slot:nth-child(7)  { animation-delay: 120ms; }
.is-motion-smooth .zy-slot-grid .zy-slot:nth-child(8)  { animation-delay: 140ms; }
/* Past eight it stops reading as a stagger and starts reading as a wait. */
.is-motion-smooth .zy-slot-grid .zy-slot:nth-child(n+9) { animation-delay: 160ms; }

/* Waiting for /slots. A shimmer where the times will be beats an empty box:
   the same wait, minus the moment of wondering whether it is broken. */
.zy-sk { display: grid; gap: 8px; }
.zy-sk i {
	display: block; height: 42px; border-radius: 8px;
	background: #f3f4f6;
}
.is-motion-smooth .zy-sk i {
	background: linear-gradient(90deg, #f3f4f6 0%, #e9ebef 50%, #f3f4f6 100%);
	background-size: 420px 100%;
	animation: zy-shimmer 1.1s linear infinite;
}

/* State changes. Short, and the same curve everywhere -- one consistent
   easing is most of what "sleek" actually means. */
.is-motion-smooth .zy-slot,
.is-motion-smooth .zy-btn,
.is-motion-smooth .zy-btn-ghost,
.is-motion-smooth .kavita-step { transition: background-color .15s ease, border-color .15s ease, color .15s ease, transform .12s ease; }
.is-motion-smooth .zy-slot:active,
.is-motion-smooth .zy-btn:active { transform: scale(.985); }
.is-motion-smooth .kavita-step .zy-ico { transition: background-color .18s ease, color .18s ease; }

/* THE VISITOR'S SETTING WINS. Not "mostly wins" -- the animations above are
   the ones that would trigger the symptom, so they stop entirely. */
@media (prefers-reduced-motion: reduce) {
	.is-motion-smooth .kavita-panel { transition: none; }
	.is-motion-smooth .kavita-panel.is-entering > *,
	.is-motion-smooth .zy-slot-grid .zy-slot,
	.is-motion-smooth .zy-sk i { animation: none; }
	.is-motion-smooth .zy-slot:active,
	.is-motion-smooth .zy-btn:active { transform: none; }
}

/* CUSTOM FIELD CHOICES. Buttons rather than a dropdown for three or four
   options: a dropdown hides every choice behind a tap, and the reason for
   asking at all is that the answer should be quick. */
.zy-choices{display:flex;flex-wrap:wrap;gap:8px;margin-top:6px}
.zy-choice{display:inline-flex;align-items:center;gap:7px;padding:8px 14px;border:1px solid var(--zy-line,#dcdcde);border-radius:999px;cursor:pointer;font-size:14px;line-height:1.2;background:var(--zy-card,#fff);transition:border-color .12s ease,background .12s ease}
.zy-choice:hover{border-color:var(--zy-accent,#2271b1)}
.zy-choice.on{border-color:var(--zy-accent,#2271b1);background:color-mix(in srgb,var(--zy-accent,#2271b1) 8%,transparent)}
.zy-choice input{margin:0}
.zy-choice:focus-within{outline:2px solid var(--zy-accent,#2271b1);outline-offset:2px}
/* A note asks nothing; it must not look like an unanswered question. */
.zy-note-block{margin:10px 0;padding:11px 14px;border-left:3px solid var(--zy-accent,#2271b1);background:color-mix(in srgb,var(--zy-accent,#2271b1) 5%,transparent);border-radius:0 6px 6px 0;font-size:14px}
@media (prefers-reduced-motion:reduce){.zy-choice{transition:none}}

/* How many are coming, on a class. Never drawn for a one-to-one appointment. */
.zy-cart-seats{padding:5px 8px;border:1px solid var(--zy-line,#dcdcde);border-radius:8px;background:var(--zy-card,#fff);font-size:13px;max-width:130px}

/* Event tags. A second axis beside the category, so a list of thirty reads at
   a glance rather than needing to be opened one by one. */
.zy-event-tags{display:flex;flex-wrap:wrap;gap:6px;margin:6px 0 2px}
.zy-tag{font-size:11px;font-weight:600;letter-spacing:.02em;padding:2px 9px;border-radius:999px;background:color-mix(in srgb,var(--zy-accent,#2271b1) 10%,transparent);color:var(--zy-accent,#2271b1)}

/* The line that says where a typed sentence goes. Under the box, quiet, and
   rendered only when the server says something really does leave the site --
   a privacy notice that overstates is its own kind of wrong. */
.zy-ask-notice {
	margin: 6px 2px 0;
	font-size: 12px;
	line-height: 1.5;
	color: var(--zy-muted, #6b7280);
}

/* The waitlist form gained a preference and a note, and a textarea in a stack
   built for single-line inputs needs to be told it may not be resized sideways
   out of its own box. */
.zy-wl-notes { resize: vertical; min-height: 56px; font: inherit; }
