Upstream version 7.36.149.0
[platform/framework/web/crosswalk.git] / src / third_party / WebKit / Source / core / dom / Node.h
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, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All rights reserved.
6  * Copyright (C) 2008, 2009 Torch Mobile Inc. All rights reserved. (http://www.torchmobile.com/)
7  *
8  * This library is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU Library General Public
10  * License as published by the Free Software Foundation; either
11  * version 2 of the License, or (at your option) any later version.
12  *
13  * This library is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16  * Library General Public License for more details.
17  *
18  * You should have received a copy of the GNU Library General Public License
19  * along with this library; see the file COPYING.LIB.  If not, write to
20  * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
21  * Boston, MA 02110-1301, USA.
22  *
23  */
24
25 #ifndef Node_h
26 #define Node_h
27
28 #include "bindings/v8/ExceptionStatePlaceholder.h"
29 #include "bindings/v8/ScriptWrappable.h"
30 #include "core/dom/MutationObserver.h"
31 #include "core/dom/SimulatedClickOptions.h"
32 #include "core/dom/TreeScope.h"
33 #include "core/dom/TreeShared.h"
34 #include "core/editing/EditingBoundary.h"
35 #include "core/events/EventTarget.h"
36 #include "core/inspector/InspectorCounters.h"
37 #include "core/rendering/style/RenderStyleConstants.h"
38 #include "platform/geometry/LayoutRect.h"
39 #include "platform/heap/Handle.h"
40 #include "platform/weborigin/KURLHash.h"
41 #include "wtf/Forward.h"
42 #include "wtf/ListHashSet.h"
43 #include "wtf/text/AtomicString.h"
44
45 // This needs to be here because Document.h also depends on it.
46 #define DUMP_NODE_STATISTICS 0
47
48 namespace WebCore {
49
50 class Attribute;
51 class ClassCollection;
52 class ContainerNode;
53 class DOMSettableTokenList;
54 class Document;
55 class Element;
56 class Event;
57 class EventDispatchMediator;
58 class EventListener;
59 class ExceptionState;
60 class FloatPoint;
61 class LocalFrame;
62 class HTMLInputElement;
63 class IntRect;
64 class KeyboardEvent;
65 class NSResolver;
66 class NameNodeList;
67 class NamedNodeMap;
68 class NodeEventContext;
69 class NodeList;
70 class NodeListsNodeData;
71 class NodeRareData;
72 class PlatformGestureEvent;
73 class PlatformKeyboardEvent;
74 class PlatformMouseEvent;
75 class PlatformWheelEvent;
76 class QualifiedName;
77 class RadioNodeList;
78 class RegisteredEventListener;
79 class RenderBox;
80 class RenderBoxModelObject;
81 class RenderObject;
82 class RenderStyle;
83 class ShadowRoot;
84 class TagCollection;
85 class Text;
86 class TouchEvent;
87 class WeakNodeMap;
88
89 const int nodeStyleChangeShift = 19;
90
91 enum StyleChangeType {
92     NoStyleChange = 0,
93     LocalStyleChange = 1 << nodeStyleChangeShift,
94     SubtreeStyleChange = 2 << nodeStyleChangeShift,
95     NeedsReattachStyleChange = 3 << nodeStyleChangeShift,
96 };
97
98 class NodeRareDataBase {
99 public:
100     RenderObject* renderer() const { return m_renderer; }
101     void setRenderer(RenderObject* renderer) { m_renderer = renderer; }
102
103 protected:
104     NodeRareDataBase(RenderObject* renderer)
105         : m_renderer(renderer)
106     { }
107
108 private:
109     RenderObject* m_renderer;
110 };
111
112 class Node : public TreeSharedWillBeRefCountedGarbageCollected<Node>, public EventTarget, public ScriptWrappable {
113     friend class Document;
114     friend class TreeScope;
115     friend class TreeScopeAdopter;
116
117     DEFINE_EVENT_TARGET_REFCOUNTING(TreeSharedWillBeRefCountedGarbageCollected<Node>);
118 public:
119     enum NodeType {
120         ELEMENT_NODE = 1,
121         ATTRIBUTE_NODE = 2,
122         TEXT_NODE = 3,
123         CDATA_SECTION_NODE = 4,
124         PROCESSING_INSTRUCTION_NODE = 7,
125         COMMENT_NODE = 8,
126         DOCUMENT_NODE = 9,
127         DOCUMENT_TYPE_NODE = 10,
128         DOCUMENT_FRAGMENT_NODE = 11,
129     };
130
131     // Entity, EntityReference, Notation, and XPathNamespace nodes are impossible to create in Blink.
132     // But for compatibility reasons we want these enum values exist in JS, and this enum makes the bindings
133     // generation not complain about ENTITY_REFERENCE_NODE being missing from the implementation
134     // while not requiring all switch(NodeType) blocks to include this deprecated constant.
135     enum DeprecatedNodeType {
136         ENTITY_REFERENCE_NODE = 5,
137         ENTITY_NODE = 6,
138         NOTATION_NODE = 12,
139         XPATH_NAMESPACE_NODE = 13,
140     };
141
142     enum DocumentPosition {
143         DOCUMENT_POSITION_EQUIVALENT = 0x00,
144         DOCUMENT_POSITION_DISCONNECTED = 0x01,
145         DOCUMENT_POSITION_PRECEDING = 0x02,
146         DOCUMENT_POSITION_FOLLOWING = 0x04,
147         DOCUMENT_POSITION_CONTAINS = 0x08,
148         DOCUMENT_POSITION_CONTAINED_BY = 0x10,
149         DOCUMENT_POSITION_IMPLEMENTATION_SPECIFIC = 0x20,
150     };
151
152 #if !ENABLE(OILPAN)
153     // All Nodes are placed in their own heap partition for security.
154     // See http://crbug.com/246860 for detail.
155     void* operator new(size_t);
156     void operator delete(void*);
157 #endif
158
159     static void dumpStatistics();
160
161     virtual ~Node();
162
163     // DOM methods & attributes for Node
164
165     bool hasTagName(const QualifiedName&) const;
166     virtual String nodeName() const = 0;
167     virtual String nodeValue() const;
168     virtual void setNodeValue(const String&);
169     virtual NodeType nodeType() const = 0;
170     ContainerNode* parentNode() const;
171     Element* parentElement() const;
172     ContainerNode* parentElementOrShadowRoot() const;
173     Node* previousSibling() const { return m_previous; }
174     Node* nextSibling() const { return m_next; }
175     PassRefPtr<NodeList> childNodes();
176     Node* firstChild() const;
177     Node* lastChild() const;
178
179     void remove(ExceptionState&);
180
181     Node* pseudoAwareNextSibling() const;
182     Node* pseudoAwarePreviousSibling() const;
183     Node* pseudoAwareFirstChild() const;
184     Node* pseudoAwareLastChild() const;
185
186     virtual KURL baseURI() const;
187
188     // These should all actually return a node, but this is only important for language bindings,
189     // which will already know and hold a ref on the right node to return.
190     void insertBefore(PassRefPtr<Node> newChild, Node* refChild, ExceptionState& = ASSERT_NO_EXCEPTION);
191     void replaceChild(PassRefPtr<Node> newChild, Node* oldChild, ExceptionState& = ASSERT_NO_EXCEPTION);
192     void removeChild(Node* child, ExceptionState&);
193     void appendChild(PassRefPtr<Node> newChild, ExceptionState& = ASSERT_NO_EXCEPTION);
194
195     bool hasChildren() const { return firstChild(); }
196     virtual PassRefPtr<Node> cloneNode(bool deep = false) = 0;
197     virtual const AtomicString& localName() const;
198     virtual const AtomicString& namespaceURI() const;
199     void normalize();
200
201     bool isSameNode(Node* other) const { return this == other; }
202     bool isEqualNode(Node*) const;
203     bool isDefaultNamespace(const AtomicString& namespaceURI) const;
204     const AtomicString& lookupPrefix(const AtomicString& namespaceURI) const;
205     const AtomicString& lookupNamespaceURI(const String& prefix) const;
206
207     String textContent(bool convertBRsToNewlines = false) const;
208     void setTextContent(const String&);
209
210     Node& lastDescendantOrSelf() const;
211
212     // Other methods (not part of DOM)
213
214     bool isElementNode() const { return getFlag(IsElementFlag); }
215     bool isContainerNode() const { return getFlag(IsContainerFlag); }
216     bool isTextNode() const { return getFlag(IsTextFlag); }
217     bool isHTMLElement() const { return getFlag(IsHTMLFlag); }
218     bool isSVGElement() const { return getFlag(IsSVGFlag); }
219
220     bool isPseudoElement() const { return pseudoId() != NOPSEUDO; }
221     bool isBeforePseudoElement() const { return pseudoId() == BEFORE; }
222     bool isAfterPseudoElement() const { return pseudoId() == AFTER; }
223     PseudoId pseudoId() const { return (isElementNode() && hasCustomStyleCallbacks()) ? customPseudoId() : NOPSEUDO; }
224
225     bool isCustomElement() const { return getFlag(CustomElementFlag); }
226     enum CustomElementState {
227         NotCustomElement  = 0,
228         WaitingForUpgrade = 1 << 0,
229         Upgraded          = 1 << 1
230     };
231     CustomElementState customElementState() const
232     {
233         return isCustomElement()
234             ? (getFlag(CustomElementUpgradedFlag) ? Upgraded : WaitingForUpgrade)
235             : NotCustomElement;
236     }
237     void setCustomElementState(CustomElementState newState);
238
239     virtual bool isMediaControlElement() const { return false; }
240     virtual bool isMediaControls() const { return false; }
241     virtual bool isVTTElement() const { return false; }
242     virtual bool isAttributeNode() const { return false; }
243     virtual bool isCharacterDataNode() const { return false; }
244     virtual bool isFrameOwnerElement() const { return false; }
245
246     // StyledElements allow inline style (style="border: 1px"), presentational attributes (ex. color),
247     // class names (ex. class="foo bar") and other non-basic styling features. They and also control
248     // if this element can participate in style sharing.
249     //
250     // FIXME: The only things that ever go through StyleResolver that aren't StyledElements are
251     // PseudoElements and VTTElements. It's possible we can just eliminate all the checks
252     // since those elements will never have class names, inline style, or other things that
253     // this apparently guards against.
254     bool isStyledElement() const { return isHTMLElement() || isSVGElement(); }
255
256     bool isDocumentNode() const;
257     bool isTreeScope() const { return &treeScope().rootNode() == this; }
258     bool isDocumentFragment() const { return getFlag(IsDocumentFragmentFlag); }
259     bool isShadowRoot() const { return isDocumentFragment() && isTreeScope(); }
260     bool isInsertionPoint() const { return getFlag(IsInsertionPointFlag); }
261
262     bool hasCustomStyleCallbacks() const { return getFlag(HasCustomStyleCallbacksFlag); }
263
264     bool hasSyntheticAttrChildNodes() const { return getFlag(HasSyntheticAttrChildNodesFlag); }
265     void setHasSyntheticAttrChildNodes(bool flag) { setFlag(flag, HasSyntheticAttrChildNodesFlag); }
266
267     // If this node is in a shadow tree, returns its shadow host. Otherwise, returns 0.
268     Element* shadowHost() const;
269     // If this node is in a shadow tree, returns its shadow host. Otherwise, returns this.
270     // Deprecated. Should use shadowHost() and check the return value.
271     Node* deprecatedShadowAncestorNode() const;
272     ShadowRoot* containingShadowRoot() const;
273     ShadowRoot* youngestShadowRoot() const;
274
275     // Returns 0, a child of ShadowRoot, or a legacy shadow root.
276     Node* nonBoundaryShadowTreeRootNode();
277
278     // Node's parent, shadow tree host.
279     ContainerNode* parentOrShadowHostNode() const;
280     Element* parentOrShadowHostElement() const;
281     void setParentOrShadowHostNode(ContainerNode*);
282     Node& highestAncestorOrSelf() const;
283
284     // Knows about all kinds of hosts.
285     ContainerNode* parentOrShadowHostOrTemplateHostNode() const;
286
287     // Returns the parent node, but 0 if the parent node is a ShadowRoot.
288     ContainerNode* nonShadowBoundaryParentNode() const;
289
290     bool selfOrAncestorHasDirAutoAttribute() const { return getFlag(SelfOrAncestorHasDirAutoFlag); }
291     void setSelfOrAncestorHasDirAutoAttribute(bool flag) { setFlag(flag, SelfOrAncestorHasDirAutoFlag); }
292
293     // Returns the enclosing event parent node (or self) that, when clicked, would trigger a navigation.
294     Node* enclosingLinkEventParentOrSelf();
295
296     bool isBlockFlowElement() const;
297
298     // These low-level calls give the caller responsibility for maintaining the integrity of the tree.
299     void setPreviousSibling(Node* previous) { m_previous = previous; }
300     void setNextSibling(Node* next) { m_next = next; }
301
302     virtual bool canContainRangeEndPoint() const { return false; }
303
304     // FIXME: These two functions belong in editing -- "atomic node" is an editing concept.
305     Node* previousNodeConsideringAtomicNodes() const;
306     Node* nextNodeConsideringAtomicNodes() const;
307
308     // Returns the next leaf node or 0 if there are no more.
309     // Delivers leaf nodes as if the whole DOM tree were a linear chain of its leaf nodes.
310     // Uses an editing-specific concept of what a leaf node is, and should probably be moved
311     // out of the Node class into an editing-specific source file.
312     Node* nextLeafNode() const;
313
314     // Returns the previous leaf node or 0 if there are no more.
315     // Delivers leaf nodes as if the whole DOM tree were a linear chain of its leaf nodes.
316     // Uses an editing-specific concept of what a leaf node is, and should probably be moved
317     // out of the Node class into an editing-specific source file.
318     Node* previousLeafNode() const;
319
320     // enclosingBlockFlowElement() is deprecated. Use enclosingBlock instead.
321     Element* enclosingBlockFlowElement() const;
322
323     bool isRootEditableElement() const;
324     Element* rootEditableElement() const;
325     Element* rootEditableElement(EditableType) const;
326
327     bool inSameContainingBlockFlowElement(Node*);
328
329     // For <link> and <style> elements.
330     virtual bool sheetLoaded() { return true; }
331     virtual void notifyLoadedSheetAndAllCriticalSubresources(bool /* error loading subresource */) { }
332     virtual void startLoadingDynamicSheet() { ASSERT_NOT_REACHED(); }
333
334     bool hasName() const { return !isTextNode() && getFlag(HasNameOrIsEditingTextFlag); }
335     bool hasID() const;
336     bool hasClass() const;
337
338     bool isUserActionElement() const { return getFlag(IsUserActionElementFlag); }
339     void setUserActionElement(bool flag) { setFlag(flag, IsUserActionElementFlag); }
340
341     bool active() const { return isUserActionElement() && isUserActionElementActive(); }
342     bool inActiveChain() const { return isUserActionElement() && isUserActionElementInActiveChain(); }
343     bool hovered() const { return isUserActionElement() && isUserActionElementHovered(); }
344     bool focused() const { return isUserActionElement() && isUserActionElementFocused(); }
345
346     bool needsAttach() const { return styleChangeType() == NeedsReattachStyleChange; }
347     bool needsStyleRecalc() const { return styleChangeType() != NoStyleChange; }
348     StyleChangeType styleChangeType() const { return static_cast<StyleChangeType>(m_nodeFlags & StyleChangeMask); }
349     bool childNeedsStyleRecalc() const { return getFlag(ChildNeedsStyleRecalcFlag); }
350     bool isLink() const { return getFlag(IsLinkFlag); }
351     bool isEditingText() const { return isTextNode() && getFlag(HasNameOrIsEditingTextFlag); }
352
353     void setHasName(bool f) { ASSERT(!isTextNode()); setFlag(f, HasNameOrIsEditingTextFlag); }
354     void setChildNeedsStyleRecalc() { setFlag(ChildNeedsStyleRecalcFlag); }
355     void clearChildNeedsStyleRecalc() { clearFlag(ChildNeedsStyleRecalcFlag); }
356
357     void setNeedsStyleRecalc(StyleChangeType);
358     void clearNeedsStyleRecalc();
359
360     bool childNeedsDistributionRecalc() const { return getFlag(ChildNeedsDistributionRecalcFlag); }
361     void setChildNeedsDistributionRecalc()  { setFlag(ChildNeedsDistributionRecalcFlag); }
362     void clearChildNeedsDistributionRecalc()  { clearFlag(ChildNeedsDistributionRecalcFlag); }
363     void markAncestorsWithChildNeedsDistributionRecalc();
364
365     bool childNeedsStyleInvalidation() const { return getFlag(ChildNeedsStyleInvalidationFlag); }
366     void setChildNeedsStyleInvalidation()  { setFlag(ChildNeedsStyleInvalidationFlag); }
367     void clearChildNeedsStyleInvalidation()  { clearFlag(ChildNeedsStyleInvalidationFlag); }
368     void markAncestorsWithChildNeedsStyleInvalidation();
369     bool needsStyleInvalidation() const { return getFlag(NeedsStyleInvalidationFlag); }
370     void clearNeedsStyleInvalidation() { clearFlag(NeedsStyleInvalidationFlag); }
371     void setNeedsStyleInvalidation();
372
373     void recalcDistribution();
374
375     bool needsLayerUpdate() const { return getFlag(NeedsLayerUpdateFlag); }
376     void setNeedsLayerUpdate() { setFlag(NeedsLayerUpdateFlag); }
377     void clearNeedsLayerUpdate() { clearFlag(NeedsLayerUpdateFlag); }
378
379     void setIsLink(bool f);
380
381     bool hasScopedHTMLStyleChild() const { return getFlag(HasScopedHTMLStyleChildFlag); }
382     void setHasScopedHTMLStyleChild(bool flag) { setFlag(flag, HasScopedHTMLStyleChildFlag); }
383
384     bool hasEventTargetData() const { return getFlag(HasEventTargetDataFlag); }
385     void setHasEventTargetData(bool flag) { setFlag(flag, HasEventTargetDataFlag); }
386
387     bool isV8CollectableDuringMinorGC() const { return getFlag(V8CollectableDuringMinorGCFlag); }
388     void markV8CollectableDuringMinorGC() { setFlag(true, V8CollectableDuringMinorGCFlag); }
389     void clearV8CollectableDuringMinorGC() { setFlag(false, V8CollectableDuringMinorGCFlag); }
390
391     virtual void setFocus(bool flag);
392     virtual void setActive(bool flag = true);
393     virtual void setHovered(bool flag = true);
394
395     virtual short tabIndex() const;
396
397     virtual Node* focusDelegate();
398     // This is called only when the node is focused.
399     virtual bool shouldHaveFocusAppearance() const;
400
401     // Whether the node is inert. This can't be in Element because text nodes
402     // must be recognized as inert to prevent text selection.
403     bool isInert() const;
404
405     enum UserSelectAllTreatment {
406         UserSelectAllDoesNotAffectEditability,
407         UserSelectAllIsAlwaysNonEditable
408     };
409     bool isContentEditable(UserSelectAllTreatment = UserSelectAllDoesNotAffectEditability);
410     bool isContentRichlyEditable();
411
412     bool rendererIsEditable(EditableType editableType = ContentIsEditable, UserSelectAllTreatment treatment = UserSelectAllIsAlwaysNonEditable) const
413     {
414         switch (editableType) {
415         case ContentIsEditable:
416             return rendererIsEditable(Editable, treatment);
417         case HasEditableAXRole:
418             return isEditableToAccessibility(Editable);
419         }
420         ASSERT_NOT_REACHED();
421         return false;
422     }
423
424     bool rendererIsRichlyEditable(EditableType editableType = ContentIsEditable) const
425     {
426         switch (editableType) {
427         case ContentIsEditable:
428             return rendererIsEditable(RichlyEditable, UserSelectAllIsAlwaysNonEditable);
429         case HasEditableAXRole:
430             return isEditableToAccessibility(RichlyEditable);
431         }
432         ASSERT_NOT_REACHED();
433         return false;
434     }
435
436     virtual bool shouldUseInputMethod();
437     virtual LayoutRect boundingBox() const;
438     IntRect pixelSnappedBoundingBox() const { return pixelSnappedIntRect(boundingBox()); }
439
440     // Returns true if the node has a non-empty bounding box in layout.
441     // This does not 100% guarantee the user can see it, but is pretty close.
442     // Note: This method only works properly after layout has occurred.
443     bool hasNonEmptyBoundingBox() const;
444
445     unsigned nodeIndex() const;
446
447     // Returns the DOM ownerDocument attribute. This method never returns NULL, except in the case
448     // of a Document node.
449     Document* ownerDocument() const;
450
451     // Returns the document associated with this node. A Document node returns itself.
452     Document& document() const
453     {
454         return treeScope().document();
455     }
456
457     TreeScope& treeScope() const
458     {
459         ASSERT(m_treeScope);
460         return *m_treeScope;
461     }
462
463     bool inActiveDocument() const;
464
465     // Returns true if this node is associated with a document and is in its associated document's
466     // node tree, false otherwise.
467     bool inDocument() const
468     {
469         return getFlag(InDocumentFlag);
470     }
471     bool isInShadowTree() const { return getFlag(IsInShadowTreeFlag); }
472     bool isInTreeScope() const { return getFlag(static_cast<NodeFlags>(InDocumentFlag | IsInShadowTreeFlag)); }
473
474     bool isDocumentTypeNode() const { return nodeType() == DOCUMENT_TYPE_NODE; }
475     virtual bool childTypeAllowed(NodeType) const { return false; }
476     unsigned countChildren() const;
477     Node* traverseToChildAt(unsigned index) const;
478
479     bool isDescendantOf(const Node*) const;
480     bool contains(const Node*) const;
481     bool containsIncludingShadowDOM(const Node*) const;
482     bool containsIncludingHostElements(const Node&) const;
483     Node* commonAncestor(const Node&, Node* (*parent)(const Node&));
484
485     // Used to determine whether range offsets use characters or node indices.
486     virtual bool offsetInCharacters() const;
487     // Number of DOM 16-bit units contained in node. Note that rendered text length can be different - e.g. because of
488     // css-transform:capitalize breaking up precomposed characters and ligatures.
489     virtual int maxCharacterOffset() const;
490
491     // Whether or not a selection can be started in this object
492     virtual bool canStartSelection() const;
493
494     // Getting points into and out of screen space
495     FloatPoint convertToPage(const FloatPoint&) const;
496     FloatPoint convertFromPage(const FloatPoint&) const;
497
498     // -----------------------------------------------------------------------------
499     // Integration with rendering tree
500
501     // As renderer() includes a branch you should avoid calling it repeatedly in hot code paths.
502     // Note that if a Node has a renderer, it's parentNode is guaranteed to have one as well.
503     RenderObject* renderer() const { return hasRareData() ? m_data.m_rareData->renderer() : m_data.m_renderer; };
504     void setRenderer(RenderObject* renderer)
505     {
506         if (hasRareData())
507             m_data.m_rareData->setRenderer(renderer);
508         else
509             m_data.m_renderer = renderer;
510     }
511     bool hasRenderer() const { return renderer(); }
512
513     // Use these two methods with caution.
514     RenderBox* renderBox() const;
515     RenderBoxModelObject* renderBoxModelObject() const;
516
517     struct AttachContext {
518         RenderStyle* resolvedStyle;
519         bool performingReattach;
520
521         AttachContext() : resolvedStyle(0), performingReattach(false) { }
522     };
523
524     // Attaches this node to the rendering tree. This calculates the style to be applied to the node and creates an
525     // appropriate RenderObject which will be inserted into the tree (except when the style has display: none). This
526     // makes the node visible in the FrameView.
527     virtual void attach(const AttachContext& = AttachContext());
528
529     // Detaches the node from the rendering tree, making it invisible in the rendered view. This method will remove
530     // the node's rendering object from the rendering tree and delete it.
531     virtual void detach(const AttachContext& = AttachContext());
532
533 #ifndef NDEBUG
534     bool inDetach() const;
535 #endif
536
537     void reattach(const AttachContext& = AttachContext());
538     void lazyReattachIfAttached();
539
540     // Returns true if recalcStyle should be called on the object, if there is such a method (on Document and Element).
541     bool shouldCallRecalcStyle(StyleRecalcChange);
542
543     // Wrapper for nodes that don't have a renderer, but still cache the style (like HTMLOptionElement).
544     RenderStyle* renderStyle() const;
545     RenderStyle* parentRenderStyle() const;
546
547     RenderStyle* computedStyle(PseudoId pseudoElementSpecifier = NOPSEUDO) { return virtualComputedStyle(pseudoElementSpecifier); }
548
549     // -----------------------------------------------------------------------------
550     // Notification of document structure changes (see ContainerNode.h for more notification methods)
551     //
552     // At first, WebKit notifies the node that it has been inserted into the document. This is called during document parsing, and also
553     // when a node is added through the DOM methods insertBefore(), appendChild() or replaceChild(). The call happens _after_ the node has been added to the tree.
554     // This is similar to the DOMNodeInsertedIntoDocument DOM event, but does not require the overhead of event
555     // dispatching.
556     //
557     // WebKit notifies this callback regardless if the subtree of the node is a document tree or a floating subtree.
558     // Implementation can determine the type of subtree by seeing insertionPoint->inDocument().
559     // For a performance reason, notifications are delivered only to ContainerNode subclasses if the insertionPoint is out of document.
560     //
561     // There are another callback named didNotifySubtreeInsertionsToDocument(), which is called after all the descendant is notified,
562     // if this node was inserted into the document tree. Only a few subclasses actually need this. To utilize this, the node should
563     // return InsertionShouldCallDidNotifySubtreeInsertions from insertedInto().
564     //
565     enum InsertionNotificationRequest {
566         InsertionDone,
567         InsertionShouldCallDidNotifySubtreeInsertions
568     };
569
570     virtual InsertionNotificationRequest insertedInto(ContainerNode* insertionPoint);
571     virtual void didNotifySubtreeInsertionsToDocument() { }
572
573     // Notifies the node that it is no longer part of the tree.
574     //
575     // This is a dual of insertedInto(), and is similar to the DOMNodeRemovedFromDocument DOM event, but does not require the overhead of event
576     // dispatching, and is called _after_ the node is removed from the tree.
577     //
578     virtual void removedFrom(ContainerNode* insertionPoint);
579
580     String debugName() const;
581
582 #ifndef NDEBUG
583     virtual void formatForDebugger(char* buffer, unsigned length) const;
584
585     void showNode(const char* prefix = "") const;
586     void showTreeForThis() const;
587     void showNodePathForThis() const;
588     void showTreeAndMark(const Node* markedNode1, const char* markedLabel1, const Node* markedNode2 = 0, const char* markedLabel2 = 0) const;
589     void showTreeForThisAcrossFrame() const;
590 #endif
591
592     void invalidateNodeListCachesInAncestors(const QualifiedName* attrName = 0, Element* attributeOwnerElement = 0);
593     NodeListsNodeData* nodeLists();
594     void clearNodeLists();
595
596     virtual bool willRespondToMouseMoveEvents();
597     virtual bool willRespondToMouseClickEvents();
598     virtual bool willRespondToTouchEvents();
599
600     unsigned short compareDocumentPosition(const Node*) const;
601
602     enum ShadowTreesTreatment {
603         TreatShadowTreesAsDisconnected,
604         TreatShadowTreesAsComposed
605     };
606
607     unsigned short compareDocumentPositionInternal(const Node*, ShadowTreesTreatment) const;
608
609     virtual Node* toNode() OVERRIDE FINAL;
610
611     virtual const AtomicString& interfaceName() const OVERRIDE;
612     virtual ExecutionContext* executionContext() const OVERRIDE;
613
614     virtual bool addEventListener(const AtomicString& eventType, PassRefPtr<EventListener>, bool useCapture = false) OVERRIDE;
615     virtual bool removeEventListener(const AtomicString& eventType, EventListener*, bool useCapture = false) OVERRIDE;
616     virtual void removeAllEventListeners() OVERRIDE;
617     void removeAllEventListenersRecursively();
618
619     // Handlers to do/undo actions on the target node before an event is dispatched to it and after the event
620     // has been dispatched.  The data pointer is handed back by the preDispatch and passed to postDispatch.
621     virtual void* preDispatchEventHandler(Event*) { return 0; }
622     virtual void postDispatchEventHandler(Event*, void* /*dataFromPreDispatch*/) { }
623
624     using EventTarget::dispatchEvent;
625     virtual bool dispatchEvent(PassRefPtrWillBeRawPtr<Event>) OVERRIDE;
626
627     void dispatchScopedEvent(PassRefPtrWillBeRawPtr<Event>);
628     void dispatchScopedEventDispatchMediator(PassRefPtr<EventDispatchMediator>);
629
630     virtual void handleLocalEvents(Event*);
631
632     void dispatchSubtreeModifiedEvent();
633     bool dispatchDOMActivateEvent(int detail, PassRefPtrWillBeRawPtr<Event> underlyingEvent);
634
635     bool dispatchKeyEvent(const PlatformKeyboardEvent&);
636     bool dispatchWheelEvent(const PlatformWheelEvent&);
637     bool dispatchMouseEvent(const PlatformMouseEvent&, const AtomicString& eventType, int clickCount = 0, Node* relatedTarget = 0);
638     bool dispatchGestureEvent(const PlatformGestureEvent&);
639     bool dispatchTouchEvent(PassRefPtrWillBeRawPtr<TouchEvent>);
640
641     void dispatchSimulatedClick(Event* underlyingEvent, SimulatedClickMouseEventOptions = SendNoEvents);
642
643     void dispatchInputEvent();
644
645     // Perform the default action for an event.
646     virtual void defaultEventHandler(Event*);
647     virtual void willCallDefaultEventHandler(const Event&);
648
649     virtual EventTargetData* eventTargetData() OVERRIDE;
650     virtual EventTargetData& ensureEventTargetData() OVERRIDE;
651
652     void getRegisteredMutationObserversOfType(WillBeHeapHashMap<RawPtrWillBeMember<MutationObserver>, MutationRecordDeliveryOptions>&, MutationObserver::MutationType, const QualifiedName* attributeName);
653     void registerMutationObserver(MutationObserver&, MutationObserverOptions, const HashSet<AtomicString>& attributeFilter);
654     void unregisterMutationObserver(MutationObserverRegistration*);
655     void registerTransientMutationObserver(MutationObserverRegistration*);
656     void unregisterTransientMutationObserver(MutationObserverRegistration*);
657     void notifyMutationObserversNodeWillDetach();
658
659     virtual void registerScopedHTMLStyleChild();
660     virtual void unregisterScopedHTMLStyleChild();
661     size_t numberOfScopedHTMLStyleChildren() const;
662
663     unsigned connectedSubframeCount() const;
664     void incrementConnectedSubframeCount(unsigned amount = 1);
665     void decrementConnectedSubframeCount(unsigned amount = 1);
666     void updateAncestorConnectedSubframeCountForRemoval() const;
667     void updateAncestorConnectedSubframeCountForInsertion() const;
668
669     PassRefPtr<NodeList> getDestinationInsertionPoints();
670
671     void setAlreadySpellChecked(bool flag) { setFlag(flag, AlreadySpellCheckedFlag); }
672     bool isAlreadySpellChecked() { return getFlag(AlreadySpellCheckedFlag); }
673
674     bool isFinishedParsingChildren() const { return getFlag(IsFinishedParsingChildrenFlag); }
675
676     virtual void trace(Visitor*);
677
678 private:
679     enum NodeFlags {
680         HasRareDataFlag = 1,
681
682         // Node type flags. These never change once created.
683         IsTextFlag = 1 << 1,
684         IsContainerFlag = 1 << 2,
685         IsElementFlag = 1 << 3,
686         IsHTMLFlag = 1 << 4,
687         IsSVGFlag = 1 << 5,
688         IsDocumentFragmentFlag = 1 << 6,
689         IsInsertionPointFlag = 1 << 7,
690
691         // Changes based on if the element should be treated like a link,
692         // ex. When setting the href attribute on an <a>.
693         IsLinkFlag = 1 << 8,
694
695         // Changes based on :hover, :active and :focus state.
696         IsUserActionElementFlag = 1 << 9,
697
698         // Tree state flags. These change when the element is added/removed
699         // from a DOM tree.
700         InDocumentFlag = 1 << 10,
701         IsInShadowTreeFlag = 1 << 11,
702
703         // Set by the parser when the children are done parsing.
704         IsFinishedParsingChildrenFlag = 1 << 12,
705
706         // Flags related to recalcStyle.
707         NeedsLayerUpdateFlag = 1 << 13,
708         HasCustomStyleCallbacksFlag = 1 << 14,
709         ChildNeedsStyleInvalidationFlag = 1 << 15,
710         NeedsStyleInvalidationFlag = 1 << 16,
711         ChildNeedsDistributionRecalcFlag = 1 << 17,
712         ChildNeedsStyleRecalcFlag = 1 << 18,
713         StyleChangeMask = 1 << nodeStyleChangeShift | 1 << (nodeStyleChangeShift + 1),
714
715         CustomElementFlag = 1 << 21,
716         CustomElementUpgradedFlag = 1 << 22,
717
718         HasNameOrIsEditingTextFlag = 1 << 23,
719         HasWeakReferencesFlag = 1 << 24,
720         V8CollectableDuringMinorGCFlag = 1 << 25,
721         HasSyntheticAttrChildNodesFlag = 1 << 26,
722         HasEventTargetDataFlag = 1 << 27,
723         AlreadySpellCheckedFlag = 1 << 28,
724
725         // HTML dir=auto.
726         SelfOrAncestorHasDirAutoFlag = 1 << 29,
727
728         // FIXME: Remove <style scoped> support.
729         HasScopedHTMLStyleChildFlag = 1 << 30,
730
731         DefaultNodeFlags = IsFinishedParsingChildrenFlag | ChildNeedsStyleRecalcFlag | NeedsReattachStyleChange
732     };
733
734     // 1 bits remaining.
735
736     bool getFlag(NodeFlags mask) const { return m_nodeFlags & mask; }
737     void setFlag(bool f, NodeFlags mask) const { m_nodeFlags = (m_nodeFlags & ~mask) | (-(int32_t)f & mask); }
738     void setFlag(NodeFlags mask) const { m_nodeFlags |= mask; }
739     void clearFlag(NodeFlags mask) const { m_nodeFlags &= ~mask; }
740
741 protected:
742     enum ConstructionType {
743         CreateOther = DefaultNodeFlags,
744         CreateText = DefaultNodeFlags | IsTextFlag,
745         CreateContainer = DefaultNodeFlags | IsContainerFlag,
746         CreateElement = CreateContainer | IsElementFlag,
747         CreateShadowRoot = CreateContainer | IsDocumentFragmentFlag | IsInShadowTreeFlag,
748         CreateDocumentFragment = CreateContainer | IsDocumentFragmentFlag,
749         CreateHTMLElement = CreateElement | IsHTMLFlag,
750         CreateSVGElement = CreateElement | IsSVGFlag,
751         CreateDocument = CreateContainer | InDocumentFlag,
752         CreateInsertionPoint = CreateHTMLElement | IsInsertionPointFlag,
753         CreateEditingText = CreateText | HasNameOrIsEditingTextFlag,
754     };
755
756     Node(TreeScope* treeScope, ConstructionType type)
757         : m_nodeFlags(type)
758         , m_parentOrShadowHostNode(nullptr)
759         , m_treeScope(treeScope)
760         , m_previous(nullptr)
761         , m_next(nullptr)
762     {
763         ASSERT(m_treeScope || type == CreateDocument || type == CreateShadowRoot);
764         ScriptWrappable::init(this);
765 #if !ENABLE(OILPAN)
766         if (m_treeScope)
767             m_treeScope->guardRef();
768 #endif
769
770 #if !defined(NDEBUG) || (defined(DUMP_NODE_STATISTICS) && DUMP_NODE_STATISTICS)
771         trackForDebugging();
772 #endif
773         InspectorCounters::incrementCounter(InspectorCounters::NodeCounter);
774     }
775
776     virtual void didMoveToNewDocument(Document& oldDocument);
777
778     static void reattachWhitespaceSiblings(Text* start);
779
780 #if !ENABLE(OILPAN)
781     void willBeDeletedFromDocument();
782 #endif
783
784     bool hasRareData() const { return getFlag(HasRareDataFlag); }
785
786     NodeRareData* rareData() const;
787     NodeRareData& ensureRareData();
788 #if !ENABLE(OILPAN)
789     void clearRareData();
790
791     void clearEventTargetData();
792 #endif
793
794     void setHasCustomStyleCallbacks() { setFlag(true, HasCustomStyleCallbacksFlag); }
795
796     void setTreeScope(TreeScope* scope) { m_treeScope = scope; }
797
798     // isTreeScopeInitialized() can be false
799     // - in the destruction of Document or ShadowRoot where m_treeScope is set to null or
800     // - in the Node constructor called by these two classes where m_treeScope is set by TreeScope ctor.
801     bool isTreeScopeInitialized() const { return m_treeScope; }
802
803     void markAncestorsWithChildNeedsStyleRecalc();
804
805     void setIsFinishedParsingChildren(bool value) { setFlag(value, IsFinishedParsingChildrenFlag); }
806
807 private:
808     friend class TreeShared<Node>;
809     friend class WeakNodeMap;
810
811     virtual PseudoId customPseudoId() const
812     {
813         ASSERT(hasCustomStyleCallbacks());
814         return NOPSEUDO;
815     }
816
817 #if !ENABLE(OILPAN)
818     void removedLastRef();
819 #endif
820     bool hasTreeSharedParent() const { return !!parentOrShadowHostNode(); }
821
822     enum EditableLevel { Editable, RichlyEditable };
823     bool rendererIsEditable(EditableLevel, UserSelectAllTreatment = UserSelectAllIsAlwaysNonEditable) const;
824     bool isEditableToAccessibility(EditableLevel) const;
825
826     bool isUserActionElementActive() const;
827     bool isUserActionElementInActiveChain() const;
828     bool isUserActionElementHovered() const;
829     bool isUserActionElementFocused() const;
830
831     void traceStyleChange(StyleChangeType);
832     void traceStyleChangeIfNeeded(StyleChangeType);
833     void setStyleChange(StyleChangeType);
834
835     virtual RenderStyle* nonRendererStyle() const { return 0; }
836
837     virtual RenderStyle* virtualComputedStyle(PseudoId = NOPSEUDO);
838
839     void trackForDebugging();
840
841     WillBeHeapVector<OwnPtrWillBeMember<MutationObserverRegistration> >* mutationObserverRegistry();
842     WillBeHeapHashSet<RawPtrWillBeMember<MutationObserverRegistration> >* transientMutationObserverRegistry();
843
844     mutable uint32_t m_nodeFlags;
845     RawPtrWillBeMember<ContainerNode> m_parentOrShadowHostNode;
846     RawPtrWillBeMember<TreeScope> m_treeScope;
847     RawPtrWillBeMember<Node> m_previous;
848     RawPtrWillBeMember<Node> m_next;
849     // When a node has rare data we move the renderer into the rare data.
850     union DataUnion {
851         DataUnion() : m_renderer(0) { }
852         RenderObject* m_renderer;
853         NodeRareDataBase* m_rareData;
854     } m_data;
855 };
856
857 inline void Node::setParentOrShadowHostNode(ContainerNode* parent)
858 {
859     ASSERT(isMainThread());
860     m_parentOrShadowHostNode = parent;
861 }
862
863 inline ContainerNode* Node::parentOrShadowHostNode() const
864 {
865     ASSERT(isMainThread());
866     return m_parentOrShadowHostNode;
867 }
868
869 inline ContainerNode* Node::parentNode() const
870 {
871     return isShadowRoot() ? 0 : parentOrShadowHostNode();
872 }
873
874 inline void Node::lazyReattachIfAttached()
875 {
876     if (styleChangeType() == NeedsReattachStyleChange)
877         return;
878     if (!inActiveDocument())
879         return;
880
881     AttachContext context;
882     context.performingReattach = true;
883
884     detach(context);
885     markAncestorsWithChildNeedsStyleRecalc();
886 }
887
888 inline bool Node::shouldCallRecalcStyle(StyleRecalcChange change)
889 {
890     return change >= Inherit || needsStyleRecalc() || childNeedsStyleRecalc();
891 }
892
893 inline bool isTreeScopeRoot(const Node* node)
894 {
895     return !node || node->isDocumentNode() || node->isShadowRoot();
896 }
897
898 inline bool isTreeScopeRoot(const Node& node)
899 {
900     return node.isDocumentNode() || node.isShadowRoot();
901 }
902
903 // Allow equality comparisons of Nodes by reference or pointer, interchangeably.
904 inline bool operator==(const Node& a, const Node& b) { return &a == &b; }
905 inline bool operator==(const Node& a, const Node* b) { return &a == b; }
906 inline bool operator==(const Node* a, const Node& b) { return a == &b; }
907 inline bool operator!=(const Node& a, const Node& b) { return !(a == b); }
908 inline bool operator!=(const Node& a, const Node* b) { return !(a == b); }
909 inline bool operator!=(const Node* a, const Node& b) { return !(a == b); }
910 inline bool operator==(const PassRefPtr<Node>& a, const Node& b) { return a.get() == &b; }
911 inline bool operator==(const Node& a, const PassRefPtr<Node>& b) { return &a == b.get(); }
912 inline bool operator!=(const PassRefPtr<Node>& a, const Node& b) { return !(a == b); }
913 inline bool operator!=(const Node& a, const PassRefPtr<Node>& b) { return !(a == b); }
914
915
916 #define DEFINE_NODE_TYPE_CASTS(thisType, predicate) \
917     template<typename T> inline thisType* to##thisType(const RefPtr<T>& node) { return to##thisType(node.get()); } \
918     DEFINE_TYPE_CASTS(thisType, Node, node, node->predicate, node.predicate)
919
920 // This requires isClassName(const Node&).
921 #define DEFINE_NODE_TYPE_CASTS_WITH_FUNCTION(thisType) \
922     template<typename T> inline thisType* to##thisType(const RefPtr<T>& node) { return to##thisType(node.get()); } \
923     DEFINE_TYPE_CASTS(thisType, Node, node, is##thisType(*node), is##thisType(node))
924
925 } // namespace WebCore
926
927 #ifndef NDEBUG
928 // Outside the WebCore namespace for ease of invocation from gdb.
929 void showNode(const WebCore::Node*);
930 void showTree(const WebCore::Node*);
931 void showNodePath(const WebCore::Node*);
932 #endif
933
934 #endif