Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(79)

Side by Side Diff: third_party/WebKit/Source/core/dom/custom/CustomElementDefinition.cpp

Issue 2060753002: Implement script-side of callback reactions for Custom Elements V1 (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@callback-ce
Patch Set: dominicc review Created 4 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
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/Attr.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"
13 14
14 namespace blink { 15 namespace blink {
15 16
16 CustomElementDefinition::CustomElementDefinition( 17 CustomElementDefinition::CustomElementDefinition(
17 const CustomElementDescriptor& descriptor) 18 const CustomElementDescriptor& descriptor)
18 : m_descriptor(descriptor) 19 : m_descriptor(descriptor)
19 { 20 {
20 } 21 }
21 22
23 CustomElementDefinition::CustomElementDefinition(
24 const CustomElementDescriptor& descriptor,
25 const HashSet<AtomicString>& observedAttributes)
26 : m_descriptor(descriptor)
27 , m_observedAttributes(observedAttributes)
28 {
29 }
30
22 CustomElementDefinition::~CustomElementDefinition() 31 CustomElementDefinition::~CustomElementDefinition()
23 { 32 {
24 } 33 }
25 34
26 DEFINE_TRACE(CustomElementDefinition) 35 DEFINE_TRACE(CustomElementDefinition)
27 { 36 {
28 visitor->trace(m_constructionStack); 37 visitor->trace(m_constructionStack);
29 } 38 }
30 39
31 // https://html.spec.whatwg.org/multipage/scripting.html#concept-upgrade-an-elem ent 40 // https://html.spec.whatwg.org/multipage/scripting.html#concept-upgrade-an-elem ent
32 void CustomElementDefinition::upgrade(Element* element) 41 void CustomElementDefinition::upgrade(Element* element)
33 { 42 {
34 // TODO(kojii): This should be reversed by exposing observedAttributes from 43 if (!m_observedAttributes.isEmpty())
35 // ScriptCustomElementDefinition, because Element::attributes() requires 44 enqueueAttributeChangedCallbackForAllAttributes(element);
36 // attribute synchronizations, and generally elements have more attributes
37 // than custom elements observe.
38 for (const auto& attribute : element->attributes()) {
39 if (hasAttributeChangedCallback(attribute.name()))
40 enqueueAttributeChangedCallback(element, attribute.name(), nullAtom, attribute.value());
41 }
42 45
43 if (element->inShadowIncludingDocument() && hasConnectedCallback()) 46 if (element->inShadowIncludingDocument() && hasConnectedCallback())
44 enqueueConnectedCallback(element); 47 enqueueConnectedCallback(element);
45 48
46 m_constructionStack.append(element); 49 m_constructionStack.append(element);
47 size_t depth = m_constructionStack.size(); 50 size_t depth = m_constructionStack.size();
48 51
49 bool succeeded = runConstructor(element); 52 bool succeeded = runConstructor(element);
50 53
51 // Pop the construction stack. 54 // Pop the construction stack.
52 if (m_constructionStack.last().get()) 55 if (m_constructionStack.last().get())
53 DCHECK_EQ(m_constructionStack.last(), element); 56 DCHECK_EQ(m_constructionStack.last(), element);
54 DCHECK_EQ(m_constructionStack.size(), depth); // It's a *stack*. 57 DCHECK_EQ(m_constructionStack.size(), depth); // It's a *stack*.
55 m_constructionStack.removeLast(); 58 m_constructionStack.removeLast();
56 59
57 if (!succeeded) 60 if (!succeeded)
58 return; 61 return;
59 62
60 CHECK(element->getCustomElementState() == CustomElementState::Custom); 63 CHECK(element->getCustomElementState() == CustomElementState::Custom);
61 } 64 }
62 65
66 bool CustomElementDefinition::hasAttributeChangedCallback(
67 const QualifiedName& name)
68 {
69 return m_observedAttributes.contains(name.localName());
70 }
71
63 static void enqueueReaction(Element* element, CustomElementReaction* reaction) 72 static void enqueueReaction(Element* element, CustomElementReaction* reaction)
64 { 73 {
65 // CEReactionsScope must be created by [CEReactions] in IDL, 74 // CEReactionsScope must be created by [CEReactions] in IDL,
66 // or callers must setup explicitly if it does not go through bindings. 75 // or callers must setup explicitly if it does not go through bindings.
67 DCHECK(CEReactionsScope::current()); 76 DCHECK(CEReactionsScope::current());
68 CEReactionsScope::current()->enqueue(element, reaction); 77 CEReactionsScope::current()->enqueue(element, reaction);
69 } 78 }
70 79
71 void CustomElementDefinition::enqueueUpgradeReaction(Element* element) 80 void CustomElementDefinition::enqueueUpgradeReaction(Element* element)
72 { 81 {
(...skipping 10 matching lines...) Expand all
83 enqueueReaction(element, new CustomElementDisconnectedCallbackReaction(this) ); 92 enqueueReaction(element, new CustomElementDisconnectedCallbackReaction(this) );
84 } 93 }
85 94
86 void CustomElementDefinition::enqueueAttributeChangedCallback(Element* element, 95 void CustomElementDefinition::enqueueAttributeChangedCallback(Element* element,
87 const QualifiedName& name, 96 const QualifiedName& name,
88 const AtomicString& oldValue, const AtomicString& newValue) 97 const AtomicString& oldValue, const AtomicString& newValue)
89 { 98 {
90 enqueueReaction(element, new CustomElementAttributeChangedCallbackReaction(t his, name, oldValue, newValue)); 99 enqueueReaction(element, new CustomElementAttributeChangedCallbackReaction(t his, name, oldValue, newValue));
91 } 100 }
92 101
102 void CustomElementDefinition::enqueueAttributeChangedCallbackForAllAttributes(
103 Element* element)
104 {
105 // Avoid synchronizing all attributes unless it is needed, while enqueing
106 // callbacks "in order" as defined in the spec.
107 // https://html.spec.whatwg.org/multipage/scripting.html#concept-upgrade-an- element
108 for (const AtomicString& name : m_observedAttributes)
109 element->synchronizeAttribute(name);
110 for (const auto& attribute : element->attributesWithoutUpdate()) {
111 if (hasAttributeChangedCallback(attribute.name())) {
112 enqueueAttributeChangedCallback(element, attribute.name(),
113 nullAtom, attribute.value());
114 }
115 }
116 }
117
93 } // namespace blink 118 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698