Icônes en HTML pur depuis un CDN
Une seule balise script donne à une page toutes les icônes glyphfox, l'élément <glyph-fox> et un runtime qui transforme les placeholders <i data-glyph> en SVG inline. Aucune étape de build, aucun framework.
Ajouter le script
Le build en fichier unique contient toutes les icônes, l'élément, le runtime des placeholders et le moteur. jsDelivr et unpkg résolvent tous deux l'URL du paquet, sans chemin, vers ce fichier : dist/web/glyphfox.min.js.
<!doctype html> <html lang="en"> <head> <meta charset="utf-8"> <title>My page</title> <script defer src="https://cdn.jsdelivr.net/npm/glyphfox@1"></script> <!-- or https://unpkg.com/glyphfox@1 --> </head> <body> <glyph-fox name="home"></glyph-fox> <i data-glyph="search" data-size="20"></i> </body> </html>
Avec defer, le téléchargement ne bloque pas l'analyse du HTML. Le script s'exécute une fois le document analysé, définit l'élément, met à niveau chaque <glyph-fox> de la page et remplace les placeholders.
Figer la version
glyphfox@1 suit la dernière version 1.x, ce qui est pratique pendant le prototypage. En production, figez la version exacte et le fichier : la page ne change jamais à votre insu et le CDN peut mettre le fichier en cache définitivement.
<script defer src="https://cdn.jsdelivr.net/npm/glyphfox@1.3.0/dist/web/glyphfox.min.js"></script>
Une version exacte permet aussi l'intégrité des sous-ressources (Subresource Integrity) : récupérez l'empreinte de ce fichier, que jsDelivr indique pour chaque fichier, puis ajoutez integrity et crossorigin="anonymous" à la balise. Une plage comme @1 ne peut pas porter d'empreinte, car le fichier qu'elle désigne change à chaque version.
Vous pouvez aussi l'héberger vous-même. Copiez node_modules/glyphfox/dist/web/glyphfox.min.js dans votre dossier public et faites pointer la balise vers ce fichier : il est autonome et n'effectue aucune autre requête.
L'élément glyph-fox
Utilisez l'élément pour les icônes qui changent : un nom qui varie, un morph, un déclencheur au survol ou au clic, un état. Il lit chaque prop depuis ses attributs et se redessine dès que l'un d'eux change.
<button type="button" class="menu" aria-label="Open menu" aria-expanded="false"> <glyph-fox name="menu" morph duration="300"></glyph-fox> </button> <script type="module"> const button = document.querySelector('.menu'); const icon = button.querySelector('glyph-fox'); button.addEventListener('click', () => { const open = button.getAttribute('aria-expanded') !== 'true'; button.setAttribute('aria-expanded', String(open)); button.setAttribute('aria-label', open ? 'Close menu' : 'Open menu'); icon.setAttribute('name', open ? 'x' : 'menu'); }); </script>
L'attribut morph anime le passage de menu à x, l'une des paires ajustées à la main. Le style dans le shadow DOM, les noms de balise personnalisés et les déclencheurs sont traités dans le guide des web components.
Placeholders avec data-glyph
Pour les icônes qui ne changent jamais, un placeholder est plus léger qu'un élément dynamique. Le runtime remplace par du SVG inline chaque élément doté d'un attribut data-glyph, copie sa class sur le svg et continue d'observer la page : les placeholders ajoutés plus tard par vos scripts sont donc eux aussi remplacés.
<i data-glyph="search" data-size="20"></i> <i data-glyph="file+check@tr" data-weight="1.5"></i> <i data-glyph="folder" data-variant="duotone" data-secondary-color="#ff7a1a"></i> <i data-glyph="trash" class="danger" aria-label="Delete"></i>
Les props sont des attributs data en kebab-case : data-size, data-weight, data-variant, data-modifier, data-animate et les autres du tableau ci-dessous. Un aria-label placé sur le placeholder devient le titre de l'icône : le svg reçoit ainsi un nom accessible.
Le remplacement n'a lieu qu'une fois. Le placeholder disparaît ensuite : modifier ses attributs data par la suite n'a donc aucun effet, et les écouteurs attachés au <i> disparaissent avec lui. Attachez les écouteurs à un parent, ou utilisez l'élément lorsque l'icône doit changer.
Avec un bundler, importez glyphfox/runtime au lieu du fichier du CDN. Il exporte replaceGlyphs et l'exécute au chargement, et il inclut toutes les icônes, puisqu'une page peut demander n'importe quel nom. Ne chargez pas ce module directement depuis un CDN : il importe le paquet sous forme de modules ES séparés, un fichier par icône, ce qui représente des centaines de requêtes. Le build en fichier unique contient déjà ce même runtime.
L'API globale
Le build pour CDN définit aussi window.glyphfox avec l'API principale : toSvg, fuse, search, getIcon, iconNames, categories, createMorph, toDataUri, replaceGlyphs et d'autres encore. Elle n'existe qu'une fois le script exécuté : appelez-la donc depuis un script module placé après la balise, ou après DOMContentLoaded.
<input type="search" id="q" placeholder="Search icons" aria-label="Search icons"> <div id="results"></div> <script type="module"> const { search, toSvg } = window.glyphfox; const q = document.getElementById('q'); const results = document.getElementById('results'); q.addEventListener('input', () => { results.innerHTML = search(q.value, { limit: 24 }) .map((icon) => `<button type="button" aria-label="${icon.name}">${toSvg(icon.name, { size: 28 })}</button>`) .join(''); }); </script>
toDataUri transforme une chaîne SVG en URL utilisable pour les arrière-plans CSS ou un élément <img>. Une image ne peut pas hériter de currentColor depuis la page : indiquez donc une couleur explicite.
const { toDataUri, toSvg } = window.glyphfox; const check = toDataUri(toSvg('check', { size: 16, color: '#16a34a' })); document.documentElement.style.setProperty('--icon-check', `url("${check}")`);
.done::before { content: ''; display: inline-block; width: 16px; height: 16px; margin-right: 6px; background: var(--icon-check) no-repeat center / contain; }
dist/web/glyphfox.esm.js est le même build sous forme de module ES. Son export par défaut est l'objet de l'API et, comme le fichier classique, il définit l'élément et exécute le runtime des placeholders.
<div id="logo"></div> <script type="module"> import glyphfox from 'https://cdn.jsdelivr.net/npm/glyphfox@1/dist/web/glyphfox.esm.js'; document.getElementById('logo').innerHTML = glyphfox.toSvg('fox', { size: 48, variant: 'duotone' }); </script>
Taille du fichier et quand préférer un build
Le fichier unique contient toutes les icônes : 216,4 Ko minifié, 62,4 Ko avec gzip. Servi depuis un CDN avec une longue durée de cache, c'est un prix raisonnable pour un prototype, un site de documentation ou une page qui affiche de nombreuses icônes différentes. C'est un mauvais calcul pour une landing page qui n'en affiche que six.
| Approche | Contenu | Idéal pour |
|---|---|---|
| Un seul script depuis le CDN | Toutes les icônes, l'élément, le runtime et l'API. | Prototypes, documentation, pages avec beaucoup d'icônes. |
Un bundler avec glyphfox/web/element | L'élément et les icônes que vous enregistrez. | Applications qui ont déjà une étape de build (voir tree shaking). |
| Sous-ensemble CSS via la CLI | Une feuille de style avec une classe de masque par icône, sans JavaScript. | Sites statiques et icônes qui ne changent jamais. |
| Sous-ensemble en sprite via la CLI | Un fichier SVG avec un symbole par icône. | HTML rendu côté serveur qui répète les mêmes icônes (voir sprites SVG). |
npx glyphfox build home search menu loader --type css --out public npx glyphfox build home search menu loader --type sprite --out public/icons
<link rel="stylesheet" href="/glyphfox.css"> <span class="gf gf-home" aria-hidden="true"></span> <span class="gf gf-loader gf-spin" aria-hidden="true"></span>
Le build CSS dessine chaque icône comme un masque rempli de currentColor : elle prend donc la couleur du texte et la taille de la police. Il inclut aussi les animations gf-spin et gf-pulse. Chaque commande accepte les props communes sous forme d'options, comme --weight 1.5 ou --variant duotone.
Attributs
L'élément et les placeholders lisent les mêmes props, en kebab-case dans les deux cas : sous forme d'attributs simples sur <glyph-fox>, comme size et secondary-color, et avec le préfixe data- sur les placeholders, comme data-size et data-secondary-color. L'élément accepte aussi layout, gap et morph.
| Attribut | Type | Par défaut | Description |
|---|---|---|---|
name | string | aucun | La spécification de l'icône : un nom, name+modifier@corner, a&b:layout ou name/variant. |
layout | overlap, side, stack, grid, orbit, badge, inside | aucun | Disposition de la fusion quand le nom combine des icônes avec &. |
gap | number | 1 | Espace de découpe d'une fusion, en unités de la grille. |
morph | boolean | false | Anime chaque changement de name sous forme de morph. |
size | number, string | 24 | Largeur et hauteur ; les nombres sont en pixels. |
color | string | currentColor | Couleur principale. |
secondary-color | string | color | Couleur du calque duotone et du remplissage plein. |
secondary-opacity | number | 0.3 / 1 | Opacité du calque duotone ou du remplissage plein. |
weight | number | 2 | Trait de 1 à 3 sur la grille de 24, avec compensation optique en dessous de 24 px. |
absolute-weight | boolean | false | Garde le trait à weight pixels quelle que soit la taille. |
corners | round, sharp | round | Jointures et extrémités arrondies ou vives. |
variant | outline, duotone, solid | outline | Axe de style ; solid vient des formes fermées. |
rotate | number | 0 | Rotation en degrés. |
flip-x | boolean | false | Miroir horizontal. |
flip-y | boolean | false | Miroir vertical. |
mirror-rtl | boolean | false | Miroir dans les mises en page de droite à gauche. |
animate | draw, pop, wiggle, spin, pulse, bounce, shake | aucun | Préréglage d'état vivant. |
trigger | mount, hover, click, state | mount | Moment où l'animation ou le morph se joue. |
active | boolean | false | L'état pour le déclencheur state. |
duration | number (ms) | selon le préréglage | Durée de l'animation ou du morph. |
delay | number (ms) | 0 | Délai de l'animation ou du morph. |
loop | boolean, number | false | Répète à l'infini ou un certain nombre de fois (spin et pulse bouclent par défaut). |
modifier | plus, minus, check, x, alert, lock, clock, sync, arrow-up, arrow-down, dot | aucun | Badge avec espace de découpe automatique. |
modifier-corner | top-left, top-right, bottom-left, bottom-right | bottom-right | Coin du badge. |
morph-to | name, data | aucun | Cible du morph ; le déclencheur décide quand elle s'affiche. |
title | string | aucun | Nom accessible : title, role img et aria-label. |
decorative | boolean | true sans title | Masque l'icône aux technologies d'assistance. |
Pièges courants
- Scripts exécutés trop tôt
- Un script classique inline s'exécute pendant l'analyse du HTML, avant un script CDN différé :
window.glyphfoxy est donc encore indéfini. Utiliseztype="module", car les scripts module s'exécutent après les scripts différés, dans l'ordre du document, ou attendezDOMContentLoaded. - Le module runtime chargé depuis un CDN
dist/runtime/auto.jsest destiné aux bundlers. Chargé directement dans le navigateur, il récupère le paquet module par module, un fichier par icône. Sur les pages HTML simples, utilisez le build en fichier unique.- Les placeholders ne sont remplacés qu'une fois
- Modifier les attributs
data-*après le remplacement n'a aucun effet, et les écouteurs du placeholder sont perdus. Utilisez<glyph-fox>pour les icônes qui changent. - Éléments autofermants
- En HTML,
<glyph-fox name="home" />reste une balise ouvrante : le contenu qui suit disparaît donc à l'intérieur de l'élément. Écrivez toujours la balise fermante. - currentColor dans les images
- Un SVG utilisé comme source d'un
<img>ou comme arrière-plan CSS n'a pas accès à la couleur de la page. Passez une couleur àtoSvg, ou utilisez le sous-ensemble CSS, qui fonctionne avec des masques. - Déclencheurs au clic sur les placeholders
- Les placeholders deviennent du SVG statique. Les morphs au survol et les animations fonctionnent toujours, car ce sont du CSS intégré au SVG, mais les déclencheurs de clic et d'état ont besoin de l'élément, qui bascule les états pour vous.
- Versions flottantes en production
glyphfox@1évolue à chaque version 1.x, et un fichier modifié invalide l'empreinte d'intégrité. Figezglyphfox@1.0.0et le chemin complet du fichier.
Questions fréquentes
Faut-il utiliser l'élément ou les placeholders data-glyph ?
Les placeholders pour les icônes qui ne changent jamais après le chargement : ils deviennent du simple SVG inline, sans élément dynamique derrière eux. L'élément pour les icônes qui changent de nom, se transforment ou réagissent au survol, au clic ou à un état. Les deux proviennent du même script et peuvent cohabiter sur une même page.
Est-ce que cela fonctionne avec du HTML inséré plus tard, par exemple par htmx ?
Oui. Le runtime observe tout le document : les placeholders contenus dans le HTML inséré sont donc remplacés dès leur arrivée, et les éléments <glyph-fox> sont mis à niveau dès leur insertion, puisque l'élément est défini pour la page.