Polimer - Shadow DOM i stylizacja

Shadow DOM to nowa właściwość DOM używana do tworzenia komponentów.

Example

W poniższym kodzie składnik nagłówka zawiera tytuł strony i przycisk menu.

<header-demo>
   <header>
      <h1>
         <button>

Shadow DOM umożliwia lokalizowanie dzieci w poddrzewie o określonym zakresie, które jest znane jako shadow tree.

<header-demo>
   #shadow-root
   <header>
      <h1>
      <button>

Główny element cienia nazywany jest wierzchołkiem drzewa cienia, a element, który jest do niego dołączony, nazywany jest hostem cienia (nagłówek-demo). Ten host-cień zawiera właściwość o nazwie shadowRoot, która określa główny element cienia. Cień główny identyfikuje element hosta za pomocą właściwości hosta.

Shadow DOM i kompozycja

Drzewo cienia może być renderowane zamiast elementów potomnych elementu, jeśli istnieje element w cieniu DOM. Elementy podrzędne elementu można renderować, dodając element <slot> do drzewa cienia.

Na przykład użyj następującego drzewa cieni dla <header-demo>.

<header>
   <h1><slot></slot></h1>
   <button>Menu</button>
</header>

Dodaj dzieci do elementu <my-header> jako -

<header-demo>Shadow DOM</header-demo>

Nagłówek zastępuje element </slot> powyższymi określonymi dziećmi jako -

<header-demo>
   <header>
      <h1>Shadow DOM</h1>
      <button>Menu</button>
   </header>
</header-demo>

Treść zastępcza

Zawartość rezerwową można wyświetlić, gdy do gniazda nie są przydzielone żadne węzły. Na przykład -

<my-element>
   #shadow-root
   <slot id = "myimgicon">
      <img src = "img-demo.png">
   </slot>
   <slot></slot>
<my-element>

Możesz podać własną ikonę dla elementu, tak jak -

<my-element>
   <img slot = "myimgicon" src = "warning.png">
<my-element>

Dystrybucja wielopoziomowa

Możesz przydzielić element gniazda do boksu, który jest znany jako dystrybucja wielopoziomowa.

Na przykład weź dwa poziomy drzewa cienia, jak pokazano poniżej -

<parent-element>
   #shadow-root
      <child-element>
      <!-- display the light DOM children of parent-element inside child-element -->
      <slot id = "parent-slot">
	  
   <child-element>
      #shadow-root
         <div>
            <!-- Render the light DOM children inside div by using child-element -->
            <slot id = "child-slot">

Rozważ następujący kod -

<parent-element>
   <p>This is light DOM</p>
<parent-element>

Struktura spłaszczonego drzewa wygląda następująco.

<parent-element>
   <child-element>
      <div>
         <slot id = "child-slot">
            <slot id = "parent-slot">
               <p>This is light DOM</p>

Shadow DOM używa następujących API slotów do sprawdzania dystrybucji -

  • HTMLElement.assignedSlot - Przydziela miejsce na element i zwraca wartość null, jeśli nie ma przypisania elementu do gniazda.

  • HTMLSlotElement.assignedNodes - Dostarcza listę węzłów wraz z gniazdem i zwraca rozproszone węzły, gdy ustawisz opcję spłaszczania na true.

  • HTMLSlotElement.slotchange - To zdarzenie jest wyzwalane, gdy nastąpią zmiany w rozproszonych węzłach gniazda.

Retargeting wydarzeń

Określa cel zdarzenia, w którym element może być reprezentowany w tym samym zakresie, co element nasłuchiwania. Zapewnia zdarzenie z elementu niestandardowego, które wygląda tak, jakby pochodziło z tagu elementu niestandardowego, w przeciwieństwie do elementu wewnątrz.

Example

Poniższy przykład ilustruje użycie retargetingu zdarzeń w Polymer.js. Utwórz plik o nazwie index.html i umieść w nim następujący kod.

