001 /*
002 * This file is part of the Echo Point Project. This project is a collection
003 * of Components that have extended the Echo Web Application Framework.
004 *
005 * Version: MPL 1.1/GPL 2.0/LGPL 2.1
006 *
007 * The contents of this file are subject to the Mozilla Public License Version
008 * 1.1 (the "License"); you may not use this file except in compliance with
009 * the License. You may obtain a copy of the License at
010 * http://www.mozilla.org/MPL/
011 *
012 * Software distributed under the License is distributed on an "AS IS" basis,
013 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
014 * for the specific language governing rights and limitations under the
015 * License.
016 *
017 * Alternatively, the contents of this file may be used under the terms of
018 * either the GNU General Public License Version 2 or later (the "GPL"), or
019 * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
020 * in which case the provisions of the GPL or the LGPL are applicable instead
021 * of those above. If you wish to allow use of your version of this file only
022 * under the terms of either the GPL or the LGPL, and not to allow others to
023 * use your version of this file under the terms of the MPL, indicate your
024 * decision by deleting the provisions above and replace them with the notice
025 * and other provisions required by the GPL or the LGPL. If you do not delete
026 * the provisions above, a recipient may use your version of this file under
027 * the terms of any one of the MPL, the GPL or the LGPL.
028 */
029
030 /*
031 * This file was taken from the Echo 1.x code base on the 23rd Jan 2006 and made part of
032 * EchoPointNG. It is therefore Copyright (C) 2002-2004 NextApp, Inc.
033 */
034
035 /*
036 * This file is part of the Echo Web Application Framework (hereinafter "Echo").
037 * Copyright (C) 2002-2004 NextApp, Inc.
038 *
039 * Version: MPL 1.1/GPL 2.0/LGPL 2.1
040 *
041 * The contents of this file are subject to the Mozilla Public License Version
042 * 1.1 (the "License"); you may not use this file except in compliance with
043 * the License. You may obtain a copy of the License at
044 * http://www.mozilla.org/MPL/
045 *
046 * Software distributed under the License is distributed on an "AS IS" basis,
047 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
048 * for the specific language governing rights and limitations under the
049 * License.
050 *
051 * Alternatively, the contents of this file may be used under the terms of
052 * either the GNU General Public License Version 2 or later (the "GPL"), or
053 * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
054 * in which case the provisions of the GPL or the LGPL are applicable instead
055 * of those above. If you wish to allow use of your version of this file only
056 * under the terms of either the GPL or the LGPL, and not to allow others to
057 * use your version of this file under the terms of the MPL, indicate your
058 * decision by deleting the provisions above and replace them with the notice
059 * and other provisions required by the GPL or the LGPL. If you do not delete
060 * the provisions above, a recipient may use your version of this file under
061 * the terms of any one of the MPL, the GPL or the LGPL.
062 */
063
064 package echopoint.util;
065
066 import java.util.ArrayList;
067 import java.util.List;
068
069 import nextapp.echo.app.ImageReference;
070
071 import org.w3c.dom.Document;
072 import org.w3c.dom.Node;
073
074 //import echopoint.ui.util.ImageManager;
075
076 /**
077 * Encodes text strings into HTML.
078 */
079 public class HtmlKit {
080
081 public static final int NEWLINE_REMOVE = 3;
082
083 public static final int NEWLINE_TO_BR = 2;
084
085 public static final int NEWLINE_TO_SPACE = 1;
086
087 public static final int NEWLINE_TRANSPARENT = 0;
088
089 /**
090 * Encodes a string of text into HTML by replacing less than, greater than,
091 * ampersand, and quotation mark characters with their HTML escaped
092 * equivalents. Groups of spaces are replaced with alternating spaces and
093 * non-breaking space characters.
094 *
095 * @param text
096 * The text to be encoded into HTML.
097 * @return The text, converted to HTML. Newlines will be left intact, NOT
098 * translated to <br> tags.
099 */
100 public static String encode(String text) {
101 return encode(text, NEWLINE_TRANSPARENT);
102 }
103 /**
104 * Encodes a string of text into HTML by replacing less than, greater than,
105 * ampersand, and quotation mark characters with their HTML escaped
106 * equivalents. Groups of spaces are replaced with alternating spaces and
107 * non-breaking space characters.
108 *
109 * @param text
110 * The text to be encoded into HTML.
111 * @param newLinePolicy
112 * The policy for handling newline characters, one of the
113 * following values:
114 * <ul>
115 * <li>NEWLINE_TRANSPARENT - Leave newline characters intact.</li>
116 * <li>NEWLINE_TO_SPACE - Convert newlines to spaces.</li>
117 * <li>NEWLINE_TO_BR - Convert newlines to <br> tags.</li>
118 * <li>NEWLINE_REMOVE - Remove newlines entirely.</li>
119 * </ul>
120 * @return The text, converted to HTML.
121 */
122 public static String encode(String text, int newLinePolicy) {
123 StringBuffer sb = new StringBuffer();
124
125 final String quot = """; // String.valueOf((char) 0x0022); // why can I do "\u0022"
126 final String amp = "&"; //"\u0026";
127 final String lt = "<"; //"\u003C";
128 final String gt = ">"; //"\u003E";
129 final String nbsp = " "; //"\u00a0";
130
131
132 if (text != null) {
133 int length = text.length();
134 int startIndex = 0;
135 int index = 0;
136
137 while (index < length) {
138 switch (text.charAt(index)) {
139 case ' ':
140 if (index == 0 || index == length - 1) {
141 // Convert spaces at beginning or end of text string to
142 // NBSPs.
143 if (startIndex < index) {
144 sb.append(text.substring(startIndex, index));
145 }
146 sb.append(nbsp);
147 startIndex = index + 1;
148 } else if (index < length - 1 && text.charAt(index + 1) == ' ') {
149 // Break down blocks of spaces in text so that text is
150 // formatted correctly.
151 // This code, while moderately confusing is necessary.
152 // The rule is that non-breaking space (NBSP)
153 // characters should replace every other space in a
154 // continued string of spaces. The exception is
155 // that a NBSP should never immediately precede a
156 // character.
157 if (startIndex < index) {
158 sb.append(text.substring(startIndex, index));
159 }
160 if (index < length - 3 && text.charAt(index + 2) == ' ' && text.charAt(index + 3) != ' ') {
161 sb.append(nbsp);
162 sb.append(nbsp);
163 sb.append(" ");
164 index += 2; // skip second and third space.
165 } else {
166 sb.append(nbsp);
167 sb.append(" ");
168 ++index; // skip second space.
169 }
170 startIndex = index + 1;
171 }
172 break;
173 case '\r':
174 case '\n':
175 if (newLinePolicy != NEWLINE_TRANSPARENT) {
176 if (startIndex < index) {
177 sb.append(text.substring(startIndex, index));
178 }
179 if (index < length - 1
180 && ((text.charAt(index) == '\r' && text.charAt(index + 1) == '\n') || (text.charAt(index) == '\n' && text
181 .charAt(index + 1) == '\r'))) {
182 ++index; // skip second character of newline
183 // sequence.
184 }
185 switch (newLinePolicy) {
186 case NEWLINE_TO_SPACE:
187 sb.append(" ");
188 break;
189 case NEWLINE_TO_BR:
190 sb.append("<br/>\n");
191 break;
192 // NEWLINE_REMOVE will not add any characters to output.
193 }
194 startIndex = index + 1;
195 }
196 break;
197 case '<':
198 if (startIndex < index) {
199 sb.append(text.substring(startIndex, index));
200 }
201 sb.append(lt);
202 startIndex = index + 1;
203 break;
204 case '>':
205 if (startIndex < index) {
206 sb.append(text.substring(startIndex, index));
207 }
208 sb.append(gt);
209 startIndex = index + 1;
210 break;
211 case '"':
212 if (startIndex < index) {
213 sb.append(text.substring(startIndex, index));
214 }
215 sb.append(quot);
216 startIndex = index + 1;
217 break;
218 case '&':
219 if (startIndex < index) {
220 sb.append(text.substring(startIndex, index));
221 }
222 sb.append(amp);
223 startIndex = index + 1;
224 break;
225 }
226
227 ++index;
228 }
229
230 if (startIndex < index) {
231 sb.append(text.substring(startIndex));
232 }
233 }
234
235 return sb.toString();
236 }
237
238 /**
239 * Encodes a string of text into DOM Nodes by taking new lines and replacing
240 * them aoccording to the policy provided.
241 *
242 * @param text
243 * The text to be encoded into DOM Nodes.
244 * @param newLinePolicy
245 * The policy for handling newline characters, one of the
246 * following values:
247 * <ul>
248 * <li>NEWLINE_TRANSPARENT - Leave newline characters intact.</li>
249 * <li>NEWLINE_TO_SPACE - Convert newlines to spaces.</li>
250 * <li>NEWLINE_TO_BR - Convert newlines to <br> tags.</li>
251 * <li>NEWLINE_REMOVE - Remove newlines entirely.</li>
252 * </ul>
253 * @return The text, converted to an array of DOM Nodes.
254 */
255 public static Node[] encodeNewLines(Document document, String text, int newLinePolicy) {
256 List nodeList = new ArrayList();
257 StringBuffer sb = new StringBuffer();
258 int length = text.length();
259 int startIndex = 0;
260 int index = 0;
261
262 while (index < length) {
263 switch (text.charAt(index)) {
264 case '\r':
265 case '\n':
266 if (newLinePolicy != NEWLINE_TRANSPARENT) {
267 if (startIndex < index) {
268 sb.append(text.substring(startIndex, index));
269 }
270 if (index < length - 1
271 && ((text.charAt(index) == '\r' && text.charAt(index + 1) == '\n') || (text.charAt(index) == '\n' && text
272 .charAt(index + 1) == '\r'))) {
273 ++index; // skip second character of newline
274 // sequence.
275 }
276 switch (newLinePolicy) {
277 case NEWLINE_TO_SPACE:
278 sb.append(" ");
279 break;
280 case NEWLINE_TO_BR:
281 Node node = document.createTextNode(sb.toString());
282 nodeList.add(node);
283 node = document.createElement("br");
284 nodeList.add(node);
285 sb.setLength(0);
286 break;
287 // NEWLINE_REMOVE will not add any characters to output.
288 }
289 startIndex = index + 1;
290 }
291 break;
292 }
293 ++index;
294 }
295 if (startIndex < index) {
296 sb.append(text.substring(startIndex));
297 Node node = document.createTextNode(sb.toString());
298 nodeList.add(node);
299 }
300 return (Node[]) nodeList.toArray(new Node[nodeList.size()]);
301 }
302
303 /**
304 * todo Fix this method!
305 * This returns the URI for the given <code>ImageReference</code>
306 *
307 * @param imageReference -
308 * the <code>ImageReference</code> to get a URI for
309 * @return the URI for the given <code>ImageReference</code>
310 * @throws IllegalArgumentException -
311 * if the <code>ImageReference</code> is null
312 */
313 // public static String getImageURI(ImageReference imageReference) {
314 // if (imageReference == null) {
315 // throw new IllegalArgumentException("The imageReference must not be null!");
316 // }
317 // return ImageManager.getURI(imageReference);
318 // }
319
320 /** Non-instantiable class. */
321 private HtmlKit() {
322 }
323 }