/*
 * Signature graphique — le trait vertical (voir design-system-web-v1.md,
 * section "Signature graphique — le trait vertical").
 *
 * Le motif vient des lettres D et O du wordmark, tranchées par une fente
 * verticale nette. Deux déclinaisons génériques ci-dessous, réutilisables
 * partout dans le thème :
 *
 *   .dov-ring     — anneau fendu autour d'une photo ronde (portraits équipe,
 *                   et toute future photo ronde). L'anneau est un SVG (cercle
 *                   à deux ouvertures via stroke-dasharray) posé par-dessus
 *                   une photo normale, chargée via la médiathèque WordPress
 *                   comme n'importe quelle image — pas de fichier composité
 *                   à refaire à chaque nouvelle photo.
 *   .dov-divider  — la même fente appliquée à un simple trait vertical,
 *                   pour les contextes denses (en-tête, séparateurs,
 *                   bordures de carte) où un anneau serait disproportionné.
 *
 *   .dov-hero-marks — repères de mesure (coins de cadrage + règle graduée +
 *                   coordonnées), pour l'usage "grand format photo" du
 *                   même principe (voir exemple Hero, design-system-web-v1.md) :
 *                   pas la fente D/O elle-même, mais le même vocabulaire
 *                   d'instrument de précision, en évidence sur le hero.
 *
 * Couleur et épaisseur pilotées par variables CSS pour rester alignées sur
 * theme.json sans dupliquer les couleurs ici.
 */

:root {
	--dov-accent-color: var(--wp--preset--color--teal);
	/* Piste B — Précision Numérique (nuancier 2026, provisoire) : réservée
	   aux petites touches "instrument technique", ex. le soulignement du
	   menu ci-dessous. Voir design-system-web-v1.md, Nuanciers 2026. */
	--dov-accent-color-b: var(--wp--preset--color--cyan-technique);
}

/* --- Anneau fendu (portraits) ------------------------------------------ */

.dov-ring {
	position: relative;
	display: inline-block;
	width: var(--dov-ring-size, 140px);
	height: var(--dov-ring-size, 140px);
}

.dov-ring img {
	position: absolute;
	top: 50%;
	left: 50%;
	transform: translate(-50%, -50%);
	width: 64%;
	height: 64%;
	object-fit: cover;
	border-radius: 50%;
	display: block;
}

.dov-ring svg {
	position: absolute;
	inset: 0;
	width: 100%;
	height: 100%;
	overflow: visible;
}

.dov-ring circle {
	fill: none;
	stroke: var(--dov-ring-color, var(--dov-accent-color));
	stroke-width: var(--dov-ring-width, 5.5);
}

/* --- Trait fendu (usages denses : en-tête, cartes) ---------------------- */

.dov-divider {
	display: block;
	width: var(--dov-divider-width, 2px);
	height: var(--dov-divider-height, 28px);
	align-self: center;
	background: linear-gradient(
		var(--dov-divider-color, var(--dov-accent-color)) 0,
		var(--dov-divider-color, var(--dov-accent-color)) 42%,
		transparent 42%,
		transparent 58%,
		var(--dov-divider-color, var(--dov-accent-color)) 58%,
		var(--dov-divider-color, var(--dov-accent-color)) 100%
	);
}

/* En-tête : le trait sert de séparateur entre le logo et le menu */
.dov-divider.is-header-divider {
	--dov-divider-height: 26px;
}

/* Cartes bénéfice (page d'accueil, section "Cinq raisons") : le trait
   remplace le bandeau horizontal utilisé initialement en haut de carte. */
.benefit-card {
	position: relative;
}

.benefit-card::before {
	content: "";
	position: absolute;
	left: -1px;
	top: 50%;
	transform: translateY(-50%);
	width: 3px;
	height: 64%;
	border-radius: 2px;
	background: linear-gradient(
		var(--dov-accent-color) 0,
		var(--dov-accent-color) 44%,
		transparent 44%,
		transparent 56%,
		var(--dov-accent-color) 56%,
		var(--dov-accent-color) 100%
	);
}

/* --- Surtitres : filet vertical fendu avant le label --------------------
   Retouche du 10.09.2026 (analyse "Extensions signature D/O") : chaque
   surtitre en capitales (PRESTATION, SECTEUR, L'ÉQUIPE...) reçoit la même
   fente que le logo et l'en-tête, mais à la verticale plutôt qu'en tiret
   horizontal — on garde la verticalité de la signature plutôt que d'en
   faire un élément décoratif indépendant. currentColor reprend la couleur
   de texte déjà posée sur chaque surtitre (teal, teal-300, cyan-technique
   selon le fond), donc aucune variable de couleur à gérer ici.
   display:inline-block (plutôt que le bloc par défaut du <p>) : le filet
   doit coller au texte, y compris quand le surtitre est centré
   (has-text-align-center) — sinon il resterait plaqué à gauche du bloc
   pendant que le texte se centre ailleurs. */

.dov-kicker {
	position: relative;
	display: inline-block;
	padding-left: 13px;
}

.dov-kicker::before {
	content: "";
	position: absolute;
	left: 0;
	top: 50%;
	transform: translateY(-50%);
	width: 2px;
	height: 1.35em;
	background: linear-gradient(
		currentColor 0,
		currentColor 40%,
		transparent 40%,
		transparent 60%,
		currentColor 60%,
		currentColor 100%
	);
}