<!doctype html>
<html>
   <head>
      <title>Polymer Example</title>
      <script src = "bower_components/webcomponentsjs/webcomponents-lite.js"></script>
      <link rel = "import" href = "bower_components/polymer/polymer.html">
      <link rel = "import" href = "retarget-event.html">
   </head>
   
   <body>
      <template id = "myapp" is = "dom-bind">
         <retarget-event on-tap = "clicky"></retarget-event>
      </template>
      
      <script>
         var myval = document.querySelector('#myapp');
         myval.clicky = function(e) {
            console.log("The retargeted result:", Polymer.dom(myval));
            console.log("Normal result:", e);
         };
      </script>
   </body>
</html>

Teraz utwórz kolejny plik o nazwie retarget-event.html i dołącz następujący kod.

<link rel = "import" href = "bower_components/polymer/polymer-element.html">

//it specifies the start of an element's local DOM
<dom-module id = "retarget-event">

   <template>
      <span>Click on this text to see result in console...</span>
   </template>

   <script>
      Polymer ({
         is: 'retarget-event',
      });
   </script>
</dom-module>

Output

Aby uruchomić aplikację, przejdź do utworzonego katalogu projektu i uruchom następujące polecenie.

polymer serve

Teraz otwórz przeglądarkę i przejdź do http://127.0.0.1:8081/. Poniżej będzie wynik.

Kliknij powyższy tekst i otwórz konsolę, aby zobaczyć ponownie skierowane wydarzenie, jak pokazano na poniższym zrzucie ekranu.

Stylowanie Shadow DOM

Możesz stylizować cień DOM używając właściwości stylu, które dziedziczą z hosta do drzewa cienia.

Example

<style>
   .mydemo { background-color: grey; }
</style>

<my-element>
#shadow-root
   <style>
      //this div will have blue background color
      div { background-color: orange; }
   </style>
   <div class = "mydemo">Demo</div>

DOM Templating

Poddrzewo DOM można utworzyć dla elementu za pomocą szablonu DOM. Możesz utworzyć cień główny dla elementu i skopiować szablon do drzewa cienia, dodając szablon DOM do elementu.

Szablon DOM można określić na dwa sposoby -

  • Utwórz element <dom-module>, który powinien pasować do nazwy elementu wraz z atrybutem id.

  • Zdefiniuj element <template> wewnątrz <dom-module>.

Example

<dom-module id = "my-template">
   <template>I am in my template!!!</template>

   <script>
      class MyTemplate extends Polymer.Element {
         static get is() { return  'my-template' }
      }
      customElements.define(MyTemplate.is, MyTemplate);
   </script>
</dom-module>

Stylizacja Shadow DOM elementu

Shadow DOM umożliwia stylizowanie niestandardowych elementów za pomocą właściwości stylów, takich jak czcionki, kolory tekstu i klasy, bez stosowania ich poza zakresem elementu.

Stylizujmy element hosta za pomocą :hostselector (element dołączony do Shadow DOM jest nazywany hostem). Utwórz plik o nazwie polimer-app.html i dodaj do niego następujący kod.

<link rel = "import" href = "../../bower_components/polymer/polymer-element.html">

<dom-module id = "polymer-app">
   <template>
      <style>
         :host {
            color:#33ACC9;
         }
      </style>
      <h2>Hello...[[myval]]!</h2>	
  </template>

  <script>
      class PolymerApp extends Polymer.Element {
         static get is() { return 'polymer-app'; }
         static get properties() {
            return {
               myval: {
                  type: String, value: 'Welcome to Tutorialspoint!!!'
               }
            };
         }
      }

      window.customElements.define(PolymerApp.is, PolymerApp);
   </script>
</dom-module>

Uruchom aplikację, jak pokazano w poprzednim rozdziale i przejdź dohttp://127.0.0.1:8000/. Poniżej będzie wynik.

Stylizacja treści z otworami

Jest możliwe do stworzenia slots w szablonie elementu, który jest zajęty w czasie wykonywania.

Example

Poniższy przykład przedstawia użycie zawartości przedziału w szablonie elementu. Utwórz plik index.html i dodaj w nim następujący kod.

<!doctype html>
<html>
   <head>
      <title>Polymer Example</title>
      <link rel = "import" href = "bower_components/polymer/polymer.html">
      <link rel = "import" href = "slotted-content.html">
   </head>
   
   <body>
      <slotted-content>
         <div slot = "text">This is Polymer.JS Slotted Content Example</div>
      </slotted-content> 
   </body>
