2017-05-07 4 views
5

ich ein benutzerdefiniertes Element wie so definiert haben:Fehlgeschlagen ‚CustomElement‘ Fehler zu konstruieren, wenn der JavaScript-Datei in den Kopf gesetzt wird

class SquareLetter extends HTMLElement { 
    constructor() { 
     super(); 
     this.className = getRandomColor(); 
    } 
} 
customElements.define("square-letter", SquareLetter); 

Wenn die JavaScript-Datei in HTML <head>-Tag enthalten ist, die Chrome-Konsole meldet diesen Fehler :

Uncaught DOMException: Failed to construct 'CustomElement': The result must not have attributes

Aber wenn die JavaScript-Datei vor dem </body> End-Tag enthalten ist, funktioniert alles einwandfrei. Was ist der Grund?

<head> 
    <script src="js/SquareLetter.js"></script> <!-- here --> 
</head> 
<body> 
    <square-letter>A</square-letter> 
    <script src="js/SquareLetter.js"></script> <!-- or here --> 
</body> 
+3

Mögliches Duplikat von [Zugriff auf Attribute eines benutzerdefinierten Elements aus seinem Konstruktor nicht möglich] (http://stackoverflow.com/questions/42251094/cannot-access-attributes-of-a-custom-element-from-its-constructor) – Supersharp

Antwort

6

Der Fehler korrekt geändert werden soll, und in beiden Fällen auftreten könnten. Sie haben Glück, da einige aktuelle Implementierungen von benutzerdefinierten Elementen diese Anforderung nicht erzwingen.

Der Konstruktor für ein benutzerdefiniertes Element soll sein DOM weder lesen noch schreiben. Es sollte keine untergeordneten Elemente erstellen oder Attribute ändern. Diese Arbeit muss später ausgeführt werden, normalerweise in einer connectedCallback()-Methode (beachten Sie jedoch, dass connectedCallback() mehrere Male aufgerufen werden kann, wenn das Element entfernt und erneut zum DOM hinzugefügt wird. Sie müssen dies möglicherweise überprüfen oder Änderungen in a rückgängig machen disconnectedCallback()).

Zitieren die WHATWG HTML-Spezifikation, Schwerpunkt Mine:

§ 4.13.2 Requirements for custom element constructors :

When authoring custom element constructors, authors are bound by the following conformance requirements:

  • A parameter-less call to super() must be the first statement in the constructor body, to establish the correct prototype chain and this value before any further code is run.

  • A return statement must not appear anywhere inside the constructor body, unless it is a simple early-return (return or return this).

  • The constructor must not use the document.write() or document.open() methods.

  • The element's attributes and children must not be inspected, as in the non-upgrade case none will be present, and relying on upgrades makes the element less usable.

  • The element must not gain any attributes or children, as this violates the expectations of consumers who use the createElement or createElementNS methods.

  • In general, work should be deferred to connectedCallback as much as possible—especially work involving fetching resources or rendering. However, note that connectedCallback can be called more than once, so any initialization work that is truly one-time will need a guard to prevent it from running twice.

  • In general, the constructor should be used to set up initial state and default values, and to set up event listeners and possibly a shadow root.

Several of these requirements are checked during element creation, either directly or indirectly, and failing to follow them will result in a custom element that cannot be instantiated by the parser or DOM APIs. This is true even if the work is done inside a constructor-initiated microtask, as a microtask checkpoint can occur immediately after construction.

Wenn Sie das Skript nach dem Elemente im DOM bewegen, Sie führen die vorhandenen Elemente durch den „Upgrade“ Prozess zu gehen. Wenn sich das Skript vor dem Element befindet, durchläuft das Element den Standardkonstruktionsprozess. Dieser Unterschied verursacht offensichtlich, dass der Fehler nicht in allen Fällen auftritt, aber dies ist ein Implementierungsdetail und kann sich ändern.

-1

Das Element wurde noch nicht geladen, so dass es nicht geändert werden kann, um das Skript Laden unter das Element bedeutet, es kann

Verwandte Themen