/* Fix : aligner le titre sur le TEXTE du surtitre, pas sur le trait fendu
   (10.09.2026). Le padding-left de .dov-kicker (13px) laisse la place au
   filet vertical mais décale d'autant le texte du surtitre par rapport au
   titre qui le suit, lequel n'a lui aucun décalage : les deux ne partagent
   plus le même bord gauche. On aligne le titre sur le texte du surtitre
   plutôt que l'inverse, pour garder le filet bien au bord réel du bloc.
   Ignoré si le surtitre est centré (.has-text-align-center) : dans ce cas
   le bloc est déjà centré comme un tout, ce décalage ne s'y pose pas. */
.dov-kicker:not(.has-text-align-center) + :is(h1, h2, h3, h4) {
	margin-left: 13px;
}

/* --- Cartes témoignage : accent fendu en bordure gauche ------------------
   Section "Ils nous font confiance" (page d'accueil). Même vocabulaire que
   .benefit-card ci-dessus, mais en cyan technique plutôt qu'en couleur
   d'accent, pour ne pas confondre les deux familles de carte au survol de
   l'œil. Positionné dans la marge intérieure existante (padding-left:24px
   posé en style inline par Gutenberg) plutôt que d'agrandir cette marge :
   pas besoin de !important, et le texte ne bouge pas. */

.dov-testimonial {
	position: relative;
	border: 1px solid #dde4e4;
	border-radius: 8px;
	margin-top: 48px;
	padding: 22px 24px;
}

.dov-testimonial::before {
	content: "";
	position: absolute;
	left: 10px;
	top: 14px;
	bottom: 14px;
	width: 3px;
	border-radius: 2px;
	background: linear-gradient(
		var(--dov-accent-color-b) 0,
		var(--dov-accent-color-b) 40%,
		transparent 40%,
		transparent 60%,
		var(--dov-accent-color-b) 60%,
		var(--dov-accent-color-b) 100%
	);
}

/* --- Bandeaux CTA : fil vertical entre le texte et le bouton -------------
   Bandeau teal plein (« Un projet de relevé numérique ? » et variantes,
   bas de page). Le bandeau porte déjà tout le poids visuel de la page
   (couleur pleine, gros bouton) : le fil reste volontairement quasi
   invisible (1px, opacité réduite) — une respiration qui a une forme,
   plutôt qu'un vrai accent. Repasse à zéro sous 680px : au flexWrap, le
   bouton tombe sur sa propre ligne et le fil n'aurait plus de sens entre
   les deux blocs. */

.dov-cta > .wp-block-buttons {
	position: relative;
	margin-left: 12px;
	padding-left: 24px;
}

.dov-cta > .wp-block-buttons::before {
	content: "";
	position: absolute;
	left: 0;
	top: 10%;
	bottom: 10%;
	width: 1px;
	background: linear-gradient(
		var(--dov-accent-color-b) 0,
		var(--dov-accent-color-b) 38%,
		transparent 38%,
		transparent 62%,
		var(--dov-accent-color-b) 62%,
		var(--dov-accent-color-b) 100%
	);
	opacity: 0.5;
}

@media (max-width: 680px) {
	.dov-cta > .wp-block-buttons {
		margin-left: 0;
		padding-left: 0;
	}
	.dov-cta > .wp-block-buttons::before {
		display: none;
	}
}

/* --- Filet de secours : largeur des sections "wide" ---------------------
 * Constat (10.09.2026) : sur new.3dvisions.ch, WordPress n'émet pas la
 * règle `.wp-site-blocks > .alignwide { max-width: ... }` qu'il génère
 * normalement à partir de theme.json (wideSize: 1200px) — seules les
 * règles alignleft/alignright/aligncenter du même groupe sont présentes.
 * add_theme_support('align-wide') et theme.json sont pourtant corrects ;
 * tout pointe vers un cache de styles globaux WordPress resté figé sur un
 * état antérieur du thème plutôt qu'un problème dans nos fichiers (une
 * simple re-sauvegarde dans Apparence → Éditeur → Styles devrait le
 * régénérer côté serveur). En attendant, on pose nous-mêmes la règle
 * manquante — elle correspond exactement à ce que WordPress est censé
 * produire, donc sans risque si le cache se corrige de son côté (les deux
 * règles seraient alors simplement identiques).
 *
 * Symptôme observé : toutes les sections "alignwide" (donc aussi les
 * surtitres qu'elles contiennent) s'étalaient bord à bord sur toute la
 * largeur de l'écran au lieu d'être centrées à 1200px — d'où l'impression
 * de surtitre "décalé" alors que c'est toute la section qui avait perdu
 * sa largeur normale.
 */

.wp-site-blocks > .alignwide {
	max-width: var(--wp--style--global--wide-size, 1200px);
	margin-left: auto;
	margin-right: auto;
}

