View Javadoc

1   /*
2    * Copyright 2001-2005 (C) MetaStuff, Ltd. All Rights Reserved.
3    *
4    * This software is open source.
5    * See the bottom of this file for the licence.
6    */
7   
8   package org.dom4j.io;
9   
10  import org.dom4j.Document;
11  import org.dom4j.Element;
12  import org.dom4j.ElementHandler;
13  import org.dom4j.ElementPath;
14  
15  /***
16   * This {@link org.dom4j.ElementHandler}is used to trigger {@link
17   * ElementModifier} objects in order to modify (parts of) the Document on the
18   * fly.
19   * 
20   * <p>
21   * When an element is completely parsed, a copy is handed to the associated (if
22   * any) {@link ElementModifier}that on his turn returns the modified element
23   * that has to come in the tree.
24   * </p>
25   * 
26   * @author Wonne Keysers (Realsoftware.be)
27   */
28  class SAXModifyElementHandler implements ElementHandler {
29      private ElementModifier elemModifier;
30  
31      private Element modifiedElement;
32  
33      public SAXModifyElementHandler(ElementModifier elemModifier) {
34          this.elemModifier = elemModifier;
35      }
36  
37      public void onStart(ElementPath elementPath) {
38          this.modifiedElement = elementPath.getCurrent();
39      }
40  
41      public void onEnd(ElementPath elementPath) {
42          try {
43              Element origElement = elementPath.getCurrent();
44              Element currentParent = origElement.getParent();
45  
46              if (currentParent != null) {
47                  // Clone sets parent + document to null
48                  Element clonedElem = (Element) origElement.clone();
49  
50                  // Ask for modified element
51                  modifiedElement = elemModifier.modifyElement(clonedElem);
52  
53                  if (modifiedElement != null) {
54                      // Restore parent + document
55                      modifiedElement.setParent(origElement.getParent());
56                      modifiedElement.setDocument(origElement.getDocument());
57  
58                      // Replace old with new element in parent
59                      int contentIndex = currentParent.indexOf(origElement);
60                      currentParent.content().set(contentIndex, modifiedElement);
61                  }
62  
63                  // Remove the old element
64                  origElement.detach();
65              } else {
66                  if (origElement.isRootElement()) {
67                      // Clone sets parent + document to null
68                      Element clonedElem = (Element) origElement.clone();
69  
70                      // Ask for modified element
71                      modifiedElement = elemModifier.modifyElement(clonedElem);
72  
73                      if (modifiedElement != null) {
74                          // Restore parent + document
75                          modifiedElement.setDocument(origElement.getDocument());
76  
77                          // Replace old with new element in parent
78                          Document doc = origElement.getDocument();
79                          doc.setRootElement(modifiedElement);
80                      }
81  
82                      // Remove the old element
83                      origElement.detach();
84                  }
85              }
86  
87              // Put the new element on the ElementStack, it might get pruned by
88              // the PruningDispatchHandler
89              if (elementPath instanceof ElementStack) {
90                  ElementStack elementStack = ((ElementStack) elementPath);
91                  elementStack.popElement();
92                  elementStack.pushElement(modifiedElement);
93              }
94          } catch (Exception ex) {
95              throw new SAXModifyException(ex);
96          }
97      }
98  
99      /***
100      * DOCUMENT ME!
101      * 
102      * @return Returns the modified Element.
103      */
104     protected Element getModifiedElement() {
105         return modifiedElement;
106     }
107 }
108 
109 /*
110  * Redistribution and use of this software and associated documentation
111  * ("Software"), with or without modification, are permitted provided that the
112  * following conditions are met:
113  * 
114  * 1. Redistributions of source code must retain copyright statements and
115  * notices. Redistributions must also contain a copy of this document.
116  * 
117  * 2. Redistributions in binary form must reproduce the above copyright notice,
118  * this list of conditions and the following disclaimer in the documentation
119  * and/or other materials provided with the distribution.
120  * 
121  * 3. The name "DOM4J" must not be used to endorse or promote products derived
122  * from this Software without prior written permission of MetaStuff, Ltd. For
123  * written permission, please contact dom4j-info@metastuff.com.
124  * 
125  * 4. Products derived from this Software may not be called "DOM4J" nor may
126  * "DOM4J" appear in their names without prior written permission of MetaStuff,
127  * Ltd. DOM4J is a registered trademark of MetaStuff, Ltd.
128  * 
129  * 5. Due credit should be given to the DOM4J Project - http://www.dom4j.org
130  * 
131  * THIS SOFTWARE IS PROVIDED BY METASTUFF, LTD. AND CONTRIBUTORS ``AS IS'' AND
132  * ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
133  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
134  * ARE DISCLAIMED. IN NO EVENT SHALL METASTUFF, LTD. OR ITS CONTRIBUTORS BE
135  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
136  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
137  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
138  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
139  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
140  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
141  * POSSIBILITY OF SUCH DAMAGE.
142  * 
143  * Copyright 2001-2005 (C) MetaStuff, Ltd. All Rights Reserved.
144  */