OLD | NEW |
1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "core/dom/custom/CustomElementDefinition.h" | 5 #include "core/dom/custom/CustomElementDefinition.h" |
6 | 6 |
| 7 #include "core/dom/ExceptionCode.h" |
7 #include "core/dom/custom/CEReactionsScope.h" | 8 #include "core/dom/custom/CEReactionsScope.h" |
8 #include "core/dom/custom/CustomElement.h" | 9 #include "core/dom/custom/CustomElement.h" |
9 #include "core/dom/custom/CustomElementAttributeChangedCallbackReaction.h" | 10 #include "core/dom/custom/CustomElementAttributeChangedCallbackReaction.h" |
10 #include "core/dom/custom/CustomElementConnectedCallbackReaction.h" | 11 #include "core/dom/custom/CustomElementConnectedCallbackReaction.h" |
11 #include "core/dom/custom/CustomElementDisconnectedCallbackReaction.h" | 12 #include "core/dom/custom/CustomElementDisconnectedCallbackReaction.h" |
12 #include "core/dom/custom/CustomElementUpgradeReaction.h" | 13 #include "core/dom/custom/CustomElementUpgradeReaction.h" |
| 14 #include "core/html/HTMLElement.h" |
13 | 15 |
14 namespace blink { | 16 namespace blink { |
15 | 17 |
16 CustomElementDefinition::CustomElementDefinition( | 18 CustomElementDefinition::CustomElementDefinition( |
17 const CustomElementDescriptor& descriptor) | 19 const CustomElementDescriptor& descriptor) |
18 : m_descriptor(descriptor) | 20 : m_descriptor(descriptor) |
19 { | 21 { |
20 } | 22 } |
21 | 23 |
22 CustomElementDefinition::~CustomElementDefinition() | 24 CustomElementDefinition::~CustomElementDefinition() |
23 { | 25 { |
24 } | 26 } |
25 | 27 |
26 DEFINE_TRACE(CustomElementDefinition) | 28 DEFINE_TRACE(CustomElementDefinition) |
27 { | 29 { |
28 visitor->trace(m_constructionStack); | 30 visitor->trace(m_constructionStack); |
29 } | 31 } |
30 | 32 |
| 33 static String errorMessageForConstructorResult(Element* element, |
| 34 Document& document, const QualifiedName& tagName) |
| 35 { |
| 36 // https://dom.spec.whatwg.org/#concept-create-element |
| 37 // 6.1.4. If result's attribute list is not empty, then throw a NotSupported
Error. |
| 38 if (element->hasAttributes()) |
| 39 return "The result must not have attributes"; |
| 40 // 6.1.5. If result has children, then throw a NotSupportedError. |
| 41 if (element->hasChildren()) |
| 42 return "The result must not have children"; |
| 43 // 6.1.6. If result's parent is not null, then throw a NotSupportedError. |
| 44 if (element->parentNode()) |
| 45 return "The result must not have a parent"; |
| 46 // 6.1.7. If result's node document is not document, then throw a NotSupport
edError. |
| 47 if (&element->document() != &document) |
| 48 return "The result must be in the same document"; |
| 49 // 6.1.8. If result's namespace is not the HTML namespace, then throw a NotS
upportedError. |
| 50 if (element->namespaceURI() != HTMLNames::xhtmlNamespaceURI) |
| 51 return "The result must have HTML namespace"; |
| 52 // 6.1.9. If result's local name is not equal to localName, then throw a Not
SupportedError. |
| 53 if (element->localName() != tagName.localName()) |
| 54 return "The result must have the same localName"; |
| 55 return String(); |
| 56 } |
| 57 |
| 58 void CustomElementDefinition::checkConstructorResult(Element* element, |
| 59 Document& document, const QualifiedName& tagName, |
| 60 ExceptionState& exceptionState) |
| 61 { |
| 62 // https://dom.spec.whatwg.org/#concept-create-element |
| 63 // 6.1.3. If result does not implement the HTMLElement interface, throw a Ty
peError. |
| 64 // See https://github.com/whatwg/html/issues/1402 for more clarifications. |
| 65 if (!element || !element->isHTMLElement()) { |
| 66 exceptionState.throwTypeError("The result must implement HTMLElement int
erface"); |
| 67 return; |
| 68 } |
| 69 |
| 70 // 6.1.4. through 6.1.9. |
| 71 const String message = errorMessageForConstructorResult(element, document, t
agName); |
| 72 if (!message.isEmpty()) |
| 73 exceptionState.throwDOMException(NotSupportedError, message); |
| 74 } |
| 75 |
| 76 HTMLElement* CustomElementDefinition::createElementAsync(Document& document, con
st QualifiedName& tagName) |
| 77 { |
| 78 // https://dom.spec.whatwg.org/#concept-create-element |
| 79 // 6. If definition is non-null, then: |
| 80 // 6.2. If the synchronous custom elements flag is not set: |
| 81 // 6.2.1. Set result to a new element that implements the HTMLElement |
| 82 // interface, with no attributes, namespace set to the HTML namespace, |
| 83 // namespace prefix set to prefix, local name set to localName, custom |
| 84 // element state set to "undefined", and node document set to document. |
| 85 HTMLElement* element = HTMLElement::create(tagName, document); |
| 86 element->setCustomElementState(CustomElementState::Undefined); |
| 87 // 6.2.2. Enqueue a custom element upgrade reaction given result and |
| 88 // definition. |
| 89 enqueueUpgradeReaction(element); |
| 90 return element; |
| 91 } |
| 92 |
31 // https://html.spec.whatwg.org/multipage/scripting.html#concept-upgrade-an-elem
ent | 93 // https://html.spec.whatwg.org/multipage/scripting.html#concept-upgrade-an-elem
ent |
32 void CustomElementDefinition::upgrade(Element* element) | 94 void CustomElementDefinition::upgrade(Element* element) |
33 { | 95 { |
34 // TODO(kojii): This should be reversed by exposing observedAttributes from | 96 // TODO(kojii): This should be reversed by exposing observedAttributes from |
35 // ScriptCustomElementDefinition, because Element::attributes() requires | 97 // ScriptCustomElementDefinition, because Element::attributes() requires |
36 // attribute synchronizations, and generally elements have more attributes | 98 // attribute synchronizations, and generally elements have more attributes |
37 // than custom elements observe. | 99 // than custom elements observe. |
38 for (const auto& attribute : element->attributes()) { | 100 for (const auto& attribute : element->attributes()) { |
39 if (hasAttributeChangedCallback(attribute.name())) | 101 if (hasAttributeChangedCallback(attribute.name())) |
40 enqueueAttributeChangedCallback(element, attribute.name(), nullAtom,
attribute.value()); | 102 enqueueAttributeChangedCallback(element, attribute.name(), nullAtom,
attribute.value()); |
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
84 } | 146 } |
85 | 147 |
86 void CustomElementDefinition::enqueueAttributeChangedCallback(Element* element, | 148 void CustomElementDefinition::enqueueAttributeChangedCallback(Element* element, |
87 const QualifiedName& name, | 149 const QualifiedName& name, |
88 const AtomicString& oldValue, const AtomicString& newValue) | 150 const AtomicString& oldValue, const AtomicString& newValue) |
89 { | 151 { |
90 enqueueReaction(element, new CustomElementAttributeChangedCallbackReaction(t
his, name, oldValue, newValue)); | 152 enqueueReaction(element, new CustomElementAttributeChangedCallbackReaction(t
his, name, oldValue, newValue)); |
91 } | 153 } |
92 | 154 |
93 } // namespace blink | 155 } // namespace blink |
OLD | NEW |