/* --- Marge de sécurité horizontale (root padding) -----------------------
 * Constat (11.09.2026, retour mobile) : le thème n'active pas
 * `useRootPaddingAwareAlignments` dans theme.json et ne définit aucun
 * `styles.spacing.padding` — WordPress n'ajoute donc AUCUN padding gauche/
 * droite au conteneur du site. Sous la largeur "wide" (1200px, donc sur
 * tout mobile/tablette et même certaines fenêtres desktop), les sections
 * alignwide/alignfull font exactement la largeur de l'écran et leur texte
 * touche les bords — d'où l'absence de marge à droite constatée sur
 * téléphone.
 *
 * On reproduit ici le comportement root-padding-aware standard de
 * WordPress : une marge de sécurité posée sur .wp-site-blocks, neutralisée
 * par une marge négative équivalente sur les blocs alignfull (qui doivent
 * au contraire aller bord à bord), puis réappliquée en padding sur ces
 * mêmes blocs alignfull pour que LEUR contenu garde la même marge que le
 * reste du site — qu'il s'agisse d'un wp:group ou d'un wp:cover (hero).
 */

.wp-site-blocks {
	padding-left: 20px;
	padding-right: 20px;
}

.wp-site-blocks > .alignfull {
	margin-left: -20px;
	margin-right: -20px;
	padding-left: 20px;
	padding-right: 20px;
}

/* --- Boutons : la fente en mouvement ------------------------------------
 * Système de boutons interactifs qui porte la signature D/O jusque dans
 * l'interaction (survol + clic), documenté dans design-system-web-v1.md
 * (artboard "Boutons — la fente en mouvement", 10.09.2026) et exploré
 * dans l'artifact "La fente en mouvement".
 *
 * Un seul socle partagé (.dov-btn__curtain + .dov-btn__edge) : un rideau
 * se ferme d'un bord à l'autre au survol, jamais depuis le centre, porté
 * par une arête cyan qui le précède. Les trois variantes ne diffèrent que
 * par un détail secondaire — jamais par la mécanique de remplissage.
 *
 *   .dov-btn--obturateur — bouton primaire (teal), se soulève au survol.
 *   .dov-btn--volet       — bouton secondaire (stone/blanc), sans fioriture.
 *   .dov-btn--contour     — bouton fantôme (outline), un tick remplace
 *                            la flèche et s'étire au survol.
 *
 * Appliqué directement sur les liens .wp-block-button__link existants,
 * en plus de leurs classes de couleur d'origine (has-teal-background-color,
 * etc.) — celles-ci restent pour la compatibilité éditeur, .dov-btn
 * prend le dessus sur l'apparence visuelle.
 */

.dov-btn {
	position: relative;
	isolation: isolate;
	display: inline-flex;
	align-items: center;
	gap: 10px;
	overflow: hidden;
	border-radius: 4px;
	padding: 15px 32px;
	font-size: 0.8125rem;
	font-weight: 600;
	text-transform: uppercase;
	letter-spacing: 0.06em;
	text-decoration: none;
	-webkit-tap-highlight-color: transparent;
}

.dov-btn:focus-visible {
	outline: 2px solid var(--dov-accent-color-b);
	outline-offset: 3px;
}

.dov-btn__label {
	position: relative;
	z-index: 2;
}

.dov-btn__curtain {
	position: absolute;
	z-index: 1;
	inset: 0;
	clip-path: inset(0 100% 0 0);
	transition: clip-path 0.4s cubic-bezier(0.65, 0, 0.35, 1);
}

.dov-btn:hover .dov-btn__curtain {
	clip-path: inset(0 0 0 0);
}

.dov-btn__edge {
	position: absolute;
	z-index: 2;
	top: 0;
	bottom: 0;
	left: 0;
	width: 3px;
	background: var(--dov-accent-color-b);
	opacity: 0;
	box-shadow: 0 0 9px 1px var(--dov-accent-color-b);
	transition: left 0.4s cubic-bezier(0.65, 0, 0.35, 1), opacity 0.12s ease;
}

.dov-btn:hover .dov-btn__edge {
	left: calc(100% - 3px);
	opacity: 1;
}

.dov-btn.is-confirming .dov-btn__edge {
	box-shadow: 0 0 16px 3px var(--dov-accent-color-b);
}

/* 01 — Obturateur (primaire) */

.dov-btn--obturateur {
	background: var(--wp--preset--color--teal);
	color: var(--wp--preset--color--white);
	box-shadow: 0 1px 2px rgba(11, 55, 67, 0.18);
	transition: transform 0.2s ease, box-shadow 0.3s ease;
}

.dov-btn--obturateur .dov-btn__curtain {
	background: var(--wp--preset--color--teal-900);
}

.dov-btn--obturateur:hover {
	transform: translateY(-3px);
	box-shadow: 0 14px 24px rgba(11, 55, 67, 0.28);
	/* !important : WordPress ajoute déjà !important à .has-white-color
	   (classe générée depuis theme.json) — sans ça, cette règle perd
	   systématiquement face à elle. */
	color: var(--wp--preset--color--white) !important;
}

.dov-btn--obturateur:active {
	transform: translateY(-1px) scale(0.97);
	transition-duration: 0.08s;
}

/* 02 — Volet (secondaire) */

.dov-btn--volet {
	transition: color 0.34s ease 0.1s, transform 0.2s ease;
}

.dov-btn--volet .dov-btn__curtain {
	background: var(--wp--preset--color--teal-900);
}