</html>

Teraz utwórz kolejny plik o nazwie slotted-content.html i dołącz następujący kod.

<link rel = "import" href = "bower_components/polymer/polymer-element.html">

<dom-module id = "slotted-content">
   <template>
      <style>
         ::slotted(*) {
            font-family: sans-serif;
            color:#E94A9D;
         }
      </style>
      
      <h2>Hello...[[prop1]]</h2>
      <h3>
         <div><slot name='text'></slot></div>
      </h3>
   </template>
   
   <script>
      Polymer ({
         is: 'slotted-content', properties: {
            prop1: {
               type: String,
               value: 'Welcome to Tutorialspoint!!',
            },
         },
      });
   </script>
</dom-module>

Uruchom aplikację, jak pokazano w poprzednim przykładzie, i przejdź do http://127.0.0.1:8081/. Poniżej będzie wynik.

Korzystanie z modułów stylów

Możesz udostępniać style między elementami wraz z modułami stylów. Określ style w module stylów i udostępnij je między elementami.

Example

Poniższy przykład pokazuje, jak używać modułu stylu między elementami. Utwórz plik index.html i dodaj w nim następujący kod.

<!doctype html>
<html>
   <head>
      <title>Polymer Example</title>
      <link rel = "import" href = "bower_components/polymer/polymer.html">
      <link rel = "import" href = "style-module.html">
   </head>
   
   <body>
      <style-module></style-module> 
   </body>
</html>

Utwórz inny plik o nazwie style-module.html z następującym kodem.

<link rel = "import" href = "bower_components/polymer/polymer-element.html">

<dom-module id = "style-module">
   <template>
      <!-- here, including the imported styles from colors-module page -->
      <style include="colors-module"></style>
      <style>
         :host {
            font-family: sans-serif;
            color: green;    
         }
      </style>
      
      <h2>Hello...[[prop1]]</h2>
      <p class = "color1">Sharing styles with style modules 1...</p>
      <p class = "color2">Sharing styles with style modules 2...</p>
      <p class = "color3">Sharing styles with style modules 3...</p>
   </template>
   
   <script>
      Polymer ({
         is: 'style-module', properties: {
            prop1: {
               type: String, value: 'Welcome to Tutorialspoint!!',
            },
         },
      });
   </script>
</dom-module>

Teraz utwórz jeszcze jeden plik o nazwie colors-module.html , który dostarcza moduły stylu do elementów, jak pokazano w poniższym kodzie.

<link rel = "import" href = "bower_components/polymer/polymer-element.html">

<dom-module id = 'colors-module'>
   <template>
      <style>
         p.color1 {
            color: #EA5AA5;
         }
         p.color2 {
            color: #4B61EA;
         }
         p.color3 {
            color: #D3AA0A;
         }
      </style>
   </template>
</dom-module>

Uruchom aplikację i przejdź do http://127.0.0.1:8081/. Poniżej będzie wynik.

Użyj właściwości niestandardowych

Niestandardowe właściwości CSS mogą służyć do stylizacji wyglądu elementu w aplikacji za pomocą elementu Polymer. Właściwości niestandardowe zapewniają kaskadowe zmienne CSS, których można używać poza środowiskiem elementów niestandardowych, aby nie rozpraszać danych stylu w arkuszu stylów.

Właściwości niestandardowe można definiować podobnie do standardowych właściwości CSS, które dziedziczą po utworzonym drzewie DOM. W poprzednim przykładzie możesz zobaczyć niestandardowe właściwości CSS zdefiniowane dla elementów.

W przypadku dziedziczenia CSS, jeśli nie ma zdefiniowanego stylu dla elementu, odziedziczy on styl po swoim rodzicu, jak pokazano w poniższym kodzie.

<link rel = "import" href = "components/polymer/myelement-style.html">
<myelement-style>
   <style is = "myelement-style">
      p {
         color: var(--paper-red-900);
      }
      paper-checkbox {
         --paper-checkbox-checked-color: var(--paper-red-900);
      }
   </style>
</myelement-style>

<body>
   <p><paper-checkbox>Check Here</paper-checkbox></p>
</body>