File indexing completed on 2024-04-28 15:22:55

0001 /*
0002  * This file is part of the DOM implementation for KDE.
0003  *
0004  * Copyright 1999 Lars Knoll (knoll@kde.org)
0005  * Copyright 2000 Frederik Holljen (frederik.holljen@hig.no)
0006  * This library is free software; you can redistribute it and/or
0007  * modify it under the terms of the GNU Library General Public
0008  * License as published by the Free Software Foundation; either
0009  * version 2 of the License, or (at your option) any later version.
0010  *
0011  * This library is distributed in the hope that it will be useful,
0012  * but WITHOUT ANY WARRANTY; without even the implied warranty of
0013  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
0014  * Library General Public License for more details.
0015  *
0016  * You should have received a copy of the GNU Library General Public License
0017  * along with this library; see the file COPYING.LIB.  If not, write to
0018  * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
0019  * Boston, MA 02110-1301, USA.
0020  *
0021  * This file includes excerpts from the Document Object Model (DOM)
0022  * Level 2 Specification (Candidate Recommendation)
0023  * https://www.w3.org/TR/2000/CR-DOM-Level-2-20000510/
0024  * Copyright © 2000 W3C® (MIT, INRIA, Keio), All Rights Reserved.
0025  *
0026  */
0027 #ifndef _dom2_traversal_h_
0028 #define _dom2_traversal_h_
0029 
0030 #include <khtml_export.h>
0031 #include <dom/dom_node.h>
0032 #include <dom/dom_misc.h>
0033 
0034 namespace DOM
0035 {
0036 class Node;
0037 class NodeFilter;
0038 class NodeIteratorImpl;
0039 class NodeFilterImpl;
0040 class TreeWalkerImpl;
0041 class CustomNodeFilter;
0042 class CustomNodeFilterImpl;
0043 
0044 /**
0045  * NodeIterators are used to step through a set of nodes, e.g. the set
0046  * of nodes in a NodeList, the document subtree governed by a
0047  * particular node, the results of a query, or any other set of nodes.
0048  * The set of nodes to be iterated is determined by the implementation
0049  * of the NodeIterator. DOM Level 2 specifies a single NodeIterator
0050  * implementation for document-order traversal of a document subtree.
0051  * Instances of these iterators are created by calling
0052  * DocumentTraversal.createNodeIterator().
0053  *
0054  *  Any Iterator that returns nodes may implement the
0055  * \c NodeIterator interface. Users and vendor libraries may also
0056  * choose to create Iterators that implement the \c NodeIterator
0057  * interface.
0058  *
0059  */
0060 class KHTML_EXPORT NodeIterator
0061 {
0062     friend class NodeIteratorImpl;
0063     friend class Document;
0064 public:
0065     NodeIterator();
0066     NodeIterator(const NodeIterator &other);
0067 
0068     NodeIterator &operator = (const NodeIterator &other);
0069 
0070     ~NodeIterator();
0071 
0072     /**
0073      * The root node of the NodeIterator, as specified when it was created.
0074      */
0075     Node root();
0076 
0077     /**
0078     * This attribute determines which node types are presented via the
0079     * iterator. The available set of constants is defined in the NodeFilter
0080     * interface. Nodes not accepted by whatToShow will be skipped, but their
0081     * children may still be considered. Note that this skip takes precedence
0082     * over the filter, if any.
0083     */
0084     unsigned long whatToShow();
0085 
0086     /**
0087      * The NodeFilter used to screen nodes.
0088      */
0089     NodeFilter filter();
0090 
0091     /**
0092      * The value of this flag determines whether the children of entity
0093      * reference nodes are visible to the iterator. If false, they and
0094      * their descendents will be rejected. Note that this rejection takes
0095      * precedence over whatToShow and the filter. Also note that this is
0096      * currently the only situation where NodeIterators may reject a complete
0097      * subtree rather than skipping individual nodes.
0098      *
0099      * To produce a view of the document that has entity references expanded
0100      * and does not expose the entity reference node itself, use the whatToShow
0101      * flags to hide the entity reference node and set expandEntityReferences to
0102      * true when creating the iterator. To produce a view of the document that
0103      * has entity reference nodes but no entity expansion, use the whatToShow
0104      * flags to show the entity reference node and set expandEntityReferences to
0105      * false.
0106      */
0107     bool expandEntityReferences();
0108 
0109     /**
0110      * Returns the next node in the set and advances the position of
0111      * the Iterator in the set. After a NodeIterator is created, the
0112      * first call to nextNode() returns the first node in the set.
0113      *
0114      * @return The next \c Node in the set being iterated
0115      * over, or \c null if there are no more members in
0116      * that set.
0117      *
0118      * @exception Exceptions from user code
0119      * Any exceptions raised by a user-written Filter will propagate
0120      * through.
0121      *
0122      */
0123     Node nextNode();
0124 
0125     /**
0126      * Returns the previous node in the set and moves the position of
0127      * the Iterator backwards in the set.
0128      *
0129      * @return The previous \c Node in the set being
0130      * iterated over, or \c null if there are no more
0131      * members in that set.
0132      *
0133      * @exception Exceptions from user code
0134      * Any exceptions raised by a user-written Filter will propagate
0135      * through.
0136      *
0137      */
0138     Node previousNode();
0139 
0140     /**
0141      * Detaches the NodeIterator from the set which it iterated over,
0142      * releasing any computational resources and placing the iterator in the
0143      * INVALID state. After detach has been invoked, calls to nextNode or
0144      * previousNode will raise the exception INVALID_STATE_ERR.
0145      */
0146     void detach();
0147 
0148     /**
0149      * @internal
0150      * not part of the DOM
0151      */
0152     NodeIteratorImpl *handle() const;
0153     bool isNull() const;
0154 
0155 protected:
0156     NodeIteratorImpl *impl;
0157     NodeIterator(NodeIteratorImpl *i);
0158 };
0159 
0160 /**
0161  * Filters are objects that know how to "filter out" nodes. If an
0162  * Iterator or \c TreeWalker is given a filter, before it
0163  * returns the next node, it applies the filter. If the filter says to
0164  * accept the node, the Iterator returns it; otherwise, the Iterator
0165  * looks for the next node and pretends that the node that was
0166  * rejected was not there.
0167  *
0168  *  The DOM does not provide any filters. Filter is just an interface
0169  * that users can implement to provide their own filters.
0170  *
0171  *  Filters do not need to know how to iterate, nor do they need to
0172  * know anything about the data structure that is being iterated. This
0173  * makes it very easy to write filters, since the only thing they have
0174  * to know how to do is evaluate a single node. One filter may be used
0175  * with a number of different kinds of Iterators, encouraging code
0176  * reuse.
0177  *
0178  * To create your own custom NodeFilter, define a subclass of
0179  * CustomNodeFilter which overrides the acceptNode() method and assign
0180  * an instance of it to the NodeFilter. For more details see the
0181  * CustomNodeFilter class
0182  */
0183 class KHTML_EXPORT NodeFilter
0184 {
0185     friend class NodeIterator;
0186     friend class NodeIteratorImpl;
0187     friend class TreeWalker;
0188     friend class TreeWalkerImpl;
0189     friend class NodeFilterImpl;
0190 public:
0191     NodeFilter();
0192     NodeFilter(const NodeFilter &other);
0193     NodeFilter(NodeFilterImpl *i);
0194 
0195     virtual NodeFilter &operator = (const NodeFilter &other);
0196 
0197     virtual ~NodeFilter();
0198     /**
0199      * The following constants are returned by the acceptNode()
0200      * method:
0201      *
0202      */
0203     enum AcceptCode {
0204         FILTER_ACCEPT = 1,
0205         FILTER_REJECT = 2,
0206         FILTER_SKIP   = 3
0207     };
0208 
0209     /**
0210      * These are the available values for the whatToShow parameter.
0211      * They are the same as the set of possible types for Node, and
0212      * their values are derived by using a bit position corresponding
0213      * to the value of NodeType for the equivalent node type.
0214      *
0215      */
0216     enum ShowCode {
0217         SHOW_ALL                       = 0xFFFFFFFF,
0218         SHOW_ELEMENT                   = 0x00000001,
0219         SHOW_ATTRIBUTE                 = 0x00000002,
0220         SHOW_TEXT                      = 0x00000004,
0221         SHOW_CDATA_SECTION             = 0x00000008,
0222         SHOW_ENTITY_REFERENCE          = 0x00000010,
0223         SHOW_ENTITY                    = 0x00000020,
0224         SHOW_PROCESSING_INSTRUCTION    = 0x00000040,
0225         SHOW_COMMENT                   = 0x00000080,
0226         SHOW_DOCUMENT                  = 0x00000100,
0227         SHOW_DOCUMENT_TYPE             = 0x00000200,
0228         SHOW_DOCUMENT_FRAGMENT         = 0x00000400,
0229         SHOW_NOTATION                  = 0x00000800
0230     };
0231 
0232     /**
0233      * Test whether a specified node is visible in the logical view of
0234      * a TreeWalker or NodeIterator. This function will be called by
0235      * the implementation of TreeWalker and NodeIterator; it is not
0236      * intended to be called directly from user code.
0237      *
0238      * @param n The node to check to see if it passes the filter or
0239      * not.
0240      *
0241      * @return a constant to determine whether the node is accepted,
0242      * rejected, or skipped, as defined <a
0243      * href="#Traversal-NodeFilter-acceptNode-constants"> above </a> .
0244      *
0245      */
0246     virtual short acceptNode(const Node &n);
0247 
0248     /**
0249      * @internal
0250      * not part of the DOM
0251      */
0252     virtual NodeFilterImpl *handle() const;
0253     virtual bool isNull() const;
0254 
0255     void setCustomNodeFilter(CustomNodeFilter *custom);
0256     CustomNodeFilter *customNodeFilter();
0257     static NodeFilter createCustom(CustomNodeFilter *custom);
0258 
0259 protected:
0260     NodeFilterImpl *impl;
0261 };
0262 
0263 /**
0264  * CustomNodeFilter can be used to define your own NodeFilter for use
0265  * with NodeIterators and TreeWalkers. You can create a custom filter
0266  * by doing the following:
0267  *
0268  * class MyCustomNodeFilter {
0269  *  .....
0270  *  virtual short acceptNode (const Node &n);
0271  *  .....
0272  * }
0273  *
0274  * Then in your program:
0275  *
0276  * short MyCustomNodeFilter::acceptNode (const Node &n)
0277  * {
0278  *   if (condition)
0279  *     return NodeFilter::FILTER_ACCEPT;
0280  *   else
0281  *    ....
0282  * }
0283  *
0284  *
0285  * MyCustomFilter *filter = new MyCustomFilter();
0286  * NodeFilter nf = NodeFilter::createCustom(filter);
0287  * NodeIterator ni = document.createNodeIterator(document,NodeFilter.SHOW_ALL,nf,false);
0288  *
0289  * The default implementation of acceptNode() returns NodeFilter::FILTER_ACCEPT
0290  * for all nodes.
0291  *
0292  */
0293 
0294 class KHTML_EXPORT CustomNodeFilter : public DomShared
0295 {
0296 public:
0297     CustomNodeFilter();
0298     virtual ~CustomNodeFilter();
0299     virtual short acceptNode(const Node &n);
0300     virtual bool isNull();
0301 
0302     /**
0303      * @internal
0304      * not part of the DOM
0305      *
0306      * Returns a name specifying the type of custom node filter. Useful for checking
0307      * if an custom node filter is of a particular sublass.
0308      *
0309      */
0310     virtual DOMString customNodeFilterType();
0311 
0312 protected:
0313     /**
0314      * @internal
0315      * Reserved. Do not use in your subclasses.
0316      */
0317     CustomNodeFilterImpl *impl;
0318 };
0319 
0320 /**
0321  * \c TreeWalker objects are used to navigate a document
0322  * tree or subtree using the view of the document defined by its
0323  * \c whatToShow flags and any filters that are defined
0324  * for the \c TreeWalker . Any function which performs
0325  * navigation using a \c TreeWalker will automatically
0326  * support any view defined by a \c TreeWalker .
0327  *
0328  *  Omitting nodes from the logical view of a subtree can result in a
0329  * structure that is substantially different from the same subtree in
0330  * the complete, unfiltered document. Nodes that are siblings in the
0331  * TreeWalker view may be children of different, widely separated
0332  * nodes in the original view. For instance, consider a Filter that
0333  * skips all nodes except for Text nodes and the root node of a
0334  * document. In the logical view that results, all text nodes will be
0335  * siblings and appear as direct children of the root node, no matter
0336  * how deeply nested the structure of the original document.
0337  *
0338  */
0339 class KHTML_EXPORT TreeWalker
0340 {
0341     friend class Document;
0342     friend class TreeWalkerImpl;
0343 public:
0344     TreeWalker();
0345     TreeWalker(const TreeWalker &other);
0346 
0347     TreeWalker &operator = (const TreeWalker &other);
0348 
0349     ~TreeWalker();
0350 
0351     /**
0352      * The root node of the TreeWalker, as specified when it was created.
0353      */
0354     Node root();
0355 
0356     /**
0357      * This attribute determines which node types are presented via the
0358      * TreeWalker. The available set of constants is defined in the NodeFilter
0359      * interface. Nodes not accepted by whatToShow will be skipped, but their
0360      * children may still be considered. Note that this skip takes precedence
0361      * over the filter, if any.
0362      */
0363     unsigned long whatToShow();
0364 
0365     /**
0366      * The filter used to screen nodes.
0367      */
0368     NodeFilter filter();
0369 
0370     /**
0371      * The value of this flag determines whether the children of entity
0372      * reference nodes are visible to the TreeWalker. If false, they and their
0373      * descendents will be rejected. Note that this rejection takes precedence
0374      * over whatToShow and the filter, if any.
0375      *
0376      * To produce a view of the document that has entity references expanded
0377      * and does not expose the entity reference node itself, use the whatToShow
0378      * flags to hide the entity reference node and set expandEntityReferences
0379      * to true when creating the TreeWalker. To produce a view of the document
0380      * that has entity reference nodes but no entity expansion, use the
0381      * whatToShow flags to show the entity reference node and set
0382      * expandEntityReferences to false.
0383      */
0384     bool expandEntityReferences();
0385 
0386     /**
0387      * The node at which the TreeWalker is currently positioned.
0388      * Alterations to the DOM tree may cause the current node to no longer be
0389      * accepted by the TreeWalker's associated filter. currentNode may also be
0390      * explicitly set to any node, whether or not it is within the subtree
0391      * specified by the root node or would be accepted by the filter and
0392      * whatToShow flags. Further traversal occurs relative to currentNode even
0393      * if it is not part of the current view, by applying the filters in the
0394      * requested direction; if no traversal is possible, currentNode is not changed.
0395      *
0396      * @exception DOMException
0397      * NOT_SUPPORTED_ERR: Raised if an attempt is made to set currentNode to null.
0398      */
0399     Node currentNode();
0400 
0401     /**
0402      * see currentNode
0403      */
0404     void setCurrentNode(const Node &_currentNode);
0405 
0406     /**
0407      * Moves to and returns the parent node of the current node. If
0408      * there is no parent node, or if the current node is the root
0409      * node from which this TreeWalker was created, retains the
0410      * current position and returns null.
0411      *
0412      * @return The new parent node, or null if the current node has no
0413      * parent in the TreeWalker's logical view.
0414      *
0415      * @exception Exceptions from user code
0416      * Any exceptions raised by a user-written Filter will propagate
0417      * through.
0418      *
0419      */
0420     Node parentNode();
0421 
0422     /**
0423      * Moves the \c TreeWalker to the first child of the
0424      * current node, and returns the new node. If the current node has
0425      * no children, returns \c null , and retains the
0426      * current node.
0427      *
0428      * @return The new node, or \c null if the current
0429      * node has no children.
0430      *
0431      * @exception Exceptions from user code
0432      * Any exceptions raised by a user-written Filter will propagate
0433      * through.
0434      *
0435      */
0436     Node firstChild();
0437 
0438     /**
0439      * Moves the \c TreeWalker to the last child of the
0440      * current node, and returns the new node. If the current node has
0441      * no children, returns \c null , and retains the
0442      * current node.
0443      *
0444      * @return The new node, or \c null if the current
0445      * node has no children.
0446      *
0447      * @exception Exceptions from user code
0448      * Any exceptions raised by a user-written Filter will propagate
0449      * through.
0450      *
0451      */
0452     Node lastChild();
0453 
0454     /**
0455      * Moves the \c TreeWalker to the previous sibling of
0456      * the current node, and returns the new node. If the current node
0457      * has no previous sibling, returns \c null , and
0458      * retains the current node.
0459      *
0460      * @return The new node, or \c null if the current
0461      * node has no previous sibling.
0462      *
0463      * @exception Exceptions from user code
0464      * Any exceptions raised by a user-written Filter will propagate
0465      * through.
0466      *
0467      */
0468     Node previousSibling();
0469 
0470     /**
0471      * Moves the \c TreeWalker to the next sibling of the
0472      * current node, and returns the new node. If the current node has
0473      * no next sibling, returns \c null , and retains the
0474      * current node.
0475      *
0476      * @return The new node, or \c null if the current
0477      * node has no next sibling.
0478      *
0479      * @exception Exceptions from user code
0480      * Any exceptions raised by a user-written Filter will propagate
0481      * through.
0482      *
0483      */
0484     Node nextSibling();
0485 
0486     /**
0487      * Moves the \c TreeWalker to the previous node in
0488      * document order relative to the current node, and returns the
0489      * new node. If the current node has no previous node, returns
0490      * \c null , and retains the current node.
0491      *
0492      * @return The new node, or \c null if the current
0493      * node has no previous node.
0494      *
0495      * @exception Exceptions from user code
0496      * Any exceptions raised by a user-written Filter will propagate
0497      * through.
0498      *
0499      */
0500     Node previousNode();
0501 
0502     /**
0503      * Moves the \c TreeWalker to the next node in
0504      * document order relative to the current node, and returns the
0505      * new node. If the current node has no next node, returns
0506      * \c null , and retains the current node.
0507      *
0508      * @return The new node, or \c null if the current
0509      * node has no next node.
0510      *
0511      * @exception Exceptions from user code
0512      * Any exceptions raised by a user-written Filter will propagate
0513      * through.
0514      *
0515      */
0516     Node nextNode();
0517 
0518     /**
0519      * @internal
0520      * not part of the DOM
0521      */
0522     TreeWalkerImpl *handle() const;
0523     bool isNull() const;
0524 
0525 protected:
0526     TreeWalker(TreeWalkerImpl *i);
0527     TreeWalkerImpl *impl;
0528 };
0529 
0530 } // namespace
0531 
0532 #endif