.dov-btn--volet:hover {
	/* !important : idem — .has-teal-900-color / .has-ink-color sont
	   générées par WordPress avec !important, elles gardaient sinon la
	   main sur la couleur de texte pendant que le rideau sombre balaie
	   par-dessous, rendant le texte illisible au survol. */
	color: var(--wp--preset--color--white) !important;
}

.dov-btn--volet:active {
	transform: scale(0.97);
	transition-duration: 0.08s;
}

/* 03 — Rideau (fantôme / outline) */

.dov-btn--contour {
	background: transparent;
	border: 1.5px solid currentColor;
	padding: 13.5px 30.5px;
	transition: color 0.36s ease 0.1s, transform 0.2s ease;
}

.dov-btn--contour .dov-btn__curtain {
	background: var(--wp--preset--color--white);
}

.dov-btn--contour:hover {
	/* !important : idem — .has-white-color (générée par WordPress avec
	   !important) gardait sinon la main, texte blanc sur rideau blanc
	   au survol. */
	color: var(--wp--preset--color--teal-900) !important;
}

.dov-btn--contour:active {
	transform: scale(0.97);
	transition-duration: 0.08s;
}

.dov-btn__tick {
	position: relative;
	z-index: 2;
	width: 10px;
	height: 2px;
	background: currentColor;
	transition: width 0.3s cubic-bezier(0.34, 1.56, 0.64, 1),
		transform 0.3s cubic-bezier(0.34, 1.56, 0.64, 1), background 0.2s ease;
}

.dov-btn--contour:hover .dov-btn__tick {
	width: 18px;
	transform: translateX(3px);
	background: var(--wp--preset--color--teal-500);
}

.dov-btn--contour.is-confirming .dov-btn__tick {
	width: 22px;
	transform: translateX(3px) scaleY(1.6);
	background: var(--dov-accent-color-b);
}

/* --- Repères de mesure (hero) -------------------------------------------
   Reprend fidèlement l'exemple "Hero" de l'artboard Signature graphique du
   design system (design-system-web-v1.md) : une ligne verticale fine posée
   sur la photo, avec une graduation discrète et une coordonnée réelle — le
   même principe de fente nette que le D/O du logo, décliné en instrument de
   mesure plutôt qu'en décor abstrait (coins de viseur + règle horizontale,
   première tentative du 10.09, qui perdait cet effet de ligne verticale).
   Le hero WordPress centre son bloc de texte (contentSize 600px) : les deux
   lignes encadrent donc ce bloc de façon symétrique plutôt que de longer un
   bord, pour rester cohérentes quelle que soit la largeur d'écran. */

