/**
 * Scroll Hero.
 *
 * The section is tall and the sticky inside it holds the top of the screen; that
 * is the whole of the pinning. The scene is a canvas behind the headline, the
 * captions are absolutely positioned and driven from inside the scene, and there
 * is one fallback for when none of it runs.
 *
 * @package Purplez\JMGWidgets
 */

.jmgw-hero {
	--jmgw-hero-run: 900vh;
	--jmgw-hero-line: #cf092c;
	--jmgw-hero-shape: #5c626b;
	--jmgw-hero-grid: #c9a5ae;
	--jmgw-hero-horizon: #e4dcde;
	--jmgw-hero-ink: #14090c;
	--jmgw-hero-quiet: #6b5b60;
	--jmgw-hero-body: #3c3236;

	position: relative;
	height: var( --jmgw-hero-run );

	/*
	 * Width, explicitly, and it is not redundant.
	 *
	 * In normal flow a block fills its parent and this would do nothing.
	 * Elementor v3 containers are flex, and a block child of a flex container
	 * does not stretch along the main axis — it sizes to its content. Every child
	 * here is out of flow, so the content measures zero wide and the section
	 * collapses to a 900vh strip of nothing while the script inside it runs
	 * perfectly.
	 *
	 * flex-shrink, not the `flex` shorthand: the shorthand sets flex-basis, and
	 * flex-basis applies to the MAIN axis — which in a flex column is the height.
	 * `flex: 1 1 100%` would therefore override the height above.
	 */
	width: 100%;
	min-width: 0;
	flex-shrink: 0;
}

/*
 * A longer run on a portrait screen. The same journey has to survive a frame
 * that shows far less of it at once.
 */
@media ( max-aspect-ratio: 1 / 1 ) {
	.jmgw-hero {
		height: calc( var( --jmgw-hero-run ) * 1.34 );
	}
}

.jmgw-hero__sticky {
	position: sticky;
	top: 0;
	height: 100vh;
	overflow: hidden;
}

/*
 * Every one of these is scoped under the section, and that is what makes them
 * apply at all.
 *
 * Elementor's Site Settings emit `.elementor-kit-N h1 { color: … }` and the same
 * for h2, h3 and p — one class and one type, which beats a bare one-class rule.
 * So the headline, the sub-headline and both halves of a caption took the site's
 * global text colour and the four colour controls in the panel did nothing at
 * all. Adding the parent takes each to two classes, which wins, without this
 * plugin ever naming an `.elementor-` class of its own.
 */
.jmgw-hero .jmgw-hero__title {
	position: relative;
	z-index: 1;
	margin: 0 auto;
	max-width: 960px;
	padding: 12vh 24px 0;
	font-size: clamp( 30px, 4.4vw, 60px );
	line-height: 1.04;
	font-weight: 600;
	text-align: center;
	text-wrap: balance;
	color: var( --jmgw-hero-ink );
}

.jmgw-hero .jmgw-hero__sub {
	display: block;
	margin-top: 14px;
	font-size: clamp( 15px, 1.5vw, 21px );
	font-weight: 300;
	letter-spacing: 0.01em;
	color: var( --jmgw-hero-quiet );
}

.jmgw-hero__scene {
	position: absolute;
	inset: 0;
}

/*
 * The canvas starts below the headline rather than at the top of the screen. The
 * scene renders its own horizon high inside that box, so the vanishing point
 * sits behind the words instead of running through them.
 */
.jmgw-hero__stage {
	position: absolute;
	top: 40%;
	right: 0;
	bottom: 0;
	left: 0;
	overflow: hidden;
}

.jmgw-hero__stage canvas {
	display: block;
}

/* --- the captions -------------------------------------------------------- */

