1/*
2 * Copyright (C) 1999 Lars Knoll (knoll@kde.org)
3 * (C) 1999 Antti Koivisto (koivisto@kde.org)
4 * (C) 2001 Dirk Mueller (mueller@kde.org)
5 * Copyright (C) 2004-2018 Apple Inc. All rights reserved.
6 *
7 * This library is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Library General Public
9 * License as published by the Free Software Foundation; either
10 * version 2 of the License, or (at your option) any later version.
11 *
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Library General Public License for more details.
16 *
17 * You should have received a copy of the GNU Library General Public License
18 * along with this library; see the file COPYING.LIB. If not, write to
19 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
20 * Boston, MA 02110-1301, USA.
21 */
22
23#include "config.h"
24#include "DocumentFragment.h"
25
26#include "Document.h"
27#include "ElementDescendantIterator.h"
28#include "HTMLDocumentParser.h"
29#include "Page.h"
30#include "XMLDocumentParser.h"
31#include <wtf/IsoMallocInlines.h>
32
33namespace WebCore {
34
35WTF_MAKE_ISO_ALLOCATED_IMPL(DocumentFragment);
36
37DocumentFragment::DocumentFragment(Document& document, ConstructionType constructionType)
38 : ContainerNode(document, constructionType)
39{
40}
41
42Ref<DocumentFragment> DocumentFragment::create(Document& document)
43{
44 return adoptRef(*new DocumentFragment(document, Node::CreateDocumentFragment));
45}
46
47String DocumentFragment::nodeName() const
48{
49 return "#document-fragment"_s;
50}
51
52Node::NodeType DocumentFragment::nodeType() const
53{
54 return DOCUMENT_FRAGMENT_NODE;
55}
56
57bool DocumentFragment::childTypeAllowed(NodeType type) const
58{
59 switch (type) {
60 case ELEMENT_NODE:
61 case PROCESSING_INSTRUCTION_NODE:
62 case COMMENT_NODE:
63 case TEXT_NODE:
64 case CDATA_SECTION_NODE:
65 return true;
66 default:
67 return false;
68 }
69}
70
71Ref<Node> DocumentFragment::cloneNodeInternal(Document& targetDocument, CloningOperation type)
72{
73 Ref<DocumentFragment> clone = create(targetDocument);
74 switch (type) {
75 case CloningOperation::OnlySelf:
76 case CloningOperation::SelfWithTemplateContent:
77 break;
78 case CloningOperation::Everything:
79 cloneChildNodes(clone);
80 break;
81 }
82 return clone;
83}
84
85void DocumentFragment::parseHTML(const String& source, Element* contextElement, ParserContentPolicy parserContentPolicy)
86{
87 ASSERT(contextElement);
88 HTMLDocumentParser::parseDocumentFragment(source, *this, *contextElement, parserContentPolicy);
89}
90
91bool DocumentFragment::parseXML(const String& source, Element* contextElement, ParserContentPolicy parserContentPolicy)
92{
93 return XMLDocumentParser::parseDocumentFragment(source, *this, contextElement, parserContentPolicy);
94}
95
96Element* DocumentFragment::getElementById(const AtomString& id) const
97{
98 if (id.isNull())
99 return nullptr;
100
101 // Fast path for ShadowRoot, where we are both a DocumentFragment and a TreeScope.
102 if (isTreeScope())
103 return treeScope().getElementById(id);
104
105 // Otherwise, fall back to iterating all of the element descendants.
106 for (auto& element : elementDescendants(*this)) {
107 if (element.getIdAttribute() == id)
108 return const_cast<Element*>(&element);
109 }
110
111 return nullptr;
112}
113
114}
115