1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 package org.millscript.millscript.render;
23
24 import org.millscript.commons.util.IList;
25 import org.millscript.commons.util.MapIterator;
26 import org.millscript.millscript.datatypes.CDATA;
27 import org.millscript.millscript.datatypes.XmlComment;
28 import org.millscript.millscript.datatypes.XmlElement;
29 import org.millscript.millscript.tools.StringTools;
30
31 import java.io.IOException;
32 import java.util.Iterator;
33 import java.util.List;
34
35 /**
36 * This renderer is used for rendering the CDATA content of an element in XML.
37 * As such it delegates most of it's rendering methods to a normal XML
38 * renderer.
39 */
40 public final class XMLCDATARenderer implements Renderer {
41
42 /**
43 * The parent XML renderer to delegate rendering calls to.
44 */
45 private final Renderer parentRenderer;
46
47 /**
48 * Constructs a new XML CDATA renderer, to use the specified XML renderer
49 * for rendering.
50 *
51 * @param hr the XML renderer to delegate to
52 */
53 public XMLCDATARenderer( final Renderer hr ) {
54 this.parentRenderer = hr;
55 }
56
57 /**
58 * @see org.millscript.millscript.render.Renderer#append(char)
59 */
60 public void append( final char ch ) throws IOException {
61 parentRenderer.append( ch );
62 }
63
64 /**
65 * @see org.millscript.millscript.render.Renderer#append(java.lang.CharSequence)
66 */
67 public void append( final CharSequence cs ) throws IOException {
68 parentRenderer.append( cs );
69 }
70
71 /**
72 * @see org.millscript.millscript.render.Renderer#appendEscapeFor(char)
73 */
74 public void appendEscapeFor( final char ch ) throws IOException {
75 parentRenderer.appendEscapeFor( ch );
76 }
77
78 /**
79 * @see org.millscript.millscript.render.Renderer#appendNoEscape(char)
80 */
81 public void appendNoEscape( final char ch ) throws IOException {
82 parentRenderer.appendNoEscape( ch );
83 }
84
85 /**
86 * @see org.millscript.millscript.render.Renderer#appendNoEscape(java.lang.CharSequence)
87 */
88 public void appendNoEscape( final CharSequence cs ) throws IOException {
89 parentRenderer.appendNoEscape( cs );
90 }
91
92 /**
93 * @see org.millscript.millscript.render.Renderer#canEncode(char)
94 */
95 public boolean canEncode( final char ch ) {
96 return parentRenderer.canEncode( ch );
97 }
98
99 /**
100 * @see org.millscript.millscript.render.Renderer#render(java.lang.Object)
101 */
102 public void render( final Object o ) throws IOException {
103 if ( o == null ) {
104 return;
105 } else if ( o instanceof Renderable ) {
106 ((Renderable) o).render( this );
107 } else if ( o instanceof IList ) {
108 MapIterator it = ((IList) o).iterator( true );
109 while ( it.hasNext() ) {
110 this.render( it.nextValue() );
111 }
112 } else if ( o instanceof List ) {
113 Iterator it = ((List)o).iterator();
114 while ( it.hasNext() ) {
115 this.render( it.next() );
116 }
117 } else {
118
119
120
121
122 this.renderObject( o );
123 }
124 }
125
126 /**
127 * @see org.millscript.millscript.render.Renderer#renderAsDocument(java.lang.Object)
128 */
129 public void renderAsDocument( final Object o ) {
130 parentRenderer.renderAsDocument( o );
131 }
132
133 /**
134 * @see org.millscript.millscript.render.Renderer#renderAsFragment(org.millscript.commons.util.IList)
135 */
136 public void renderAsFragment( final IList l ) {
137 parentRenderer.renderAsFragment( l );
138 }
139
140 /**
141 * @see org.millscript.millscript.render.Renderer#renderCDATA(org.millscript.millscript.datatypes.CDATA)
142 */
143 public void renderCDATA( final CDATA c ) throws IOException {
144 parentRenderer.appendNoEscape( "<![CDATA[" );
145 final Object[] kids = c.getStore();
146 final int nkids = kids.length;
147 for ( int i = 0; i < nkids; i++ ) {
148 this.render( kids[ i ] );
149 }
150 parentRenderer.appendNoEscape( "]]>" );
151 }
152
153 /**
154 * @see org.millscript.millscript.render.Renderer#renderDocumentFooter()
155 */
156 public void renderDocumentFooter() throws IOException {
157 parentRenderer.renderDocumentFooter();
158 }
159
160 /**
161 * @see org.millscript.millscript.render.Renderer#renderDocumentHeader()
162 */
163 public void renderDocumentHeader() throws IOException {
164 parentRenderer.renderDocumentHeader();
165 }
166
167 /**
168 * @see org.millscript.millscript.render.Renderer#renderObject(java.lang.Object)
169 */
170 public void renderObject( final Object o ) throws IOException {
171
172
173
174 parentRenderer.appendNoEscape(
175 StringTools.substituteAll(
176 o.toString(),
177 "]]>",
178 "]]]]><![CDATA[>"
179 )
180 );
181 }
182
183 /**
184 * @see org.millscript.millscript.render.Renderer#renderXMLComment(org.millscript.millscript.datatypes.XmlComment)
185 */
186 public void renderXMLComment( final XmlComment c ) throws IOException {
187 parentRenderer.renderXMLComment( c );
188 }
189
190 /**
191 * @see org.millscript.millscript.render.Renderer#renderXMLElement(org.millscript.millscript.datatypes.XmlElement)
192 */
193 public void renderXMLElement( final XmlElement x ) throws IOException {
194 parentRenderer.appendNoEscape( '<' );
195 parentRenderer.appendNoEscape( x.tagName() );
196
197 MapIterator it = x.getAttributes().iterator( true );
198 while ( it.hasNext() ) {
199 Object key = it.nextKey();
200 Object val = it.currentValue();
201 if ( key != null ) {
202 parentRenderer.appendNoEscape( ' ' );
203 parentRenderer.appendNoEscape( key.toString() );
204
205
206 parentRenderer.appendNoEscape( "=\"" );
207 if ( val != null ) {
208 parentRenderer.appendNoEscape( val.toString() );
209 }
210 parentRenderer.appendNoEscape( '"' );
211 }
212 }
213
214 final Object[] kids = x.getChildren();
215 final int nkids = kids.length;
216
217 if ( nkids == 0 ) {
218 parentRenderer.appendNoEscape( " />" );
219 } else {
220 parentRenderer.appendNoEscape( '>' );
221 for ( int i = 0; i < nkids; i++ ) {
222 this.render( kids[ i ] );
223 }
224 parentRenderer.appendNoEscape( "</" );
225 parentRenderer.appendNoEscape( x.tagName() );
226 parentRenderer.appendNoEscape( '>' );
227 }
228 }
229
230 }