rangeimpl.java

来自「JAVA的一些源码 JAVA2 STANDARD EDITION DEVELO」· Java 代码 · 共 1,767 行 · 第 1/5 页

JAVA
1,767
字号
                Range range = fDocument.createRange();        range.setStart(fStartContainer, fStartOffset);        range.setEnd(fEndContainer, fEndOffset);        return range;    }        public String toString(){    	if( fDetach) {    		throw new DOMException(    		DOMException.INVALID_STATE_ERR,                 DOMMessageFormatter.formatMessage(DOMMessageFormatter.DOM_DOMAIN, "INVALID_STATE_ERR", null));    	}    	    	Node node = fStartContainer;        Node stopNode = fEndContainer;    	StringBuffer sb = new StringBuffer();    	if (fStartContainer.getNodeType() == Node.TEXT_NODE    	 || fStartContainer.getNodeType() == Node.CDATA_SECTION_NODE    	) {    	    if (fStartContainer == fEndContainer) {    	        sb.append(fStartContainer.getNodeValue().substring(fStartOffset, fEndOffset));    	        return sb.toString();            }    	    sb.append(fStartContainer.getNodeValue().substring(fStartOffset));            node=nextNode (node,true); //fEndContainer!=fStartContainer    	        	}        else {  //fStartContainer is not a TextNode            node=node.getFirstChild();            if (fStartOffset>0) { //find a first node within a range, specified by fStartOffset               int counter=0;               while (counter<fStartOffset && node!=null) {                   node=node.getNextSibling();                   counter++;               }              }            if (node == null) {                   node = nextNode(fStartContainer,false);            }        }         if ( fEndContainer.getNodeType()!= Node.TEXT_NODE &&             fEndContainer.getNodeType()!= Node.CDATA_SECTION_NODE ){             int i=fEndOffset;             stopNode = fEndContainer.getFirstChild();             while( i>0 && stopNode!=null ){                 --i;                 stopNode = stopNode.getNextSibling();             }             if ( stopNode == null )                 stopNode = nextNode( fEndContainer, false );         }         while (node != stopNode) {  //look into all kids of the Range             if (node == null) break;             if (node.getNodeType() == Node.TEXT_NODE             ||  node.getNodeType() == Node.CDATA_SECTION_NODE) {                 sb.append(node.getNodeValue());             }             node = nextNode(node, true);         }      	if (fEndContainer.getNodeType() == Node.TEXT_NODE    	 || fEndContainer.getNodeType() == Node.CDATA_SECTION_NODE) {    	    sb.append(fEndContainer.getNodeValue().substring(0,fEndOffset));    	}    	return sb.toString();    }        public void detach() {        fDetach = true;        fDocument.removeRange(this);    }        //     // Mutation functions    //        /** Signal other Ranges to update their start/end      *  containers/offsets. The data has already been split     *  into the two Nodes.     */    void signalSplitData(Node node, Node newNode, int offset) {        fSplitNode = node;        // notify document        fDocument.splitData(node, newNode, offset);        fSplitNode = null;    }        /** Fix up this Range if another Range has split a Text Node     *  into 2 Nodes.     */    void receiveSplitData(Node node, Node newNode, int offset) {        if (node == null || newNode == null) return;        if (fSplitNode == node) return;                if (node == fStartContainer         && fStartContainer.getNodeType() == Node.TEXT_NODE) {            if (fStartOffset > offset) {                fStartOffset = fStartOffset - offset;                fStartContainer = newNode;            }        }        if (node == fEndContainer         && fEndContainer.getNodeType() == Node.TEXT_NODE) {            if (fEndOffset > offset) {                fEndOffset = fEndOffset-offset;                fEndContainer = newNode;            }        }            }       /** This function inserts text into a Node and invokes     *  a method to fix-up all other Ranges.     */    void deleteData(CharacterData node, int offset, int count) {        fDeleteNode = node;        node.deleteData( offset,  count);        fDeleteNode = null;    }            /** This function is called from DOM.     *  The  text has already beeen inserted.     *  Fix-up any offsets.     */    void receiveDeletedText(Node node, int offset, int count) {        if (node == null) return;        if (fDeleteNode == node) return;        if (node == fStartContainer         && fStartContainer.getNodeType() == Node.TEXT_NODE) {            if (fStartOffset > offset+count) {                fStartOffset = offset+(fStartOffset-(offset+count));            } else             if (fStartOffset > offset) {                fStartOffset = offset;            }          }        if (node == fEndContainer         && fEndContainer.getNodeType() == Node.TEXT_NODE) {            if (fEndOffset > offset+count) {                fEndOffset = offset+(fEndOffset-(offset+count));            } else             if (fEndOffset > offset) {                fEndOffset = offset;            }          }            }       /** This function inserts text into a Node and invokes     *  a method to fix-up all other Ranges.     */    void insertData(CharacterData node, int index, String insert) {        fInsertNode = node;        node.insertData( index,  insert);        fInsertNode = null;    }            /** This function is called from DOM.     *  The  text has already beeen inserted.     *  Fix-up any offsets.     */    void receiveInsertedText(Node node, int index, int len) {        if (node == null) return;        if (fInsertNode == node) return;        if (node == fStartContainer         && fStartContainer.getNodeType() == Node.TEXT_NODE) {            if (index < fStartOffset) {                fStartOffset = fStartOffset+len;            }        }        if (node == fEndContainer         && fEndContainer.getNodeType() == Node.TEXT_NODE) {            if (index < fEndOffset) {                fEndOffset = fEndOffset+len;            }        }            }       /** This function is called from DOM.     *  The  text has already beeen replaced.     *  Fix-up any offsets.     */    void receiveReplacedText(Node node) {        if (node == null) return;        if (node == fStartContainer         && fStartContainer.getNodeType() == Node.TEXT_NODE) {            fStartOffset = 0;        }        if (node == fEndContainer         && fEndContainer.getNodeType() == Node.TEXT_NODE) {            fEndOffset = 0;        }            }        /** This function is called from the DOM.     *  This node has already been inserted into the DOM.     *  Fix-up any offsets.     */    public void insertedNodeFromDOM(Node node) {        if (node == null) return;        if (fInsertNode == node) return;                Node parent = node.getParentNode();                if (parent == fStartContainer) {            int index = indexOf(node, fStartContainer);            if (index < fStartOffset) {                fStartOffset++;            }        }                if (parent == fEndContainer) {            int index = indexOf(node, fEndContainer);            if (index < fEndOffset) {                fEndOffset++;            }        }            }        /** This function is called within Range      *  instead of Node.removeChild,     *  so that the range can remember that it is actively     *  removing this child.     */         Node fRemoveChild = null;    Node removeChild(Node parent, Node child) {        fRemoveChild = child;        Node n = parent.removeChild(child);        fRemoveChild = null;        return n;    }        /** This function must be called by the DOM _BEFORE_     *  a node is deleted, because at that time it is     *  connected in the DOM tree, which we depend on.     */    void removeNode(Node node) {        if (node == null) return;        if (fRemoveChild == node) return;                Node parent = node.getParentNode();                if (parent == fStartContainer) {            int index = indexOf(node, fStartContainer);            if (index < fStartOffset) {                fStartOffset--;            }        }                if (parent == fEndContainer) {            int index = indexOf(node, fEndContainer);            if (index < fEndOffset) {                fEndOffset--;            }        }        //startContainer or endContainer or both is/are the ancestor(s) of the Node to be deleted        if (parent != fStartContainer         ||  parent != fEndContainer) {            if (isAncestorOf(node, fStartContainer)) {                fStartContainer = parent;                fStartOffset = indexOf( node, parent);            }               if (isAncestorOf(node, fEndContainer)) {                fEndContainer = parent;                fEndOffset = indexOf( node, parent);            }        }             }            //    // Utility functions.    //        // parameters for traverseContents(int)    //REVIST: use boolean, since there are only 2 now...    static final int EXTRACT_CONTENTS = 1;    static final int CLONE_CONTENTS = 2;    static final int DELETE_CONTENTS = 3;        /**     * This is the master routine invoked to visit the nodes     * selected by this range.  For each such node, different     * actions are taken depending on the value of the     * <code>how</code> argument.     *      * @param how    Specifies what type of traversal is being     *               requested (extract, clone, or delete).     *               Legal values for this argument are:     *      *               <ol>     *               <li><code>EXTRACT_CONTENTS</code> - will produce     *               a document fragment containing the range's content.     *               Partially selected nodes are copied, but fully     *               selected nodes are moved.     *                    *               <li><code>CLONE_CONTENTS</code> - will leave the     *               context tree of the range undisturbed, but sill     *               produced cloned content in a document fragment     *                    *               <li><code>DELETE_CONTENTS</code> - will delete from     *               the context tree of the range, all fully selected     *               nodes.     *               </ol>     *      * @return Returns a document fragment containing any     *         copied or extracted nodes.  If the <code>how</code>     *         parameter was <code>DELETE_CONTENTS</code>, the     *         return value is null.     */    private DocumentFragment traverseContents( int how )        throws DOMException    {        if (fStartContainer == null || fEndContainer == null) {            return null; // REVIST: Throw exception?        }                //Check for a detached range.        if( fDetach) {            throw new DOMException(                DOMException.INVALID_STATE_ERR,                 DOMMessageFormatter.formatMessage(DOMMessageFormatter.DOM_DOMAIN, "INVALID_STATE_ERR", null));        }        /*          Traversal is accomplished by first determining the          relationship between the endpoints of the range.          For each of four significant relationships, we will          delegate the traversal call to a method that           can make appropriate assumptions.         */        // case 1: same container        if ( fStartContainer == fEndContainer )            return traverseSameContainer( how );        // case 2: Child C of start container is ancestor of end container         // This can be quickly tested by walking the parent chain of         // end container        int endContainerDepth = 0;        for ( Node c = fEndContainer, p = c.getParentNode();             p != null;             c = p, p = p.getParentNode())        {            if (p == fStartContainer)

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?