.dov-hero-marks {
	position: absolute;
	inset: 0;
	pointer-events: none;
	color: var(--dov-hero-marks-color, #ffffff);
	/* Le bloc Cover de WordPress pose son overlay de fond
	   (.wp-block-cover__background) en z-index:1 : sans z-index
	   explicite ici (auto), cet overlay passe devant nos repères
	   malgré un ordre DOM ultérieur. On passe donc au-dessus. */
	z-index: 2;
}

.dov-hero-line {
	position: absolute;
	top: 0;
	bottom: 0;
	width: 1px;
	background: currentColor;
}

/* Bloc de texte du hero : contentSize 600px, centré. On encadre ce bloc de
   part et d'autre, avec une marge de respiration. */
.dov-hero-line.is-primary {
	left: calc(50% - 336px);
	opacity: 0.5;
}

.dov-hero-line.is-secondary {
	left: calc(50% + 336px);
	opacity: 0.28;
}

.dov-hero-tick {
	position: absolute;
	left: -9px;
	width: 18px;
	height: 1px;
	background: currentColor;
}

.dov-hero-tick.is-top {
	top: 40px;
}

.dov-hero-tick.is-bottom {
	bottom: 48px;
}

.dov-coord {
	position: absolute;
	top: 40px;
	left: calc(50% - 336px + 14px);
	font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
	font-size: 13px;
	font-weight: 600;
	letter-spacing: 0.06em;
	opacity: 0.85;
	text-shadow: 0 1px 3px rgba(0, 0, 0, 0.4);
	white-space: nowrap;
}

/* En dessous de 900px, le bloc de texte peut approcher la pleine largeur :
   les lignes symétriques ne tiendraient plus. On repasse sur une seule
   ligne, calée à gauche façon marge de page plutôt qu'encadrement. */
@media (max-width: 900px) {
	.dov-hero-line.is-secondary {
		display: none;
	}
	.dov-hero-line.is-primary {
		left: 24px;
	}
	.dov-coord {
		left: 44px;
		top: 24px;
	}
}

/* Hero bas et texte sur plusieurs lignes en mobile : le motif devient plus
   gênant que lisible, on le retire proprement. */
@media (max-width: 560px) {
	.dov-hero-marks {
		display: none;
	}
}


/* --- Navigation principale : capitales fines, soulignement fendu --------
   Retouche du 10.09.2026, demande de Marc : lettres capitales, graisse un
   peu plus fine qu'avant (600 → 500), et un filet de soulignement qui
   reprend la fente D/O du logo plutôt qu'un simple trait plein — même
   technique que .dov-divider (linear-gradient avec une coupure au milieu),
   appliquée à l'horizontale. Couleur du filet : piste B (cyan technique),
   comme touche "instrument de précision" plutôt que la couleur d'accent
   habituelle — discret sur fond blanc puisqu'il n'apparaît qu'au survol. */

.dov-nav-link {
	position: relative;
	color: inherit;
	/* Le soulignement par défaut du navigateur suit la ligne de base du
	   texte, qui se décale légèrement sur les liens avec caret (celui-ci est
	   en inline-block) : on ne garde que le filet fendu ::after ci-dessous,
	   positionné par rapport à la boîte du lien et donc toujours aligné. */
	text-decoration: none;
	transition: color 0.2s ease;
}

.dov-nav-link:hover,
.dov-nav-link:focus-visible {
	color: var(--dov-accent-color);
}

.dov-nav-link::after {
	content: "";
	position: absolute;
	left: 0;
	right: 0;
	bottom: -6px;
	height: 2px;
	background: linear-gradient(
		to right,
		var(--dov-accent-color-b) 0,
		var(--dov-accent-color-b) 42%,
		transparent 42%,
		transparent 58%,
		var(--dov-accent-color-b) 58%,
		var(--dov-accent-color-b) 100%
	);
	transform: scaleX(0);
	transform-origin: left;
	transition: transform 0.25s ease;
}

.dov-nav-link:hover::after,
.dov-nav-link:focus-visible::after {
	transform: scaleX(1);
}

/* --- Sous-menus (Prestations / Secteurs) --------------------------------
   Ajouté le 10.09.2026 à la demande de Marc, une fois les 4 pages Prestation
   et 3 pages Secteur en place. CSS pur (:hover / :focus-within), pas de JS —
   cohérent avec le reste du thème (page-level template files, pas d'app
   côté client). L'accent vertical fendu sur chaque lien de sous-menu reprend
   la même technique que .benefit-card::before, à plus petite échelle. */

.dov-nav-item {
	position: relative;
	display: inline-flex;
	align-items: center;
	/* Comble l'espace entre le lien et le panneau (la zone de survol reste
	   continue, le sous-menu ne se ferme pas quand la souris descend) —
	   en haut ET en bas à parts égales : un padding asymétrique (bas
	   seulement, version initiale) décale le item hors de l'alignement
	   flex de la ligne de menu par rapport aux liens simples (Accueil,
	   Réalisations...), qui eux n'ont pas ce padding. Repéré en comparant
	   la position réelle du texte avec/sans ce correctif sur le site en
	   direct : symétrique, le texte retombe pile sur la même ligne de
	   base que les autres liens. */
	padding-top: 14px;
	padding-bottom: 14px;
	margin-top: -14px;
	margin-bottom: -14px;
}

/* Triangle en CSS pur (bordures) plutôt que le caractère unicode ▾ :
   à 9px, ce glyphe rend comme un petit point flou selon la police système
   (repéré en vérifiant en direct sur new.3dvisions.ch) — un triangle en
   bordures reste net à n'importe quelle taille et sur n'importe quel OS. */
.dov-nav-caret {
	display: inline-block;
	margin-left: 7px;
	width: 0;
	height: 0;
	border-left: 4.5px solid transparent;
	border-right: 4.5px solid transparent;
	border-top: 6px solid currentColor;
	opacity: 0.85;
	vertical-align: middle;
	transform: translateY(-1px);
	transition: transform 0.2s ease;
}

.dov-nav-item:hover .dov-nav-caret,
.dov-nav-item:focus-within .dov-nav-caret {
	transform: rotate(180deg) translateY(1px);
}

.dov-submenu {
	position: absolute;
	top: 100%;
	left: 50%;
	min-width: 240px;
	background: #ffffff;
	border: 1px solid #dde4e4;
	border-radius: 8px;
	box-shadow: 0 12px 28px rgba(11, 55, 67, 0.14);
	padding: 8px;
	opacity: 0;
	pointer-events: none;
	transform: translate(-50%, -4px);
	transition: opacity 0.18s ease, transform 0.18s ease;
	z-index: 30;
}

.dov-nav-item:hover .dov-submenu,
.dov-nav-item:focus-within .dov-submenu {
	opacity: 1;
	pointer-events: auto;
	transform: translate(-50%, 0);
}

.dov-submenu a {
	display: block;
	position: relative;
	padding: 9px 14px 9px 18px;
	font-size: 0.8125rem;
	font-weight: 500;
	color: var(--wp--preset--color--ink, #1d1d2b);
	text-decoration: none;
	border-radius: 6px;
	white-space: nowrap;
	transition: color 0.15s ease, background-color 0.15s ease;
}

.dov-submenu a::before {
	content: "";
	position: absolute;
	left: 4px;
	top: 50%;
	transform: translateY(-50%);
	width: 3px;
	height: 60%;
	border-radius: 2px;
	background: linear-gradient(
		var(--dov-accent-color-b) 0,
		var(--dov-accent-color-b) 40%,
		transparent 40%,
		transparent 60%,
		var(--dov-accent-color-b) 60%,
		var(--dov-accent-color-b) 100%
	);
	opacity: 0;
	transition: opacity 0.15s ease;
}

.dov-submenu a:hover,
.dov-submenu a:focus-visible {
	color: var(--dov-accent-color);
	background-color: var(--wp--preset--color--stone, #f2eee7);
}

.dov-submenu a:hover::before,
.dov-submenu a:focus-visible::before {
	opacity: 1;
}

/* --- Menu burger mobile (ajouté le 10.09.2026) --------------------------
   Trois barres façon hamburger, mais la barre du milieu reprend la fente
   D/O plutôt qu'un simple trait plein — même vocabulaire que le reste de
   la signature graphique, jusque dans l'icône de menu. Piloté par
   assets/js/nav.js (vanilla, sans dépendance) : bascule aria-expanded sur
   le bouton et .is-open sur le panneau. Caché au-delà de 900px, où le
   menu horizontal habituel reste en place. */

.dov-burger {
	display: none;
	position: absolute;
	right: 32px;
	top: 50%;
	transform: translateY(-50%);
	width: 28px;
	height: 20px;
	padding: 0;
	border: 0;
	background: none;
	cursor: pointer;
	color: var(--wp--preset--color--teal-900, #0b3743);
	z-index: 60;
}

.dov-burger span {
	position: absolute;
	left: 0;
	width: 100%;
	height: 2px;
	background: currentColor;
	transition: transform 0.25s ease, opacity 0.2s ease;
}

.dov-burger span:nth-child(1) {
	top: 0;
}

.dov-burger span:nth-child(2) {
	top: 9px;
	background: linear-gradient(
		to right,
		currentColor 0,
		currentColor 42%,
		transparent 42%,
		transparent 58%,
		currentColor 58%,
		currentColor 100%
	);
}

.dov-burger span:nth-child(3) {
	top: 18px;
}

.dov-burger[aria-expanded="true"] span:nth-child(1) {
	transform: translateY(9px) rotate(45deg);
}

.dov-burger[aria-expanded="true"] span:nth-child(2) {
	opacity: 0;
}

.dov-burger[aria-expanded="true"] span:nth-child(3) {
	transform: translateY(-9px) rotate(-45deg);
}

header {
	position: relative;
}

/* Seuil relevé de 900px à 1150px (10.09.2026) : entre les deux, le
   menu horizontal + logo ne tenait plus sur une seule ligne et
   retombait sur deux lignes (logo puis menu), avec le sous-menu
   ouvert qui semblait alors mal centré par rapport à son lien —
   repéré en vérifiant en direct sur new.3dvisions.ch à une largeur
   de fenêtre "laptop" courante (~1024-1100px). Le burger prend donc
   le relais un peu plus tôt, avant que ce point de rupture n'arrive. */
@media (max-width: 1150px) {
	.dov-burger {
		display: inline-block;
	}

	/* Le groupe Gutenberg qui contient les liens + le bouton Contact devient
	   le panneau mobile : masqué par défaut, affiché en pleine largeur sous
	   l'en-tête quand le burger est actionné. */
	/* display:none/flex sont en !important pour la même raison que
	   flex-direction/align-items/gap ci-dessous : le bloc Group de
	   Gutenberg génère sa propre règle CSS (layout flex du bloc,
	   .wp-container-core-group-is-layout-xxxxx) avec la même spécificité
	   qu'un simple sélecteur de classe — sans !important, cette règle
	   générée l'emporte selon l'ordre d'impression dans le <head> et le
	   panneau mobile reste visible en permanence (display:flex) quel que
	   soit l'état de .is-open. Repéré et corrigé après vérification sur
	   le site réel (le X du burger ne fermait pas le panneau). */
	.dov-mobile-nav {
		display: none !important;
		position: absolute;
		top: 100%;
		left: 0;
		right: 0;
		flex-direction: column !important;
		align-items: stretch !important;
		gap: 2px !important;
		background: #ffffff;
		border-top: 1px solid #dde4e4;
		box-shadow: 0 16px 32px rgba(11, 55, 67, 0.14);
		padding: 8px 20px 20px;
		z-index: 50;
	}

	.dov-mobile-nav.is-open {
		display: flex !important;
	}

	.dov-mobile-nav .dov-nav-item,
	.dov-mobile-nav > p {
		padding: 12px 0;
		border-bottom: 1px solid #eef2f2;
		margin: 0;
	}

	.dov-mobile-nav .dov-nav-item {
		display: flex;
		flex-direction: column;
		align-items: stretch;
	}

	.dov-mobile-nav .dov-nav-item > a {
		display: flex;
		align-items: center;
		justify-content: space-between;
	}

	.dov-submenu {
		position: static;
		transform: none;
		box-shadow: none;
		border: none;
		min-width: 0;
		width: 100%;
		padding: 0;
		margin-top: 4px;
		display: none;
	}

	.dov-nav-item.is-submenu-open .dov-submenu {
		display: block;
		/* Neutralise le transform/opacity/pointer-events de la règle
		   :hover/:focus-within desktop (même spécificité, définie plus haut
		   dans le fichier) : sans ça, un focus-within déclenché par le tap
		   décale le panneau de -50% hors écran, ou le laisse invisible si le
		   focus-within ne se déclenche pas. */
		transform: none;
		opacity: 1;
		pointer-events: auto;
	}

	/* Retouche du 11.09.2026, retour de Marc : sur le panneau mobile, la
	   flèche du bureau (9x6px, pensée pour un simple survol souris) était
	   quasi impossible à toucher au doigt. On garde le même principe visuel
	   mais en plus grand (::before), et on ajoute une zone de tap invisible
	   de 44px de côté (::after) très au-delà du dessin lui-même — la norme
	   usuelle pour une cible tactile confortable. */
	.dov-mobile-nav .dov-nav-caret {
		position: relative;
		width: 16px;
		height: 16px;
		margin-left: 12px;
		border: 0;
		flex-shrink: 0;
	}

	.dov-mobile-nav .dov-nav-caret::before {
		content: "";
		position: absolute;
		top: 50%;
		left: 50%;
		width: 0;
		height: 0;
		border-left: 6px solid transparent;
		border-right: 6px solid transparent;
		border-top: 8px solid currentColor;
		transform: translate(-50%, -50%);
		transition: transform 0.2s ease;
	}

	.dov-mobile-nav .dov-nav-caret::after {
		content: "";
		position: absolute;
		top: 50%;
		left: 50%;
		width: 44px;
		height: 44px;
		transform: translate(-50%, -50%);
	}

	/* Sans ceci, la règle desktop .dov-nav-item:hover/:focus-within
	   .dov-nav-caret (plus haut dans ce fichier, hors media query) fait
	   tourner l'élément .dov-nav-caret LUI-MÊME de 180deg dès qu'il reçoit
	   le focus au tap (tabindex=0, posé par nav.js) — en plus de la
	   rotation posée juste au-dessus sur son ::before. Les deux tours se
	   cumulent (180 + 180 = 360), donc la flèche a l'air immobile malgré
	   l'ouverture réelle du sous-menu. On neutralise cette règle desktop
	   ici, réservée au panneau mobile. */
	.dov-mobile-nav .dov-nav-item:hover .dov-nav-caret,
	.dov-mobile-nav .dov-nav-item:focus-within .dov-nav-caret {
		transform: none;
	}

	.dov-nav-item.is-submenu-open .dov-nav-caret::before {
		transform: translate(-50%, -50%) rotate(180deg);
	}

	.dov-submenu a {
		padding: 10px 10px 10px 18px;
	}

	.dov-mobile-nav .wp-block-buttons {
		margin-top: 14px;
	}

	.dov-mobile-nav .wp-block-button__link {
		display: block;
		text-align: center;
	}
}

/* --- Page Réalisation : modules du modèle de contenu (11.09.2026) -------
   Voir patterns/realisation-modele.php pour le contenu de départ (structure
   pré-remplie à la création d'une nouvelle Réalisation, ou réinsérable
   depuis l'inséreur de blocs → onglet Modèles). Ces classes habillent les
   groupes de ce modèle ; elles ne servent à rien tant que le pattern n'est
   pas utilisé, donc aucun risque pour les Réalisations déjà publiées.
*/

/* En bref : petite ligne de repères (client / lieu / durée), séparateurs
   discrets plutôt que la fente D/O — réservée aux surtitres et accents plus
   visibles, pas à une rangée d'étiquettes de service. */

.dov-brief {
	display: flex;
	flex-wrap: wrap;
	align-items: center;
	row-gap: 6px;
	margin-bottom: 20px;
}

.dov-brief__item {
	position: relative;
	margin: 0;
	padding-right: 16px;
	font-size: 0.8125rem;
	color: var(--wp--preset--color--teal-900, #0b3743);
}

.dov-brief__item:not(:last-child)::after {
	content: "";
	position: absolute;
	right: 0;
	top: 50%;
	transform: translateY(-50%);
	width: 1px;
	height: 13px;
	background: #ccd2d2;
}

/* Carte client : même famille visuelle que .dov-testimonial (bordure fine,
   coins arrondis) avec un accent plein en bordure gauche plutôt que la
   fente — la fente reste réservée aux témoignages, pour que l'œil associe
   ce motif précis à "parole du client" et pas à toute carte du site. */

.dov-client-card {
	border-left: 3px solid var(--wp--preset--color--teal) !important;
	border-radius: 0 8px 8px 0;
	margin-top: 32px;
	padding: 24px 28px;
}

/* Chiffres clés : rangée de mini-statistiques. */

.dov-key-figures {
	display: flex;
	flex-wrap: wrap;
	column-gap: 40px;
	row-gap: 20px;
	margin-top: 40px;
}

.dov-stat {
	min-width: 110px;
	margin-top: 0 !important;
}

.dov-stat__value {
	margin: 0;
	font-size: 1.75rem;
	font-weight: 700;
	line-height: 1.1;
	color: var(--wp--preset--color--teal-900, #0b3743);
	font-variant-numeric: tabular-nums;
}

.dov-stat__label {
	margin: 4px 0 0;
	font-size: 0.75rem;
	text-transform: uppercase;
	letter-spacing: 0.05em;
	color: #6b7676;
}

/* Timeline : reprend le principe du trait fendu du logo, à la verticale,
   comme rail continu reliant chaque étape — plutôt qu'une numérotation
   abstraite (01/02/03), le rail lui-même raconte "un process, une suite
   d'étapes". Repère (le petit point) posé sur le rail à hauteur de
   chaque titre d'étape. Simplifié sous 640px : rail et repères retirés
   (comme .dov-hero-marks sous 560px, ailleurs dans ce fichier) — un
   rail qui ne longe plus rien une fois les étapes empilées en colonne
   perdrait son sens. */

.dov-timeline {
	position: relative;
	padding-left: 28px;
}

.dov-timeline::before {
	content: "";
	position: absolute;
	left: 5px;
	top: 8px;
	bottom: 8px;
	width: 2px;
	background: repeating-linear-gradient(
		to bottom,
		var(--dov-accent-color) 0,
		var(--dov-accent-color) 10px,
		transparent 10px,
		transparent 16px
	);
}

.dov-timeline-step {
	position: relative;
	display: flex;
	flex-wrap: wrap;
	align-items: flex-start;
	gap: 20px;
	margin-bottom: 32px;
}

.dov-timeline-step:last-child {
	margin-bottom: 0;
}

.dov-timeline-step::before {
	content: "";
	position: absolute;
	left: -28px;
	top: 8px;
	width: 11px;
	height: 11px;
	border-radius: 50%;
	background: var(--wp--preset--color--white, #fff);
	border: 2px solid var(--dov-accent-color);
}

.dov-timeline-step__media {
	flex: 0 0 auto;
	width: 180px;
	margin: 0;
}

.dov-timeline-step__media img {
	width: 100%;
	aspect-ratio: 4 / 3;
	object-fit: cover;
	border-radius: 8px;
	display: block;
}

.dov-timeline-step__content {
	flex: 1 1 240px;
	margin-top: 0 !important;
}

.dov-timeline-step__content .wp-block-heading {
	margin: 0 0 4px;
}

@media (max-width: 640px) {
	.dov-timeline {
		padding-left: 0;
	}
	.dov-timeline::before,
	.dov-timeline-step::before {
		display: none;
	}
	.dov-timeline-step__media {
		width: 100%;
	}
}

/* Galerie "carrousel" : le bloc Gallery natif de WordPress affiche une
   grille (colonnes) — on la transforme en bande défilante horizontalement
   (glisser au doigt, molette+shift, ou barre de défilement à la souris),
   sans JS ni plugin. L'équipe utilise le bloc Gallery normalement (bouton
   d'ajout d'images) ; c'est cette classe qui fait tout le travail visuel.
   !important nécessaire : le bloc Gallery pose son propre display/gap en
   style inline (nombre de colonnes, espacement) à la même spécificité
   qu'une classe. */

.dov-gallery-scroll.wp-block-gallery {
	display: flex !important;
	flex-wrap: nowrap !important;
	overflow-x: auto;
	scroll-snap-type: x mandatory;
	gap: 16px !important;
	padding-bottom: 10px;
	-webkit-overflow-scrolling: touch;
}

.dov-gallery-scroll.wp-block-gallery .wp-block-image {
	flex: 0 0 auto;
	width: min(78vw, 320px);
	scroll-snap-align: start;
	margin: 0;
}

.dov-gallery-scroll.wp-block-gallery .wp-block-image img {
	width: 100%;
	height: 100%;
	aspect-ratio: 4 / 3;
	object-fit: cover;
	border-radius: 8px;
}

/* Projets associés : 2-3 cases image + titre lié vers une autre
   Réalisation, en fin de page — mêmes proportions que les images
   d'étapes de la timeline pour rester dans la même famille visuelle. */

.dov-related {
	display: flex;
	flex-wrap: wrap;
	align-items: flex-start;
	gap: 28px;
}

.dov-related-item {
	flex: 1 1 200px;
	margin-top: 0 !important;
}

.dov-related-item__media {
	margin: 0 0 10px;
}

.dov-related-item__media img {
	width: 100%;
	aspect-ratio: 4 / 3;
	object-fit: cover;
	border-radius: 8px;
	display: block;
}

.dov-related-item__title {
	margin: 0;
}

.dov-related-item__title a {
	color: inherit;
	text-decoration: none;
}

.dov-related-item__title a:hover,
.dov-related-item__title a:focus-visible {
	text-decoration: underline;
}

/* Carrousel "Réalisations liées" sur les pages Prestation/Secteur —
   alimenté par une boucle wp:query (inherit) filtrée automatiquement
   sur la taxonomie de l'archive courante ; même mécanique de
   défilement horizontal que la galerie "En images" d'une page
   Réalisation (.dov-gallery-scroll). */

.dov-realisation-carousel-query {
	margin-top: 28px;
}

.dov-realisation-carousel.wp-block-post-template {
	display: flex !important;
	flex-wrap: nowrap;
	overflow-x: auto;
	scroll-snap-type: x mandatory;
	gap: 20px;
	margin: 0;
	padding: 4px 4px 10px;
	list-style: none;
	-webkit-overflow-scrolling: touch;
}

.dov-realisation-carousel.wp-block-post-template > li {
	flex: 0 0 auto;
	width: min(78vw, 280px);
	scroll-snap-align: start;
	margin: 0;
}

.dov-realisation-carousel__media {
	margin: 0 0 10px;
}

.dov-realisation-carousel__media img {
	width: 100%;
	aspect-ratio: 4 / 3;
	object-fit: cover;
	border-radius: 8px;
	display: block;
}

.dov-realisation-carousel__title {
	margin: 0;
}

.dov-realisation-carousel__title a {
	color: inherit;
	text-decoration: none;
}

.dov-realisation-carousel__title a:hover,
.dov-realisation-carousel__title a:focus-visible {
	text-decoration: underline;
}