.jmgw-hero__beat {
	position: absolute;
	left: 0;
	bottom: 100%;
	display: inline-block;
	box-sizing: content-box;

	/*
	 * Sized against the screen's height, because everything in this scene is —
	 * but bounded by its width as well. 68vh on a tall narrow phone is wider than
	 * the phone, so the card ran off the side with the sentence still going. On
	 * anything landscape the vh is the smaller of the two and nothing changes.
	 */
	width: min( 68vh, 86vw );
	height: 15vh;
	transform-origin: left bottom;
	will-change: transform;
}

.jmgw-hero__card {
	position: absolute;
	inset: 0;
	overflow: hidden;
	opacity: 0;
	background: hsla( 0, 0%, 100%, 0.6 );
	-webkit-backdrop-filter: blur( 1vh );
	backdrop-filter: blur( 1vh );
	border: 0.15vh solid #e4d7da;
	border-radius: 3vh;
	transition: opacity 0.4s ease-in-out;
}

.jmgw-hero__pad {
	position: absolute;
	left: 0;
	top: 0;
	width: 100%;
	padding: 2.4vh 3.2vh 2.4vh 3vh;
}

.jmgw-hero .jmgw-hero__name {
	margin: 0 0 0.7vh;
	font-size: min( 2.9vh, 5vw );
	font-weight: 600;
	letter-spacing: -0.01em;
	color: var( --jmgw-hero-ink );
}

.jmgw-hero .jmgw-hero__body {
	margin: 0;
	min-height: 6.3vh;
	font-size: min( 2.25vh, 3.9vw );
	font-weight: 300;
	line-height: 1.38;
	color: var( --jmgw-hero-body );
}

/* The source text: read by the script, and shown by anything that never runs it. */
.jmgw-hero__src {
	display: none;
}

/*
 * The caret. No blink animation — the flicker in a typewriter like this one is
 * the span being added and dropped on alternate frames, which is a bug rather
 * than a feature. It is drawn as a solid block and left alone.
 */
.jmgw-hero__body span {
	display: inline-block;
	font-weight: 700;
	margin-right: -10px;

	/*
	 * The caret is a letter painted its own background colour, which is how the
	 * prototype draws it — the block has to be the width of a character in the
	 * running font, and nothing else measures that for free.
	 */
	background: var( --jmgw-hero-line );
	color: var( --jmgw-hero-line );
}

/* --- the call to action --------------------------------------------------- */

.jmgw-hero__cta {
	position: absolute;
	left: 50%;
	top: 50%;
	display: flex;
	align-items: center;
	justify-content: center;
	width: 22vh;
	height: 7vh;

	/*
	 * Centred on its own position by transform, not by negative margins. The
	 * script writes left and top in pixels to put this exactly where the line
	 * ends, and a margin offset would shift it off that point by half its size.
	 * The 50%/50% below is only the resting place before the ending begins.
	 */
	margin: 0;
	transform: translate( -50%, -50% );
	opacity: 0;
	text-decoration: none;
	cursor: pointer;
}

.jmgw-hero__cta:not( .is-ready ) {
	pointer-events: none;
}

.jmgw-hero__pip {
	position: absolute;
	left: 50%;
	top: 50%;
	width: 2.4vh;
	height: 2.4vh;
	transform: translate( -50%, -50% );
	background: var( --jmgw-hero-line );
	border-radius: 1.2vh;
	box-shadow: 0 0 0 0 rgba( 207, 9, 44, 0.15 );
	transition: box-shadow 0.6s ease-in-out;
}

.jmgw-hero__pip.is-open {
	box-shadow: 0 0 0 0.85vh rgba( 207, 9, 44, 0.15 );
}

.jmgw-hero__cta.is-ready .jmgw-hero__pip {
	transition: box-shadow 0.2s ease-in-out;
}

.jmgw-hero__cta:hover .jmgw-hero__pip.is-open {
	box-shadow: 0 0 0 1.2vh rgba( 207, 9, 44, 0.15 );
}

.jmgw-hero__cta:active .jmgw-hero__pip.is-open {
	box-shadow: 0 0 0 0 rgba( 207, 9, 44, 0.15 );
	transition: box-shadow 0.1s ease-in-out;
}

