/* Qyx AI Dashboard - glassmorphism, glows, premium SaaS tweaks. */

:root {
	--qyx-bg: hsl(0 0% 98%); /* must match --background so SVG dividers blend seamlessly */
	--qyx-ink: #0f172a;

	/* Source theme tokens - needed by header-landing.php classes. */
	--background: 0 0% 98%;
	--foreground: 0 0% 17%;
	--heading-foreground: 0 0% 17%;
	--primary: 0 0% 0%;
	--primary-foreground: 0 0% 100%;

	--gradient-1: #5AAAF6;
	--gradient-2: #D52FCA;
	--gradient-3: #FF4754;
	--gradient-4: #FFB33B;
	--gradient-5: #43CC3E;
	--gradient-stops: var(--gradient-1), var(--gradient-2), var(--gradient-3), var(--gradient-4), var(--gradient-5);

	/* Dark-section glow palette (features + generators ambient/aurora). */
	--qyx-violet: #7a61b2;
	--qyx-aurora-blue: #527aad;
	--qyx-aurora-indigo: #6455d4;
	--qyx-aurora-cyan: #3fd0d6;
}

/* Custom utilities for source-theme color tokens (HSL-based).
   These mirror the Tailwind theme.extend.colors that the SCSS source assumes. */
.text-foreground { color: hsl(var(--foreground)); }
.text-background { color: hsl(var(--background)); }
.bg-background { background-color: hsl(var(--background)); }
.bg-foreground { background-color: hsl(var(--foreground)); }
.bg-heading-foreground { background-color: hsl(var(--heading-foreground)); }
.fill-foreground { fill: hsl(var(--foreground)); }
.fill-background { fill: hsl(var(--background)); }
.border-foreground\/5 { border-color: hsl(var(--foreground) / 0.05); }
.text-foreground\/30 { color: hsl(var(--foreground) / 0.30); }
.text-foreground\/40 { color: hsl(var(--foreground) / 0.40); }
.text-foreground\/50 { color: hsl(var(--foreground) / 0.50); }
.text-foreground\/60 { color: hsl(var(--foreground) / 0.60); }
.text-foreground\/70 { color: hsl(var(--foreground) / 0.70); }
.hover\:text-foreground:hover { color: hsl(var(--foreground)); }
.hover\:text-background:hover { color: hsl(var(--background)); }
.hover\:border-background:hover { border-color: hsl(var(--background)); }
.hover\:bg-background:hover { background-color: hsl(var(--background)); }
.hover\:bg-foreground:hover { background-color: hsl(var(--foreground)); }

/* Header dark-mode hover override - when site-header has .is-dark (over a dark
   section), hovering a CTA changes BG to white. Force readable dark text
   regardless of Tailwind variant compilation. Targets the rounded-full pill CTAs
   (Sign In, Join Hub, Dashboard) but not the logo or burger. */
.site-header.is-dark a.rounded-full:hover,
.site-header.is-dark a.rounded-full:hover .relative,
.site-header.is-dark a.rounded-full:hover > span {
	color: hsl(var(--foreground)) !important;
}
.site-header.is-dark button.rounded-full:hover,
.site-header.is-dark button.rounded-full:hover svg {
	color: hsl(var(--foreground)) !important;
}

/* Outline-glow base - gradient ring around CTAs (Sign In / Join Hub / Dashboard).
   Source base lives in the parent "default" theme; this is a faithful rebuild
   so the buttons render correctly until you paste the original base SCSS. */
