Chromium Code Reviews| Index: third_party/WebKit/Source/core/html/parser/HTMLConstructionSite.cpp | 
| diff --git a/third_party/WebKit/Source/core/html/parser/HTMLConstructionSite.cpp b/third_party/WebKit/Source/core/html/parser/HTMLConstructionSite.cpp | 
| index 264f2e749beb812b43f3524c10dc82614a08633d..10e6ee0772764569bcba5d51582c7abb5bfa6bab 100644 | 
| --- a/third_party/WebKit/Source/core/html/parser/HTMLConstructionSite.cpp | 
| +++ b/third_party/WebKit/Source/core/html/parser/HTMLConstructionSite.cpp | 
| @@ -677,14 +677,14 @@ void HTMLConstructionSite::InsertCommentOnHTMLHtmlElement( | 
| void HTMLConstructionSite::InsertHTMLHeadElement(AtomicHTMLToken* token) { | 
| DCHECK(!ShouldFosterParent()); | 
| - head_ = HTMLStackItem::Create(CreateHTMLElement(token), token); | 
| + head_ = HTMLStackItem::Create(CreateElement(token, xhtmlNamespaceURI), token); | 
| AttachLater(CurrentNode(), head_->GetElement()); | 
| open_elements_.PushHTMLHeadElement(head_); | 
| } | 
| void HTMLConstructionSite::InsertHTMLBodyElement(AtomicHTMLToken* token) { | 
| DCHECK(!ShouldFosterParent()); | 
| - HTMLElement* body = CreateHTMLElement(token); | 
| + Element* body = CreateElement(token, xhtmlNamespaceURI); | 
| AttachLater(CurrentNode(), body); | 
| open_elements_.PushHTMLBodyElement(HTMLStackItem::Create(body, token)); | 
| if (document_) | 
| @@ -693,7 +693,7 @@ void HTMLConstructionSite::InsertHTMLBodyElement(AtomicHTMLToken* token) { | 
| void HTMLConstructionSite::InsertHTMLFormElement(AtomicHTMLToken* token, | 
| bool is_demoted) { | 
| - HTMLElement* element = CreateHTMLElement(token); | 
| + Element* element = CreateElement(token, xhtmlNamespaceURI); | 
| DCHECK(isHTMLFormElement(element)); | 
| HTMLFormElement* form_element = toHTMLFormElement(element); | 
| if (!OpenElements()->HasTemplateInHTMLScope()) | 
| @@ -704,7 +704,7 @@ void HTMLConstructionSite::InsertHTMLFormElement(AtomicHTMLToken* token, | 
| } | 
| void HTMLConstructionSite::InsertHTMLElement(AtomicHTMLToken* token) { | 
| - HTMLElement* element = CreateHTMLElement(token); | 
| + Element* element = CreateElement(token, xhtmlNamespaceURI); | 
| AttachLater(CurrentNode(), element); | 
| open_elements_.Push(HTMLStackItem::Create(element, token)); | 
| } | 
| @@ -715,7 +715,7 @@ void HTMLConstructionSite::InsertSelfClosingHTMLElementDestroyingToken( | 
| // Normally HTMLElementStack is responsible for calling finishParsingChildren, | 
| // but self-closing elements are never in the element stack so the stack | 
| // doesn't get a chance to tell them that we're done parsing their children. | 
| - AttachLater(CurrentNode(), CreateHTMLElement(token), true); | 
| + AttachLater(CurrentNode(), CreateElement(token, xhtmlNamespaceURI), true); | 
| // FIXME: Do we want to acknowledge the token's self-closing flag? | 
| // http://www.whatwg.org/specs/web-apps/current-work/multipage/tokenization.html#acknowledge-self-closing-flag | 
| } | 
| @@ -842,16 +842,6 @@ CreateElementFlags HTMLConstructionSite::GetCreateElementFlags() const { | 
| return is_parsing_fragment_ ? kCreatedByFragmentParser : kCreatedByParser; | 
| } | 
| -Element* HTMLConstructionSite::CreateElement( | 
| - AtomicHTMLToken* token, | 
| - const AtomicString& namespace_uri) { | 
| - QualifiedName tag_name(g_null_atom, token->GetName(), namespace_uri); | 
| - Element* element = OwnerDocumentForCurrentNode().createElement( | 
| - tag_name, GetCreateElementFlags()); | 
| - SetAttributes(element, token, parser_content_policy_); | 
| - return element; | 
| -} | 
| - | 
| inline Document& HTMLConstructionSite::OwnerDocumentForCurrentNode() { | 
| if (isHTMLTemplateElement(*CurrentNode())) | 
| return toHTMLTemplateElement(CurrentElement())->content()->GetDocument(); | 
| @@ -885,22 +875,15 @@ CustomElementDefinition* HTMLConstructionSite::LookUpCustomElementDefinition( | 
| // "create an element for a token" | 
| // https://html.spec.whatwg.org/multipage/syntax.html#create-an-element-for-the-token | 
| -// TODO(dominicc): When form association is separate from creation, unify this | 
| -// with foreign element creation. Add a namespace parameter and check for HTML | 
| -// namespace to lookupCustomElementDefinition. | 
| -HTMLElement* HTMLConstructionSite::CreateHTMLElement(AtomicHTMLToken* token) { | 
| +Element* HTMLConstructionSite::CreateElement( | 
| + AtomicHTMLToken* token, | 
| + const AtomicString& namespace_uri) { | 
| // "1. Let document be intended parent's node document." | 
| Document& document = OwnerDocumentForCurrentNode(); | 
| - // Only associate the element with the current form if we're creating the new | 
| - // element in a document with a browsing context (rather than in <template> | 
| - // contents). | 
| - // TODO(dominicc): Change form to happen after element creation when | 
| - // implementing customized built-in elements. | 
| - HTMLFormElement* form = document.GetFrame() ? form_.Get() : nullptr; | 
| - | 
| // "2. Let local name be the tag name of the token." | 
| - // "3. Let is be the value of the "is" attribute in the giev token ..." etc. | 
| + QualifiedName tag_name(g_null_atom, token->GetName(), namespace_uri); | 
| + // "3. Let is be the value of the "is" attribute in the given token ..." etc. | 
| // "4. Let definition be the result of looking up a custom element ..." etc. | 
| CustomElementDefinition* definition = | 
| is_parsing_fragment_ ? nullptr | 
| @@ -910,7 +893,7 @@ HTMLElement* HTMLConstructionSite::CreateHTMLElement(AtomicHTMLToken* token) { | 
| // be true." | 
| bool will_execute_script = definition && !is_parsing_fragment_; | 
| - HTMLElement* element; | 
| + Element* element; | 
| if (will_execute_script) { | 
| // "6.1 Increment the document's throw-on-dynamic-insertion counter." | 
| @@ -931,9 +914,7 @@ HTMLElement* HTMLConstructionSite::CreateHTMLElement(AtomicHTMLToken* token) { | 
| CEReactionsScope reactions; | 
| // 7. | 
| - QualifiedName element_q_name(g_null_atom, token->GetName(), | 
| - HTMLNames::xhtmlNamespaceURI); | 
| - element = definition->CreateElementSync(document, element_q_name); | 
| + element = definition->CreateElementSync(document, tag_name); | 
| // "8. Append each attribute in the given token to element." We don't use | 
| // setAttributes here because the custom element constructor may have | 
| @@ -945,27 +926,66 @@ HTMLElement* HTMLConstructionSite::CreateHTMLElement(AtomicHTMLToken* token) { | 
| // and ThrowOnDynamicMarkupInsertionCountIncrementer destructors implement | 
| // steps 9.1-3. | 
| } else { | 
| - // FIXME: This can't use HTMLConstructionSite::createElement because we have | 
| - // to pass the current form element. We should rework form association to | 
| - // occur after construction to allow better code sharing here. | 
| - element = HTMLElementFactory::createHTMLElement(token->GetName(), document, | 
| - GetCreateElementFlags()); | 
| - if (FormAssociated* form_associated_element = | 
| - element->ToFormAssociatedOrNull()) { | 
| - form_associated_element->AssociateWith(form); | 
| - } | 
| + element = document.createElement(tag_name, GetCreateElementFlags()); | 
| // Definition for the created element does not exist here and it cannot be | 
| // custom or failed. | 
| DCHECK_NE(element->GetCustomElementState(), CustomElementState::kCustom); | 
| DCHECK_NE(element->GetCustomElementState(), CustomElementState::kFailed); | 
| + // TODO(dominicc): Move these steps so they happen for custom | 
| + // elements as well as built-in elements when customized built in | 
| + // elements are implemented for resettable, listed elements. | 
| + | 
| + // 10. If element has an xmlns attribute in the XMLNS namespace | 
| + // whose value is not exactly the same as the element's namespace, | 
| + // that is a parse error. Similarly, if element has an xmlns:xlink | 
| + // attribute in the XMLNS namespace whose value is not the XLink | 
| + // Namespace, that is a parse error. | 
| + | 
| + // TODO(dominicc): Implement step 10 when the HTML parser does | 
| + // something useful with parse errors. | 
| 
 
kouhei (in TOK)
2017/04/26 04:24:54
FYI: I think we are going to ignore all parse erro
 
 | 
| + | 
| + // 11. If element is a resettable element, invoke its reset | 
| + // algorithm. (This initializes the element's value and | 
| + // checkedness based on the element's attributes.) | 
| + // TODO(dominicc): Implement step 11, resettable elements. | 
| + | 
| + // 12. If element is a form-associated element, and the form | 
| + // element pointer is not null, and there is no template element | 
| + // on the stack of open elements, ... | 
| + FormAssociated* form_associated_element = | 
| + element->IsHTMLElement() | 
| + ? ToHTMLElement(element)->ToFormAssociatedOrNull() | 
| + : nullptr; | 
| + if (form_associated_element && document.GetFrame() && form_.Get()) { | 
| + // ... and element is either not listed or doesn't have a form | 
| + // attribute, and the intended parent is in the same tree as the | 
| + // element pointed to by the form element pointer, associate | 
| + // element with the form element pointed to by the form element | 
| + // pointer, and suppress the running of the reset the form owner | 
| + // algorithm when the parser subsequently attempts to insert the | 
| + // element. | 
| + | 
| + // TODO(dominicc): There are many differences to the spec here; | 
| + // some of them are observable: | 
| + // | 
| + // - The HTML spec tracks whether there is a template element on | 
| + // the stack both for manipulating the form element pointer | 
| + // and using it here. | 
| + // - FormAssociated::AssociateWith implementations don't do the | 
| + // "same tree" check; for example | 
| + // HTMLImageElement::AssociateWith just checks whether the form | 
| + // is in *a* tree. This check should be done here consistently. | 
| + // - ListedElement is a mixin; add IsListedElement and skip | 
| + // setting the form for listed attributes with form=. Instead | 
| + // we set attributes (step 8) out of order, after this step, | 
| + // to reset the form association. | 
| + form_associated_element->AssociateWith(form_.Get()); | 
| + } | 
| // "8. Append each attribute in the given token to element." | 
| SetAttributes(element, token, parser_content_policy_); | 
| } | 
| - // TODO(dominicc): Implement steps 10-12 when customized built-in elements are | 
| - // implemented. | 
| - | 
| return element; | 
| } | 
| @@ -975,10 +995,7 @@ HTMLStackItem* HTMLConstructionSite::CreateElementFromSavedToken( | 
| // NOTE: Moving from item -> token -> item copies the Attribute vector twice! | 
| AtomicHTMLToken fake_token(HTMLToken::kStartTag, item->LocalName(), | 
| item->Attributes()); | 
| - if (item->NamespaceURI() == HTMLNames::xhtmlNamespaceURI) | 
| - element = CreateHTMLElement(&fake_token); | 
| - else | 
| - element = CreateElement(&fake_token, item->NamespaceURI()); | 
| + element = CreateElement(&fake_token, item->NamespaceURI()); | 
| return HTMLStackItem::Create(element, &fake_token, item->NamespaceURI()); | 
| } |