peels.css
Tout Peels + le thème livré. L'usage standard — ~140 Ko.
Un fichier CSS, un attribut sur <html>, du HTML sémantique. Aucune dépendance.
Tout Peels + le thème livré. L'usage standard — ~140 Ko.
Le même + tous les thèmes optionnels (couleur, typographie, densité) — pour un sélecteur de thème.
Le <link> charge Peels ; data-theme="peels" active le thème livré. Sans l'attribut, le socle reste à l'état vide (voir plus bas). Votre CSS vit dans un second fichier : non-layeré, il gagne toujours.
<!doctype html>
<html lang="fr" data-theme="peels">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="stylesheet" href="peels.css">
<link rel="stylesheet" href="site.css">
</head>
<body>
<h1>Titre</h1>
<p>Du HTML sémantique, rendu propre.</p>
<button>Action</button>
</body>
</html>
data-theme-mode="dark" ou "light" force le schéma — sinon light-dark() suit l'OS. Fonctionne aussi à l'état vide.data-icon="…" — icônes en CSS pur, aucune police.Sans data-theme, aucune règle du layer theme ne s'applique : gris pur, police système. La toile vierge pour écrire votre propre thème, sous votre propre valeur d'attribut.
<html> <!-- état vide : socle seul -->
<html data-theme="peels"> <!-- thème livré -->
Les rôles --peels-* se posent globalement ou sur un contexte et héritent : ici, fond crème et filets accentués partout, et seuls les boutons de l'aside deviennent des pilules plus grosses.
/* site.css */
@layer theme {
:root {
--peels-surface-page: light-dark(#fbf7ef, #181a20);
--peels-component-radius: 0.65rem;
--peels-blockquote-border: var(--peels-border-accent);
--peels-hr-color: var(--peels-border-accent);
}
/* Un contexte pose les variables sur lui-même : seuls les
boutons de l'encadré deviennent des pilules plus grosses. */
aside {
--peels-component-radius: 99px;
--peels-btn-font-scale: 1;
--peels-btn-min-height: 4rem;
}
}
L'identité se pose dans @layer theme — le layer où Peels range ses thèmes. Les paires light-dark() règlent clair et sombre d'un coup ; le socle dérive survols, fonds doux et bordures. Les rôles --peels-font-* se règlent de la même façon.
/* site.css — vos 3 couleurs + votre rampe neutre */
@layer theme {
:root {
--brand: light-dark(oklch(0.55 0.19 150), oklch(0.72 0.17 155));
--action: light-dark(oklch(0.50 0.19 215), oklch(0.70 0.15 215));
--accent: light-dark(oklch(0.58 0.19 330), oklch(0.74 0.15 335));
--neutral-bg: light-dark(#f6f9f7, #101713);
--neutral-bg-elevated: light-dark(#ffffff, #1a231e);
--neutral-bg-sunken: light-dark(#e9f0ec, #0c120f);
--neutral-text: light-dark(#1c2620, #eaf2ed);
--neutral-text-muted: light-dark(#59695f, #a4b3a9);
--neutral-border: light-dark(#d3e0d8, #2f3d35);
}
}
Quand aucune variable ne suffit : votre CSS non-layeré gagne toujours. Étendez un élément (article) ou construisez le vôtre ([data-timeline]) en vous appuyant sur les rôles --peels-* — il suit le thème et le clair/sombre comme un natif.
/* site.css — non layeré : gagne toujours */
article:hover {
translate: 0 -2px;
box-shadow: var(--peels-elevation-2);
}
/* Élément maison appuyé sur le contrat */
[data-timeline] {
--_tl-line: var(--peels-border-subtle);
--_tl-dot: var(--peels-border-accent);
padding-inline-start: 1.6rem;
list-style: none;
position: relative;
}
[data-timeline]::before {
content: "";
position: absolute;
inset-block: 0.5em;
border-inline-start: 2px solid var(--_tl-line);
}
[data-timeline] > li::before {
content: "";
position: absolute;
inline-size: 0.8rem;
block-size: 0.8rem;
inset-inline-start: -1.5rem;
inset-block-start: 0.6em;
border-radius: 50%;
background: var(--_tl-dot);
}