.lqd-outline-glow {
	position: absolute;
	inset: 0;
	border-radius: inherit;
	pointer-events: none;
	opacity: 1;
	transition: opacity 0.3s ease;
	z-index: 0;
}
.lqd-outline-glow::before {
	content: "";
	position: absolute;
	inset: 0;
	border-radius: inherit;
	padding: var(--outline-glow-w, 2px);
	background: conic-gradient(from 290deg, var(--gradient-1), var(--gradient-2), var(--gradient-3), var(--gradient-4), var(--gradient-5));
	-webkit-mask:
		linear-gradient(#fff 0 0) content-box,
		linear-gradient(#fff 0 0);
	mask:
		linear-gradient(#fff 0 0) content-box,
		linear-gradient(#fff 0 0);
	-webkit-mask-composite: xor;
	mask-composite: exclude;
}
.lqd-outline-glow-custom::before {
	background: conic-gradient(from 290deg, var(--gradient-1), var(--gradient-2), var(--gradient-3), var(--gradient-4), var(--gradient-5));
}

/* Source-theme typography utilities used by hero. */
.font-body { font-family: var(--font-body, 'Inter'), 'Inter', ui-sans-serif, system-ui, sans-serif; }
.font-heading { font-family: var(--font-heading, 'Spline Sans'), 'Spline Sans', ui-sans-serif, system-ui, sans-serif; }
.text-3xs { font-size: 0.6875rem; line-height: 1rem; } /* ~11px */

/* Hero H1 - matches source `--h1-font-size: 4.75rem` (76px) with responsive scaling. */
.banner-title {
	font-family: var(--font-heading, 'Spline Sans'), 'Inter', ui-sans-serif, system-ui, sans-serif;
	font-size: clamp(2.25rem, 4vw + 1rem, 3.5rem); /* ~36px mobile -> ~56px desktop (friendlier than the old 76px) */
	font-weight: 600;
	letter-spacing: var(--h1-letter-spacing, -0.01em);
	line-height: 1.1;
	color: hsl(var(--heading-foreground));
}

/* Text rotator - width transitions handled by JS reading active item width. */
.lqd-text-rotator { vertical-align: bottom; }
.lqd-text-rotator-item > span {
	background: linear-gradient(90deg, var(--gradient-1), var(--gradient-2), var(--gradient-3), var(--gradient-4), var(--gradient-5));
	-webkit-background-clip: text;
	background-clip: text;
	-webkit-text-fill-color: transparent;
	color: transparent;
}

/* Initial-state hide so animations don't flash before .page-loaded lands. */
body:not(.page-loaded) [class*="group-[.page-loaded]/body"] { /* placeholder - relies on Tailwind variant */ }

/* ============================================================
   Hero widget grid (right column) - phot.ai-inspired card grid.
   Mixed aspect ratios, themed per qyx.ai marketing toolset.
   ============================================================ */
.qyx-hero-widget {
	position: relative;
	display: block;
	border-radius: 1.25rem; /* 20px */
	overflow: hidden;
	box-shadow: 0 6px 20px -8px rgba(15, 23, 42, 0.18), 0 2px 6px -2px rgba(15, 23, 42, 0.08);
	transition: transform .35s cubic-bezier(.2,.7,.2,1), box-shadow .35s ease;
	isolation: isolate;
}
.qyx-hero-widget:hover {
	transform: translateY(-4px) scale(1.015);
	box-shadow: 0 18px 40px -12px rgba(15, 23, 42, 0.28), 0 4px 10px -4px rgba(15, 23, 42, 0.12);
	z-index: 2;
}

/* Inner content area - sits above noise/label, below the "Try" overlay. */
.qyx-hero-widget__body {
	position: absolute;
	inset: 0;
	display: block;
	z-index: 1;
}

/* Bottom label - small chip over card */
.qyx-hero-widget__label {
	position: absolute;
	left: 0.75rem;
	bottom: 0.75rem;
	z-index: 2;
	font-size: 0.6875rem;
	font-weight: 700;
	letter-spacing: 0.01em;
	color: #fff;
	background: rgba(15, 23, 42, 0.35);
	backdrop-filter: blur(8px);
	-webkit-backdrop-filter: blur(8px);
	padding: 0.25rem 0.55rem;
	border-radius: 999px;
}
.qyx-hero-widget__label--light {
	color: #fff;
	background: rgba(255, 255, 255, 0.15);
}

/* CTA overlay - the canonical CTA, just smaller (dark pill + arrow, colour from
   the same --foreground/--background tokens). Fades in on hover. */
.qyx-hero-widget__try {
	position: absolute;
	top: 50%; left: 50%;
	transform: translate(-50%, calc(-50% + 8px));
	z-index: 3;
	display: inline-flex;
	align-items: center;
	gap: 0.3rem;
	font-size: 0.6875rem;
	font-weight: 600;
	color: hsl(var(--background));
	background: hsl(var(--foreground));
	padding: 0.4rem 0.7rem;
	border-radius: 0.55rem;
	box-shadow: 0 8px 20px -6px rgba(15, 23, 42, 0.5);
	opacity: 0;
	transition: opacity .25s ease, transform .35s cubic-bezier(.2,.7,.2,1);
	pointer-events: none;
	white-space: nowrap;
}
.qyx-hero-widget__try::after { content: "→"; font-weight: 700; }
.qyx-hero-widget:hover .qyx-hero-widget__try {
	opacity: 1;
	transform: translate(-50%, -50%);
}

/* Hero 2-row auto-carousel - scrolls LEFT toward the CTA (eye follows motion).
   Reuses .qyx-hero-widget cards at a fixed row height so each card's aspect
   ratio derives its width. GPU-only (transform), pauses on hover, off under
   reduced-motion. The two rows run at slightly different speeds for depth. */
.qyx-hero-carousel {
	display: flex;
	flex-direction: column;
	gap: 0.85rem;
	overflow: hidden;
	-webkit-mask-image: linear-gradient(90deg, transparent 0%, #000 7%, #000 93%, transparent 100%);
	mask-image: linear-gradient(90deg, transparent 0%, #000 7%, #000 93%, transparent 100%);
}
.qyx-hero-carousel__row { overflow: hidden; }
.qyx-hero-carousel__track {
	display: flex;
	gap: 0.85rem;
	width: max-content;
	animation: qyx-hero-scroll var(--qyx-hero-dur, 46s) linear infinite;
	will-change: transform;
}
.qyx-hero-carousel__row--2 .qyx-hero-carousel__track { --qyx-hero-dur: 58s; }
.qyx-hero-carousel:hover .qyx-hero-carousel__track { animation-play-state: paused; }
.qyx-hero-carousel .qyx-hero-widget {
	height: 190px;
	width: auto;
	flex: 0 0 auto;
}
@keyframes qyx-hero-scroll {
	from { transform: translateX(0); }
	to   { transform: translateX(calc(-50% - 0.425rem)); }
}
@media (max-width: 1023px) { .qyx-hero-carousel .qyx-hero-widget { height: 150px; } }
@media (max-width: 767px)  { .qyx-hero-carousel .qyx-hero-widget { height: 132px; } }
@media (prefers-reduced-motion: reduce) {
	.qyx-hero-carousel__track { animation: none; }
}

/* SVG noise texture for subtle depth */
.qyx-hero-widget__noise {
	position: absolute;
	inset: 0;
	z-index: 0;
	pointer-events: none;
	opacity: 0.12;
	mix-blend-mode: overlay;
	background-image: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 200 200'><filter id='n'><feTurbulence type='fractalNoise' baseFrequency='0.9' numOctaves='2' stitchTiles='stitch'/></filter><rect width='100%25' height='100%25' filter='url(%23n)' opacity='0.7'/></svg>");
	background-size: 200px 200px;
}

/* Rainbow gradient widget */
.qyx-hero-widget--rainbow {
	background:
		conic-gradient(from 200deg at 30% 40%, var(--gradient-2), var(--gradient-3) 25%, var(--gradient-4) 45%, var(--gradient-5) 65%, var(--gradient-1) 85%, var(--gradient-2));
	background-size: 200% 200%;
	animation: qyxRainbowShift 9s ease-in-out infinite;
}
@keyframes qyxRainbowShift {
	0%, 100% { background-position: 0% 0%; }
	50%      { background-position: 100% 100%; }
}

/* WhatsApp-style chat bubbles inside widget 1 */
.qyx-hero-widget__bubbles {
	position: absolute;
	inset: 0.6rem;
	display: flex;
	flex-direction: column;
	gap: 0.35rem;
	font-size: 0.625rem;
	line-height: 1.25;
}
.qyx-hero-widget__bubble {
	display: inline-block;
	max-width: 80%;
	padding: 0.3rem 0.5rem;
	border-radius: 0.75rem;
	background: #fff;
	color: #0f172a;
	font-weight: 500;
	box-shadow: 0 1px 2px rgba(0,0,0,0.06);
	width: fit-content;
}
.qyx-hero-widget__bubble--in {
	align-self: flex-start;
	border-bottom-left-radius: 0.25rem;
}
.qyx-hero-widget__bubble--out {
	align-self: flex-end;
	background: #dcfce7;
	border-bottom-right-radius: 0.25rem;
}

@media (prefers-reduced-motion: reduce) {
	.qyx-hero-widget,
	.qyx-hero-widget__try { transition: none; }
	.qyx-hero-widget--rainbow { animation: none; }
}

/* Curved section dividers - fill matches body bg so the transition between
   light and dark sections has zero visible seam. Use a very shallow curve
   (matches reference site) so the white "shoulders" against the tinted hero
   gradient stay minimal and the seam stays invisible. */
.qyx-features__divider path,
.qyx-generators__divider path {
	fill: var(--qyx-bg);
}

/* Features dark section - glassmorphism cards + ambient glow blobs. */
/* Violet corner glow - anchored top-left, brightest in the corner and fading
   to transparent at 60% so it never reaches the top wave (no periwinkle seam). */
.qyx-features__glow--violet {
	inset: 0 auto auto 0;
	width: 720px;
	height: 520px;
	pointer-events: none;
	background: radial-gradient(circle at 0% 0%,
		color-mix(in srgb, var(--qyx-violet) 55%, transparent), transparent 60%);
	animation: qyx-glow-breathe 12s ease-in-out infinite;
}
/* Blue ambient - soft indigo wash centred behind the cards, complements violet. */
.qyx-features__glow--blue {
	background: radial-gradient(50% 50% at 50% 35%,
		color-mix(in srgb, var(--qyx-aurora-indigo) 30%, transparent), transparent 70%);
	filter: none;
	opacity: 1;
}
.qyx-feature__icon {
	box-shadow:
		inset 0 2px 8px rgba(255, 255, 255, 0.12),
		inset 0 -1px 4px rgba(0, 0, 0, 0.4),
		0 8px 24px -8px rgba(0, 0, 0, 0.5);
}

/* Generators dark section - pure black base so it flows seamlessly out of
   features above. Tinting is provided by ambient glow blobs (see below). */
.qyx-generators__bg {
	background: #090508;
}
.qyx-generators__glow {
	position: absolute;
	border-radius: 9999px;
	pointer-events: none;
	filter: blur(130px);
}
.qyx-generators__glow--pink {
	top: 25%; right: -5%;
	width: 480px; height: 480px;
	background: #ec4899;
	opacity: 0.22;
}
.qyx-generators__glow--sky {
	bottom: 10%; left: 30%;
	width: 520px; height: 520px;
	background: #38bdf8;
	opacity: 0.18;
}
/* Bottom aurora band - blurred brand-colour wash along the dark section's lower
   edge. Each radial peaks at y=100% (section bottom), where the opaque white
   wave divider (z-2) paints over it - so nothing bleeds past the curve onto the
   light section below. The visible portion sits above the crest, already fading. */
.qyx-generators__aurora {
	filter: blur(40px);
	opacity: 0.85;
	background:
		radial-gradient(45% 130% at 12% 100%, var(--qyx-aurora-blue),   transparent 60%),
		radial-gradient(45% 130% at 45% 100%, var(--qyx-aurora-indigo), transparent 60%),
		radial-gradient(45% 130% at 88% 100%, var(--qyx-aurora-cyan),   transparent 60%);
	animation: qyx-aurora-drift 18s ease-in-out infinite;
}
.qyx-tab--active .qyx-tab__icon {
	background: rgba(255, 255, 255, 0.10);
}

/* ============================================================
   Dark-section motion - scroll reveal, glow drift, mockup anim.
   All gated behind prefers-reduced-motion at the bottom of this block.
   ============================================================ */

/* Scroll reveal - fade + slide-up, staggered via --reveal-delay. JS adds
   .is-in-view once (IntersectionObserver, see assets/js/qyx-reveal.js). */
[data-reveal] {
	opacity: 0;
	transform: translateY(24px);
	transition: opacity 0.7s ease, transform 0.7s cubic-bezier(0.2, 0.7, 0.2, 1);
	transition-delay: var(--reveal-delay, 0ms);
}
[data-reveal].is-in-view {
	opacity: 1;
	transform: none;
}

/* Kinetic word marquee - track holds two identical word-runs; translating by
   -50% loops seamlessly. See template-parts/landing/marquee.php. */
.qyx-marquee__track {
	width: max-content;
	animation: qyx-marquee 28s linear infinite;
}
.qyx-marquee:hover .qyx-marquee__track {
	animation-play-state: paused;
}
@keyframes qyx-marquee {
	from { transform: translateX(0); }
	to   { transform: translateX(-50%); }
}

/* Marketing-tools - cards fan out (rotation per --rotate) on lg+; GSAP reads
   this as the resting state and animates the fly-in toward it. */
@media (min-width: 1024px) {
	.qyx-mtools__card { transform: rotate(var(--rotate, 0deg)); }
}

/* Marketing-tools - flanking platform badges gently oscillate. */
.qyx-mtools__badge--wa { animation: qyx-oscillate 1.5s ease-in-out infinite; }
.qyx-mtools__badge--tg { animation: qyx-oscillate 1.5s ease-in-out infinite 0.2s; }
@keyframes qyx-oscillate {
	0%, 100% { transform: translateY(0) rotate(-4deg); }
	50%      { transform: translateY(-10px) rotate(4deg); }
}

/* "Start Training" - spinning conic-gradient ring around the pill. */
.qyx-train-ring::before {
	content: "";
	position: absolute;
	inset: -3px;
	border-radius: 9999px;
	padding: 3px;
	background: conic-gradient(from 0deg, #5AAAF6, #D52FCA, #FF4754, #FFB33B, #43CC3E, #5AAAF6);
	-webkit-mask: linear-gradient(#000 0 0) content-box, linear-gradient(#000 0 0);
	-webkit-mask-composite: xor;
	mask: linear-gradient(#000 0 0) content-box, linear-gradient(#000 0 0);
	mask-composite: exclude;
	animation: qyx-spin 4s linear infinite;
}
@keyframes qyx-spin { to { transform: rotate(360deg); } }

/* Flickity testimonials - room below for page dots; cells keep Flickity's
   own absolute layout (do NOT force flex on .flickity-slider - it breaks it). */
.qyx-testimonials__carousel .flickity-page-dots {
	bottom: -2.25rem;
}
.qyx-testimonials__carousel:focus,
.qyx-testimonials__carousel .flickity-viewport:focus { outline: none; }

/* Glow "breathing" + aurora drift - subtle ambient life. */
@keyframes qyx-aurora-drift {
	0%, 100% { transform: translateX(0) scale(1); }
	50%      { transform: translateX(2.5%) scale(1.05); }
}
@keyframes qyx-glow-breathe {
	0%, 100% { opacity: 0.85; }
	50%      { opacity: 1; }
}

/* Mockup - skeleton shimmer sweep on the "draft" preview bars. */
.qyx-skeleton {
	background: linear-gradient(90deg,
		rgba(255, 255, 255, 0.04) 25%,
		rgba(255, 255, 255, 0.10) 37%,
		rgba(255, 255, 255, 0.04) 63%);
	background-size: 400% 100%;
	animation: qyx-shimmer 1.6s ease infinite;
}
@keyframes qyx-shimmer {
	0%   { background-position: 100% 0; }
	100% { background-position: 0 0; }
}

@media (prefers-reduced-motion: reduce) {
	[data-reveal] {
		opacity: 1;
		transform: none;
		transition: none;
	}
	.qyx-generators__aurora,
	.qyx-features__glow--violet,
	.qyx-skeleton,
	.qyx-marquee__track,
	.qyx-mtools__badge--wa,
	.qyx-mtools__badge--tg,
	.qyx-train-ring::before {
		animation: none;
	}
}

/* Phone perf: the oversized blur blobs are GPU-heavy and can stutter/freeze
   mobile Chrome when scrolled into the dark animation sections. Shrink the
   worst offenders and drop the aurora layer on small screens. */
@media (max-width: 767px) {
	.qyx-generators__glow,
	.qyx-generators__glow--pink,
	.qyx-generators__glow--sky {
		filter: blur(60px);
		opacity: 0.45;
	}
	.qyx-features__glow--violet,
	.qyx-features__glow--blue {
		filter: blur(70px);
	}
	.qyx-generators__aurora {
		display: none;
	}
	/* Stop the continuously-running non-composited animations: each repaints or
	   relayouts every frame on the main thread (background-position, box-shadow)
	   or re-rasters a large blur (drifting orbs). Lighthouse flagged these as the
	   mobile jank sources (Style&Layout + Rendering ≈ 3.1s). Static fallbacks
	   below keep the same look, just without the per-frame cost. Desktop is
	   untouched - these rules live only inside this max-width:767px block. */
	.qyx-hero-widget--rainbow,   /* qyxRainbowShift - background-position paint */
	.qyx-skeleton,               /* qyx-shimmer      - background-position paint */
	.qyx-pulse::after,           /* qyxPulse         - box-shadow paint */
	.qyx-features__glow--violet, /* qyx-glow-breathe */
	.qyx-aurora__orb {           /* qyx-drift-*      - animated blur(90px) re-raster */
		animation: none !important;
	}
	/* The hero text rotator tweens `width` (Tailwind transition-[width]) on each
	   word swap, forcing a layout every frame. Kill the tween only - JS still
	   sets the width instantly per word, so the rotation still works. */
	.lqd-text-rotator {
		transition: none !important;
	}
}

/* Vertical-slider (cta.php) - stack all slides in a single grid cell instead of
   absolute-positioning them. The stage then grows to fit the active slide at any
   width (the old `absolute inset-0` couldn't grow, so stacked mobile content
   overflowed the fixed-height box and overlapped the prev/next nav). Only the
   active slide is visible via x-show; during a transition both briefly share the
   cell and cross-fade. */
.qyx-vslider__stage { display: grid; }
.qyx-vslider__slide { grid-area: 1 / 1; }
/* Decorative gradient band is sm+ only (matches the source vertical-slider). */
@media (max-width: 639.98px) { .qyx-vslider__band { display: none; } }

/* Tools "stacking cards" on mobile/tablet (<lg) - robust CSS position:sticky
   stack, replacing the GSAP pin (which mis-positions on mobile because the
   address bar resizes the viewport mid-scroll). Each .tool-item sticks at the
   same top with a small per-index offset, so cards stack with earlier ones
   peeking behind. Desktop (lg+) keeps the GSAP pin/scale - see initToolsPin. */
@media (max-width: 1023.98px) {
	#ai-tools {
		overflow: visible; /* the section's overflow:hidden would trap sticky */
	}
	#ai-tools .tool-item {
		min-height: 0;     /* drop min-h-screen: each card's scroll segment = its own height */
		padding-top: 1.25rem;
		padding-bottom: 1.25rem;
		position: sticky;
		top: calc(80px + var(--i, 0) * 7px);
	}
}

/* ============================================================
   "As seen on" platform logos row.
   ============================================================ */
.qyx-as-seen-on {
	background:
		radial-gradient(ellipse 70% 100% at 50% 50%, rgba(213, 47, 202, 0.04), transparent 70%);
}
.qyx-platform {
	display: inline-flex;
	align-items: center;
	gap: 0.5rem;
	color: #475569;
	font-weight: 700;
	font-size: 1.0625rem;
	letter-spacing: -0.01em;
	opacity: 0.65;
	transition: opacity .2s ease, color .2s ease;
}
.qyx-platform:hover { opacity: 1; color: #0f172a; }
.qyx-platform svg { width: 22px; height: 22px; }
.qyx-platform__name { line-height: 1; }

/* Ecosystem section - AI model name pills (ecosystem.php). */
.qyx-model-pill {
	display: inline-flex;
	align-items: center;
	gap: 0.5rem;
	flex-shrink: 0;
	padding: 0.5rem 0.9rem;
	border-radius: 999px;
	background: #fff;
	border: 1px solid rgba(15, 23, 42, 0.08);
	box-shadow: 0 2px 6px -2px rgba(15, 23, 42, 0.06);
	font-size: 0.875rem;
	font-weight: 600;
	color: #1e293b;
	white-space: nowrap;
}
.qyx-model-pill__dot {
	width: 0.6rem;
	height: 0.6rem;
	border-radius: 999px;
	background: linear-gradient(135deg, var(--gradient-2), var(--gradient-1));
	flex-shrink: 0;
}

/* Brand logo (header/footer) - assets/images/branding logos/.
   In the header the white variant swaps in over dark sections (.is-dark). */
.qyx-logo { height: 30px; width: auto; display: block; }
.qyx-logo--dark { display: none; }
.site-header.is-dark .qyx-logo--light { display: none; }
.site-header.is-dark .qyx-logo--dark { display: block; }

/* Ecosystem section - static AI model pills (logo + name), everbot-style. */
.qyx-model-pill__logo {
	width: 1.25rem;
	height: 1.25rem;
	object-fit: contain;
	flex-shrink: 0;
}
.qyx-model-grid {
	max-width: 64rem;
	margin: 2.5rem auto 50px;
	padding: 0 1rem;
	display: flex;
	flex-wrap: wrap;
	align-items: center;
	justify-content: center;
	gap: 0.625rem;
}
.qyx-model-pill--more {
	cursor: pointer;
	font-family: inherit;
	font-weight: 700;
	color: #7c3aed;
	gap: 0.35rem;
}
.qyx-model-pill--more:hover {
	background: #faf5ff;
	border-color: rgba(124, 58, 237, 0.35);
}
.qyx-model-pill__chev {
	width: 0.85rem;
	height: 0.85rem;
}
@media (min-width: 640px) {
	.qyx-model-grid { gap: 0.75rem; margin-top: 3rem; }
}

/* Pull the ecosystem section up under the hero. */
.qyx-ecosystem { margin-top: -120px; }

/* "Always the latest AI models" - live pulsing dot (signals 24/7 updates). */
.qyx-live-dot {
	position: relative;
	display: inline-block;
	width: 0.5rem;
	height: 0.5rem;
	border-radius: 999px;
	background: #10b981;
	flex-shrink: 0;
}
.qyx-live-dot::before {
	content: "";
	position: absolute;
	inset: 0;
	border-radius: inherit;
	background: #10b981;
	animation: qyxLivePing 1.8s cubic-bezier(0, 0, 0.2, 1) infinite;
}
@keyframes qyxLivePing {
	0%        { transform: scale(1);   opacity: 0.55; }
	70%, 100% { transform: scale(2.6); opacity: 0; }
}
@media (prefers-reduced-motion: reduce) {
	.qyx-live-dot::before { animation: none; }
}

/* ============================================================
   AI Models Marquee - horizontal infinite scroll, dual-row.
   ============================================================ */
.qyx-marquee {
	position: relative;
	overflow: hidden;
	-webkit-mask-image: linear-gradient(90deg, transparent 0%, #000 6%, #000 94%, transparent 100%);
	mask-image: linear-gradient(90deg, transparent 0%, #000 6%, #000 94%, transparent 100%);
}
.qyx-marquee__track {
	display: flex;
	gap: 0.75rem;
	width: max-content;
	animation: qyxMarqueeScroll var(--qyx-marquee-duration, 60s) linear infinite;
}
.qyx-marquee[data-dir="right"] .qyx-marquee__track {
	animation-direction: reverse;
}
.qyx-marquee__set {
	display: flex;
	gap: 0.75rem;
	flex-shrink: 0;
	padding-right: 0.75rem;
}
.qyx-marquee:hover .qyx-marquee__track {
	animation-play-state: paused;
}
@keyframes qyxMarqueeScroll {
	0%   { transform: translateX(0); }
	100% { transform: translateX(calc(-50% - 0.375rem)); }
}
@media (prefers-reduced-motion: reduce) {
	.qyx-marquee__track { animation: none; }
}

html, body { background: var(--qyx-bg); }
html { scroll-padding-top: 120px; scroll-behavior: smooth; }
@media (prefers-reduced-motion: reduce) { html { scroll-behavior: auto; } }
/* Only hide elements that explicitly opt in with x-cloak. Never gate <body>
   on Alpine init - if Alpine ever errors, the page must still render. */
[x-cloak] { display: none !important; }

/* ============================================================
   Background ambient glows - soft, blurred, low opacity.
   ============================================================ */
.qyx-ambient {
	position: absolute; inset: 0; overflow: hidden; pointer-events: none; z-index: 0;
}
.qyx-ambient::before,
.qyx-ambient::after,
.qyx-ambient > span {
	content: ""; position: absolute; border-radius: 9999px; filter: blur(80px);
}
.qyx-ambient::before {
	width: 520px; height: 520px; left: -120px; top: -160px;
	background: radial-gradient(closest-side, rgba(139, 92, 246, 0.35), transparent 70%);
	opacity: 0.55;
}
.qyx-ambient::after {
	width: 560px; height: 560px; right: -140px; top: -180px;
	background: radial-gradient(closest-side, rgba(56, 189, 248, 0.30), transparent 70%);
	opacity: 0.55;
}
.qyx-ambient > span {
	width: 420px; height: 420px; left: 50%; top: 60px; transform: translateX(-50%);
	background: radial-gradient(closest-side, rgba(244, 114, 182, 0.25), transparent 70%);
	opacity: 0.55;
}

/* ============================================================
   Glass card - used by most floating panels.
   ============================================================ */
.qyx-glass {
	background: rgba(255,255,255,0.78);
	backdrop-filter: saturate(140%) blur(14px);
	-webkit-backdrop-filter: saturate(140%) blur(14px);
	border: 1px solid rgba(255,255,255,0.55);
	box-shadow: 0 10px 40px rgba(15, 23, 42, 0.06);
	border-radius: 1.5rem;
}
.qyx-glass-strong {
	background: rgba(255,255,255,0.92);
	backdrop-filter: saturate(160%) blur(18px);
	-webkit-backdrop-filter: saturate(160%) blur(18px);
	border: 1px solid rgba(255,255,255,0.6);
	box-shadow: 0 18px 60px rgba(15, 23, 42, 0.08);
	border-radius: 1.5rem;
}
.qyx-lift {
	transition: transform .3s ease, box-shadow .3s ease, border-color .3s ease;
}
.qyx-lift:hover {
	transform: translateY(-2px);
	box-shadow: 0 18px 60px rgba(15, 23, 42, 0.10);
	border-color: rgba(139, 92, 246, 0.25);
}

/* ============================================================
   Brand gradient - used for the + Create button and accent fills.
   ============================================================ */
.qyx-grad {
	background-image: linear-gradient(90deg, #ec4899 0%, #a855f7 45%, #38bdf8 100%);
}
.qyx-grad-soft {
	background-image: linear-gradient(135deg, rgba(168, 85, 247, 0.12), rgba(56, 189, 248, 0.10));
}
.qyx-grad-text {
	background-image: linear-gradient(90deg, #a855f7, #ec4899, #f97316);
	-webkit-background-clip: text; background-clip: text; color: transparent;
}
.qyx-grad-border > .qyx-grad-border__inner {
	background: white; border-radius: inherit;
}

/* ============================================================
   Sidebar - floating, blurred, soft right edge.
   ============================================================ */
.qyx-sidebar {
	background: rgba(255,255,255,0.75);
	backdrop-filter: saturate(140%) blur(14px);
	-webkit-backdrop-filter: saturate(140%) blur(14px);
	border-right: 1px solid rgba(226, 232, 240, 0.6);
}
.qyx-sidebar-scroll { scrollbar-width: thin; scrollbar-color: #e2e8f0 transparent; }
.qyx-sidebar-scroll::-webkit-scrollbar { width: 4px; }
.qyx-sidebar-scroll::-webkit-scrollbar-thumb { background: #e2e8f0; border-radius: 9999px; }

.qyx-nav-label {
	font-size: 10px; line-height: 1.15; letter-spacing: 0.01em; text-align: center;
	display: -webkit-box; -webkit-line-clamp: 2; -webkit-box-orient: vertical; overflow: hidden;
}

.qyx-nav-item { position: relative; transition: background-color .25s ease, color .25s ease; }
.qyx-nav-item.is-active {
	background: linear-gradient(180deg, rgba(168, 85, 247, 0.12), rgba(56, 189, 248, 0.08));
	color: #0f172a;
}
.qyx-nav-item.is-active::before {
	content: ""; position: absolute; left: -2px; top: 12px; bottom: 12px; width: 3px;
	border-radius: 9999px;
	background: linear-gradient(180deg, #a855f7, #38bdf8);
}

/* ============================================================
   Top navbar - sticky, transparent, blurred.
   ============================================================ */
.qyx-navbar {
	background: rgba(248, 250, 252, 0.65);
	backdrop-filter: saturate(140%) blur(14px);
	-webkit-backdrop-filter: saturate(140%) blur(14px);
	border-bottom: 1px solid rgba(226, 232, 240, 0.6);
}

/* ============================================================
   AI search bar - large, floating, soft shadow.
   ============================================================ */
.qyx-search {
	background: rgba(255,255,255,0.92);
	backdrop-filter: blur(10px);
	-webkit-backdrop-filter: blur(10px);
	border: 1px solid rgba(226, 232, 240, 0.9);
	box-shadow: 0 24px 60px -20px rgba(168, 85, 247, 0.25),
	            0 8px 24px -12px rgba(56, 189, 248, 0.15);
	border-radius: 9999px;
}

/* ============================================================
   Status pulse for "Live" campaigns.
   ============================================================ */
.qyx-pulse { position: relative; }
.qyx-pulse::after {
	content: ""; position: absolute; inset: -2px; border-radius: inherit;
	box-shadow: 0 0 0 0 rgba(16, 185, 129, 0.4);
	animation: qyxPulse 2s ease-out infinite;
}
@keyframes qyxPulse {
	0%   { box-shadow: 0 0 0 0   rgba(16, 185, 129, 0.45); }
	70%  { box-shadow: 0 0 0 10px rgba(16, 185, 129, 0); }
	100% { box-shadow: 0 0 0 0   rgba(16, 185, 129, 0); }
}

/* ============================================================
   Floating assistant FAB (mobile / always-on).
   ============================================================ */
.qyx-fab {
	background-image: linear-gradient(135deg, #a855f7 0%, #ec4899 60%, #38bdf8 120%);
	box-shadow: 0 14px 40px -10px rgba(168, 85, 247, 0.55);
}

/* ============================================================
   Tone gradients (assist Tailwind utility coverage at runtime).
   We list all dynamic Tailwind class roots so the CDN keeps them.
   ============================================================ */
/*! tailwind-keep
   from-violet-500/15 from-sky-500/15 from-emerald-500/15 from-amber-500/15
   from-rose-500/15 from-indigo-500/15 from-teal-500/15 from-fuchsia-500/15
   from-blue-500/15 to-fuchsia-500/0 to-cyan-500/0 to-teal-500/0 to-orange-500/0
   to-pink-500/0 to-violet-500/0 to-emerald-500/0 to-indigo-500/0
   bg-violet-100 text-violet-600 bg-sky-100 text-sky-600 bg-emerald-100 text-emerald-600
   bg-amber-100 text-amber-600 bg-rose-100 text-rose-600 bg-indigo-100 text-indigo-600
   bg-teal-100 text-teal-600 bg-fuchsia-100 text-fuchsia-600 bg-blue-100 text-blue-600 */

/* ============================================================
   Focus rings - soft.
   ============================================================ */
:where(button, a, input, [role="button"]):focus-visible {
	outline: 2px solid rgba(168, 85, 247, 0.45);
	outline-offset: 2px;
	border-radius: 12px;
}

/* ============================================================
   SITE HEADER - floating island navigation.
   The <header> itself is a position:fixed wrapper. The visible pill is
   the inner .qyx-island; .is-scrolled (added by JS at scrollY > 50) bumps
   shadow + opacity for a subtle "lift" effect.
   ============================================================ */

.site-header { background: transparent; }

/* Defensive - kill any stray border-top / outline on elements directly after the
   header that could render as a 1px line on mobile (some browser stylesheets or
   third-party scripts inject these). */
.site-header,
.site-header-nav,
.site-header + svg,
.site-header ~ main,
.site-header ~ main > section:first-child,
.site-section {
	border: 0 !important;
	outline: 0 !important;
}
.site-header-nav::after,
.site-header-nav::before { display: none !important; }

/* Safety net - if GSAP ScrollTrigger ever runs and creates .pin-spacer wrappers,
   make sure they don't render any visible boundary. */
.pin-spacer { border: 0 !important; box-shadow: none !important; background: transparent !important; }

.qyx-island {
	background: rgba(255, 255, 255, 0.82);
	-webkit-backdrop-filter: saturate(180%) blur(18px);
	backdrop-filter: saturate(180%) blur(18px);
	box-shadow:
		0 1px 0 rgba(255, 255, 255, 0.6) inset,
		0 8px 24px -10px rgba(15, 23, 42, 0.12),
		0 2px 6px -2px rgba(15, 23, 42, 0.06);
	border: 1px solid rgba(15, 23, 42, 0.06);
	transition: background-color 0.3s ease, box-shadow 0.3s ease, transform 0.3s ease;
}
.site-header.is-scrolled .qyx-island {
	background: rgba(255, 255, 255, 0.92);
	box-shadow:
		0 1px 0 rgba(255, 255, 255, 0.7) inset,
		0 14px 36px -12px rgba(15, 23, 42, 0.18),
		0 4px 10px -4px rgba(15, 23, 42, 0.08);
	transform: translateY(0);
}

/* Nav link underline (gradient, slides in on hover). */
.nav-link::after {
	content: "";
	position: absolute;
	left: 0;
	right: 0;
	bottom: 4px;
	height: 2px;
	border-radius: 9999px;
	background-image: linear-gradient(90deg, #7c3aed, #ec4899);
	transform: scaleX(0);
	transform-origin: left;
	transition: transform 0.3s ease;
}
.nav-link:hover::after,
.nav-link:focus-visible::after { transform: scaleX(1); }

/* Primary CTA - gradient with hover lift. Used in the floating header pill
   ("Join Hub") and other secondary spots. */
.btn-primary {
	background-image: linear-gradient(135deg, #7c3aed 0%, #ec4899 100%);
	box-shadow: 0 6px 18px -6px rgba(124, 58, 237, 0.45);
	transition: transform 0.25s ease, box-shadow 0.25s ease, filter 0.25s ease;
}
.btn-primary:hover {
	transform: translateY(-2px);
	box-shadow: 0 10px 24px -6px rgba(124, 58, 237, 0.55);
	filter: brightness(1.04);
}
.btn-primary:active { transform: translateY(0); }

/* Rainbow CTA - dark pill with a blurred rainbow halo behind. Used by the
   primary hero button. The ::before halo sits OUTSIDE the button (inset:-3px)
   and intensifies on hover, so we deliberately avoid overflow: hidden. */
.btn-rainbow {
	position: relative;
	z-index: 0;
	background: linear-gradient(135deg, #1a1a1a 0%, #2d2d2d 100%);
	color: #fff;
	transition: transform 0.25s ease, box-shadow 0.25s ease;
	box-shadow: 0 6px 18px -6px rgba(15, 23, 42, 0.45);
}
.btn-rainbow::before {
	content: "";
	position: absolute;
	inset: -3px;
	border-radius: inherit;
	z-index: -1;
	background: linear-gradient(135deg, #7c3aed 0%, #ec4899 33%, #f59e0b 66%, #10b981 100%);
	opacity: 0.7;
	filter: blur(12px);
	transition: opacity 0.3s ease, filter 0.3s ease;
}
.btn-rainbow:hover {
	transform: translateY(-2px);
	box-shadow: 0 10px 24px -8px rgba(15, 23, 42, 0.55);
}
.btn-rainbow:hover::before {
	opacity: 1;
	filter: blur(16px);
}
.btn-rainbow:active { transform: translateY(0); }

/* Hamburger button - three lines that morph to an X. */
.burger__lines {
	position: relative;
	display: inline-block;
	width: 22px;
	height: 16px;
}
.burger__line {
	position: absolute;
	left: 0;
	width: 100%;
	height: 2px;
	border-radius: 2px;
	background: #0f172a;
	transition: transform 0.3s ease, opacity 0.2s ease, top 0.3s ease;
}
.burger__line:nth-child(1) { top: 0; }
.burger__line:nth-child(2) { top: 7px; }
.burger__line:nth-child(3) { top: 14px; }

.burger.is-open .burger__line:nth-child(1) { top: 7px; transform: rotate(45deg); }
.burger.is-open .burger__line:nth-child(2) { opacity: 0; }
.burger.is-open .burger__line:nth-child(3) { top: 7px; transform: rotate(-45deg); }

/* Mobile panel scrollbar tidy. */
.mobile-panel { scrollbar-width: thin; scrollbar-color: #e2e8f0 transparent; }

/* Respect reduced motion. */
@media (prefers-reduced-motion: reduce) {
	.btn-primary,
	.nav-link::after,
	.burger__line,
	.qyx-island { transition: none; }
}

/* ============================================================
   HERO - aurora orbs, noise, gradient text shift, typewriter, tilt.
   ============================================================ */

/* Aurora container */
.qyx-aurora {
	position: absolute;
	inset: 0;
	overflow: hidden;
	pointer-events: none;
	z-index: 0;
}
.qyx-aurora__orb {
	position: absolute;
	border-radius: 9999px;
	filter: blur(90px);
	will-change: transform;
}
.qyx-aurora__orb--1 {
	width: 520px; height: 520px;
	background: radial-gradient(closest-side, rgba(124, 58, 237, 0.65), transparent 70%);
	top: -120px; left: -100px;
	opacity: 0.85;
	animation: qyx-drift-1 22s ease-in-out infinite alternate;
}
.qyx-aurora__orb--2 {
	width: 560px; height: 560px;
	background: radial-gradient(closest-side, rgba(236, 72, 153, 0.55), transparent 70%);
	top: 40px; right: -160px;
	opacity: 0.8;
	animation: qyx-drift-2 24s ease-in-out infinite alternate;
}
.qyx-aurora__orb--3 {
	width: 480px; height: 480px;
	background: radial-gradient(closest-side, rgba(34, 211, 238, 0.45), transparent 70%);
	bottom: -120px; left: 35%;
	opacity: 0.7;
	animation: qyx-drift-3 18s ease-in-out infinite alternate;
}
.qyx-aurora__orb--4 {
	width: 420px; height: 420px;
	background: radial-gradient(closest-side, rgba(16, 185, 129, 0.40), transparent 70%);
	top: 30%; right: 18%;
	opacity: 0.65;
	animation: qyx-drift-4 26s ease-in-out infinite alternate;
}
@keyframes qyx-drift-1 {
	from { transform: translate3d(0, 0, 0) scale(1); }
	to   { transform: translate3d(140px, 90px, 0) scale(1.15); }
}
@keyframes qyx-drift-2 {
	from { transform: translate3d(0, 0, 0) scale(1.05); }
	to   { transform: translate3d(-110px, 140px, 0) scale(0.95); }
}
@keyframes qyx-drift-3 {
	from { transform: translate3d(0, 0, 0) scale(1); }
	to   { transform: translate3d(90px, -110px, 0) scale(1.10); }
}
@keyframes qyx-drift-4 {
	from { transform: translate3d(0, 0, 0) scale(0.95); }
	to   { transform: translate3d(-130px, -70px, 0) scale(1.10); }
}

/* SVG noise grain - inline data URI, very subtle */
.qyx-noise {
	position: absolute;
	inset: 0;
	pointer-events: none;
	z-index: 1;
	opacity: 0.05;
	mix-blend-mode: overlay;
	background-image: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='200' height='200' viewBox='0 0 200 200'><filter id='n'><feTurbulence type='fractalNoise' baseFrequency='0.9' numOctaves='3' stitchTiles='stitch'/></filter><rect width='100%25' height='100%25' filter='url(%23n)'/></svg>");
}

/* Animated gradient text - pink → orange (matches hero "autopilot" word) */
.qyx-grad-text-shift {
	background-image: linear-gradient(90deg, #ec4899 0%, #f59e0b 50%, #ec4899 100%);
	background-size: 200% 100%;
	-webkit-background-clip: text;
	background-clip: text;
	color: transparent;
	animation: qyx-grad-shift 8s ease-in-out infinite;
}
@keyframes qyx-grad-shift {
	0%   { background-position: 0% 50%; }
	50%  { background-position: 100% 50%; }
	100% { background-position: 0% 50%; }
}

/* Typewriter - placeholder reserves width, words stack absolute, opacity-fade */
.qyx-typewriter {
	position: relative;
	display: inline-block;
	vertical-align: baseline;
}
.qyx-typewriter__placeholder {
	visibility: hidden;
	display: inline-block;
}
.qyx-typewriter__word {
	position: absolute;
	left: 0;
	top: 0;
	white-space: nowrap;
	opacity: 0;
	transform: translateY(14px);
	transition: opacity 0.55s ease, transform 0.55s ease;
	pointer-events: none;
}
.qyx-typewriter__word.is-active {
	opacity: 1;
	transform: translateY(0);
	pointer-events: auto;
}

/* 3D-tilt - perspective parent + transformed card.
   Default values give a subtle "resting" tilt (rotateY -5deg, rotateX 2deg)
   that matches the magicproject-style phone presentation. JS overrides via
   inline style on pointermove; pointerleave clears inline → CSS default
   resumes (so the phone always sits in a flattering 3D pose). */
.qyx-tilt {
	perspective: 1400px;
}
.qyx-tilt__card {
	--rx: 2deg;
	--ry: -5deg;
	transform: rotateX(var(--rx)) rotateY(var(--ry)) translateZ(0);
	transform-style: preserve-3d;
	transition: transform 0.6s cubic-bezier(0.22, 1, 0.36, 1);
	will-change: transform;
}
.qyx-tilt.is-active .qyx-tilt__card {
	transition: transform 0.1s linear;
}

/* ============================================================
   HERO BACKGROUND - radial gradient ellipses + bottom wave.
   ============================================================ */
.qyx-hero-bg {
	position: absolute;
	inset: 0;
	z-index: 0;
	pointer-events: none;
	background:
		radial-gradient(ellipse 80% 50% at 50% -10%, rgba(139, 92, 246, 0.18), transparent 70%),
		radial-gradient(ellipse 60% 50% at 85% 45%, rgba(236, 72, 153, 0.15), transparent 70%),
		radial-gradient(ellipse 60% 50% at 15% 80%, rgba(59, 130, 246, 0.15), transparent 70%);
}
.qyx-hero-bg::after {
	content: "";
	position: absolute;
	left: 0;
	right: 0;
	bottom: 0;
	height: 55%;
	pointer-events: none;
	opacity: 0.55;
	background-repeat: no-repeat;
	background-position: bottom center;
	background-size: cover;
	background-image: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 1440 320' preserveAspectRatio='none'><path fill='%23a5b4fc' fill-opacity='0.18' d='M0,224 C240,288 480,288 720,224 C960,160 1200,160 1440,224 L1440,320 L0,320 Z'/><path fill='%23f9a8d4' fill-opacity='0.16' d='M0,256 C240,192 480,192 720,256 C960,320 1200,320 1440,256 L1440,320 L0,320 Z'/></svg>");
}

/* ============================================================
   PHONE MOCKUP - realistic iPhone built entirely in CSS/HTML.
   Outer frame uses gradient + dual ring + multi-layer drop shadow
   to mimic anodised aluminium edge.
   ============================================================ */
.qyx-phone {
	position: relative;
	width: 290px;
	height: 600px;
	border-radius: 48px;
	padding: 12px;
	background: linear-gradient(145deg, #1c1c1e 0%, #2c2c2e 100%);
	box-shadow:
		inset 0 1px 0 rgba(255, 255, 255, 0.10),
		0 0 0 2px #2c2c2e,
		0 36px 64px -20px rgba(15, 23, 42, 0.55),
		0 20px 40px -12px rgba(15, 23, 42, 0.35);
}
@media (min-width: 640px) {
	.qyx-phone { width: 320px; height: 650px; border-radius: 50px; }
}
.qyx-phone__notch {
	position: absolute;
	top: 18px;
	left: 50%;
	transform: translateX(-50%);
	width: 110px;
	height: 30px;
	background: #000;
	border-radius: 9999px;
	z-index: 2;
}
@media (min-width: 640px) {
	.qyx-phone__notch { width: 120px; height: 34px; }
}
.qyx-phone__screen {
	position: relative;
	width: 100%;
	height: 100%;
	border-radius: 38px;
	background: #ffffff;
	overflow: hidden;
	display: flex;
	flex-direction: column;
}
@media (min-width: 640px) {
	.qyx-phone__screen { border-radius: 40px; }
}

/* Soft coloured reflection / glow under the phone */
.qyx-phone-reflection {
	position: absolute;
	left: 50%;
	bottom: -50px;
	transform: translateX(-50%);
	width: 75%;
	height: 110px;
	border-radius: 50%;
	filter: blur(34px);
	background: radial-gradient(
		ellipse at center,
		rgba(124, 58, 237, 0.30) 0%,
		rgba(236, 72, 153, 0.20) 40%,
		transparent 72%
	);
	z-index: -1;
	pointer-events: none;
}
.qyx-phone__chat {
	background-color: #ECE5DD;
	background-image:
		radial-gradient(circle at 1px 1px, rgba(15, 23, 42, 0.04) 1px, transparent 0);
	background-size: 14px 14px;
}

/* Chat bubbles */
.qyx-bubble {
	max-width: 80%;
	padding: 7px 10px;
	font-size: 12px;
	line-height: 1.35;
	border-radius: 14px;
	box-shadow: 0 1px 1px rgba(15, 23, 42, 0.06);
	color: #1e293b;
}
.qyx-bubble--in {
	background: #ffffff;
	border-top-left-radius: 4px;
	margin-right: auto;
}
.qyx-bubble--out {
	background: #DCF8C6;
	border-top-right-radius: 4px;
	margin-left: auto;
}
.qyx-bubble--typing {
	display: inline-flex;
	gap: 4px;
	padding: 10px 12px;
	width: max-content;
}
.qyx-bubble--typing span {
	width: 6px;
	height: 6px;
	border-radius: 9999px;
	background: #94a3b8;
	animation: qyx-typing 1.2s ease-in-out infinite;
}
.qyx-bubble--typing span:nth-child(2) { animation-delay: 0.15s; }
.qyx-bubble--typing span:nth-child(3) { animation-delay: 0.30s; }
@keyframes qyx-typing {
	0%, 80%, 100% { transform: translateY(0); opacity: 0.4; }
	40%           { transform: translateY(-4px); opacity: 1; }
}

/* ============================================================
   FLOATING ANIMATIONS - used by phone, chips, avatar, badges.
   ============================================================ */
@keyframes qyx-float {
	0%, 100% { transform: translateY(0); }
	50%      { transform: translateY(-14px); }
}
@keyframes qyx-float-slow {
	0%, 100% { transform: translateY(0) rotate(0deg); }
	50%      { transform: translateY(-20px) rotate(2deg); }
}
.qyx-float      { animation: qyx-float 3.4s ease-in-out infinite; will-change: transform; }
.qyx-float-slow { animation: qyx-float-slow 4.6s ease-in-out infinite; will-change: transform; }

/* Reduced motion - kill kinetic effects */
@media (prefers-reduced-motion: reduce) {
	.qyx-aurora__orb,
	.qyx-grad-text-shift,
	.qyx-float,
	.qyx-float-slow,
	.qyx-bubble--typing span { animation: none !important; }
	.qyx-tilt__card { transform: none !important; transition: none; }
	.qyx-typewriter__word { transition: none; }
}