/*
 * The label is styled by NAME, never as `.jmgw-hero__cta span`. That selector is
 * one class and one type, which out-specifies `.jmgw-hero__pip` — so it took the
 * pip's position away, turned it into a flex item at its inline 22vh width, and
 * shoved these words out of the button. The prototype never hit it because its
 * pip is a div; that distinction survives exactly until someone changes an
 * element name, so the rule here is names only.
 */
.jmgw-hero__label {
	position: relative;
	z-index: 2;
	opacity: 0;
	font-size: 2.1vh;
	font-weight: 300;
	white-space: nowrap;
	color: #fff;
	transition: opacity 0.1s ease-in-out;
}

.jmgw-hero__cta.is-ready .jmgw-hero__label {
	opacity: 1;
	transition: opacity 0.2s ease-in-out;
}

/* --- the furniture -------------------------------------------------------- */

.jmgw-hero__hint {
	position: absolute;
	left: 50%;
	bottom: 24px;
	transform: translateX( -50% );
	margin: 0;
	font-size: 10.5px;
	line-height: 1;
	font-weight: 600;
	letter-spacing: 0.24em;
	text-transform: uppercase;
	color: #9a8b8f;
	transition: opacity 0.5s ease;
}

.jmgw-hero__hint.is-gone {
	opacity: 0;
}

/* --- when it does not run -------------------------------------------------
 * Two ways in: the visitor asked for less movement, or WebGL is unavailable.
 * Both land on the same page — the headline and the three captions as ordinary
 * text, one after another. The words were always the payload.
 * ------------------------------------------------------------------------ */

.jmgw-hero--still {
	height: auto;
}

.jmgw-hero--still .jmgw-hero__sticky {
	position: static;
	height: auto;
	padding-bottom: 8vh;
}

.jmgw-hero--still .jmgw-hero__stage,
.jmgw-hero--still .jmgw-hero__hint {
	display: none;
}

.jmgw-hero--still .jmgw-hero__scene {
	position: static;
}

.jmgw-hero--still .jmgw-hero__beat {
	position: static;
	display: block;
	width: auto;
	height: auto;
	max-width: 820px;
	margin: 0 auto 26px;
	padding: 0 24px;
	opacity: 1;
	transform: none;
}

.jmgw-hero--still .jmgw-hero__card {
	position: static;
	opacity: 1;
	background: none;
	-webkit-backdrop-filter: none;
	backdrop-filter: none;
	border: 0;
	border-left: 3px solid var( --jmgw-hero-line );
	border-radius: 0;
}

.jmgw-hero--still .jmgw-hero__pad {
	position: static;
	width: auto;
	padding: 6px 0 6px 18px;
}

.jmgw-hero--still .jmgw-hero__name {
	margin-bottom: 6px;
	font-size: clamp( 18px, 2vw, 24px );
}

.jmgw-hero--still .jmgw-hero__body {
	display: none;
}

/*
 * The script never runs, so the body is never typed. The source text is what
 * there is, and it stops being the script's private copy.
 */
.jmgw-hero--still .jmgw-hero__src {
	display: block;
	margin: 0;
	font-size: clamp( 15px, 1.4vw, 19px );
	font-weight: 300;
	line-height: 1.45;
	color: var( --jmgw-hero-body );
}

.jmgw-hero--still .jmgw-hero__cta {
	position: static;
	transform: none;
	justify-content: flex-start;
	width: auto;
	max-width: 820px;
	height: auto;
	margin: 10px auto 0;
	padding: 0 24px;
	opacity: 1;
}

.jmgw-hero--still .jmgw-hero__pip {
	position: static;
	width: auto;
	height: auto;
	padding: 14px 26px;
	transform: none;
	border-radius: 4px;
	box-shadow: none;
}

.jmgw-hero--still .jmgw-hero__label {
	position: absolute;
	padding: 14px 26px;
	opacity: 1;
	font-size: 15px;
}
