Web Components Jean-Marc Lecarpentier GREYC - Université de Caen
Web Components Ensemble de 4 spécifications Custom Elements Shadow DOM Templates HTML imports
Custom Elements Définir des éléments personnalisés Encapsuler dans une seule balise : un ensemble d éléments HTML leurs interactions Javascript leur mise en forme CSS
Shadow DOM Définir des mécanismes pour éviter les collisions en ayant plusieurs DOM dans une page Encapsulation des custom elements Frontière avec le DOM du document CSS et requêtes DOM sont séparées
Templates Permettre d avoir des squelettes HTML Templates remplis avec Javascript Utile pour la structure de certains custom elements
HTML imports Avoir un moyen d importer les custom elements Balise <link> de type import Gestion des dépendances et de l ordre d import
Custom Elements Créer des éléments HTML/DOM Pouvant dériver d autres éléments Ayant leur propre API Encapsulés dans un package Élément doit être déclaré : document.registerelement('mon-element', { options }); options est un objet décrivant le prototype de l élément Balise doit contenir un tiret et être en minuscules
Dérivation Possibilité de dériver d un élément HTML Spécifier le type et la dérivation lors de la déclaration : var monbouton = document.registerelement('mon-bouton', { prototype: Object.create(HTMLButtonElement.prototype), extends: 'button' }); <button is="mon-bouton" disabled onclick="alert('cliqué')">un bouton mon-bouton</button> Possibilité de dériver d un custom element
Propriétés et méthodes Définir le prototype de l élément en conséquence var monproto = Object.create(HTMLElement.prototype); monproto.mamethode = function() { alert('mon-proto a activé mamethode()'); } // ajouter une propriété non modifiable Object.defineProperty(monProto, 'mapropriete', { value: 'la valeur de mapropriete'}); document.registerelement('mon-proto', monproto);
Lifecycle callbacks createdcallback : une instance est créée attachedcallback : une instance est insérée dans le document detachedcallback : une instance est supprimée du document attributechangedcallback(attribut, oldval, newval) : un attribut a été ajouté, supprimé ou modifié
Ajouter du contenu Dynamiquement avec createdcallback Problématique : les éléments constituants le custom element doivent être indépendants du reste de la page Shadow DOM : mécanismes d encapsulation
Shadow DOM Encapsuler des éléments et leur contenu Éviter d être pollué par la CSS et les interactions du document Document tree Tout élément peut être Shadow host Shadow host contient shadow root Séparation complète entre host et root pas de relation parent/child DOM pas de sélection CSS Exemple : widget avec ses interactions et son style
Shadow tree Encapsule son contenu N affiche que ce qu il veut Créer un Shadow tree : var host = document.queryselector('.mon-widget'); var root = host.createshadowroot(); root.textcontent = 'Je suis le contenu du shadow tree ; Console Chrome :
Templates et Shadow DOM Prendre le contenu du Shadow host Pour le mettre dans le Shadow tree Mis en forme selon un template
HTML template Élément <template> Inerte et absent du DOM tant que non activé images, videos, etc chargées lors de l activation Activation en Javascript. Propriété content pour accéder au contenu du template <template id="template"> <h1>un exemple de template</h1> </template> var template = document.getelementbyid( template'); document.body.appendchild(document.importnode(template.content, true));
Exemple Javascript : var host = document.queryselector('.mon-widget'); var root = host.createshadowroot(); var template = document.getelementbyid('template'); root.appendchild(document.importnode(template.content, true)); HTML : <div class="mon-widget"> <h1>mon Widget n 1</h1> <p>du contenu de widget</p> </div> <template id="template"> <style> h1 { color: #aaaaaa; } </style> <h1>le titre de mon widget dans le shadow tree</h1> <content select="h1"></content> </template>
Shadow tree et CSS CSS Scoping module Pseudo classes :host et :host-context Pseudo éléments ::shadow et ::content Sélecteur /deep/ Tutoriel : http://www.html5rocks.com/en/tutorials/webcomponents/shadowdom-201/ Draft W3C : https://drafts.csswg.org/css-scoping/
Shadow tree et évènements Évènements traversent ou non la frontière Ceux qui traversent sont modifiés pour conserver l encapsulation Évènement réassigné pour sembler provenir du shadow host Javascript event.path pour voir le chemin
HTML imports Charger des ressources sans <iframe>, Ajax, etc <link rel="import" href= /chemin/du/fichier.html > Utiliser CORS si import d un autre domaine Évènements load et error Document importé disponible via son DOM
Document importé Notion de import document <link> CSS du import non utilisées dans document principal, sauf CSS dans élément <style> Propriété import de l élément link : var importdom = document.queryselector( link[rel= import"]').import; Javascript de l import exécuté dans le contexte window Accès au document principal par l objet document
Imports et Custom Elements Importer un document définissant ses éléments L import exécute les scripts document.registerelement est exécuté Éléments ainsi créés utilisables dans le document
Imports multiples Import peut importer ses propres ressources Gestion des dépendances et de l ordre des imports Ressources importées une seule fois même si incluses dans divers imports Scripts exécutés une seule fois fonctionne même si un script est importé n fois
Imports et affichage <link rel= import > bloque l affichage de la page De même que <link rel= stylesheet > Éviter l effet FOUC Être certain d avoir les custom elements déclarés Considérer les performances http://www.html5rocks.com/en/tutorials/webcomponents/imports/#depssubimports
Web Components Templates Custom Elements Shadow DOM HTML imports Ensemble intéressant Utilisable avec polyfill https://github.com/webcomponents/webcomponentsjs