1 28 package net.sf.jasperreports.engine.util; 29 30 import java.awt.Color ; 31 import java.io.IOException ; 32 import java.io.Writer ; 33 import java.util.ArrayList ; 34 import java.util.Arrays ; 35 import java.util.Iterator ; 36 import java.util.List ; 37 import java.util.Map ; 38 39 import net.sf.jasperreports.engine.JRExpression; 40 41 45 public class JRXmlWriteHelper 46 { 47 private final Writer writer; 48 49 private final List indents; 50 51 private int indent; 52 private final List elementStack; 53 private StringBuffer buffer; 54 private StackElement lastElement; 55 56 protected static class Attribute 57 { 58 String name; 59 String value; 60 61 Attribute(String name, String value) 62 { 63 this.name = name; 64 this.value = value; 65 } 66 } 67 68 protected static class StackElement 69 { 70 String name; 71 List atts; 72 boolean hasChildren; 73 74 StackElement(String name) 75 { 76 this.name = name; 77 this.atts = new ArrayList (); 78 this.hasChildren = false; 79 } 80 81 void addAttribute(String attName, String value) 82 { 83 atts.add(new Attribute(attName, value)); 84 } 85 } 86 87 public JRXmlWriteHelper(Writer writer) 88 { 89 this.writer = writer; 90 91 indents = new ArrayList (); 92 93 indent = 0; 94 elementStack = new ArrayList (); 95 lastElement = null; 96 97 clearBuffer(); 98 } 99 100 public void writeProlog(String encoding) throws IOException 101 { 102 writer.write("<?xml version=\"1.0\" encoding=\"" + encoding + "\"?>\n"); 103 } 104 105 public void writePublicDoctype(String rootElement, String description, String dtdLocation) throws IOException 106 { 107 writer.write("<!DOCTYPE " + rootElement + " PUBLIC \"" + description + "\" \"" + dtdLocation + "\">\n\n"); 108 } 109 110 public void startElement(String name) 111 { 112 ++indent; 113 lastElement = new StackElement(name); 114 elementStack.add(lastElement); 115 } 116 117 protected void writeParents(boolean content) throws IOException 118 { 119 int stackSize = elementStack.size(); 120 121 int startWrite = stackSize - 1; 122 while (startWrite >= 0) 123 { 124 StackElement element = (StackElement) elementStack.get(startWrite); 125 126 if (element.hasChildren) 127 { 128 break; 129 } 130 131 if (startWrite < stackSize - 1) 132 { 133 element.hasChildren = true; 134 } 135 else 136 { 137 element.hasChildren |= content; 138 } 139 140 --startWrite; 141 } 142 143 for (int i = startWrite + 1; i < stackSize; ++i) 144 { 145 StackElement element = (StackElement) elementStack.get(i); 146 writeElementAttributes(element, i); 147 } 148 } 149 150 public void writeCDATA(String data) throws IOException 151 { 152 if (data != null) 153 { 154 writeParents(true); 155 156 buffer.append(getIndent(indent)); 157 buffer.append("<![CDATA["); 158 buffer.append(data); 159 buffer.append("]]>\n"); 160 flushBuffer(); 161 } 162 } 163 164 public void writeCDATAElement(String name, String data) throws IOException 165 { 166 if (data != null) 167 { 168 writeParents(true); 169 170 buffer.append(getIndent(indent)); 171 buffer.append('<'); 172 buffer.append(name); 173 buffer.append("><![CDATA["); 174 buffer.append(data); 175 buffer.append("]]></"); 176 buffer.append(name); 177 buffer.append(">\n"); 178 flushBuffer(); 179 } 180 } 181 182 public void writeCDATAElement(String name, String data, String attName, String attValue) throws IOException 183 { 184 if (data != null) 185 { 186 writeParents(true); 187 188 buffer.append(getIndent(indent)); 189 buffer.append('<'); 190 buffer.append(name); 191 buffer.append(' '); 192 buffer.append(attName); 193 buffer.append("=\""); 194 buffer.append(attValue); 195 buffer.append("\"><![CDATA["); 196 buffer.append(data); 197 buffer.append("]]></"); 198 buffer.append(name); 199 buffer.append(">\n"); 200 flushBuffer(); 201 } 202 } 203 204 protected void writeElementAttributes(StackElement element, int level) throws IOException 205 { 206 buffer.append(getIndent(level)); 207 buffer.append('<'); 208 buffer.append(element.name); 209 for (Iterator i = element.atts.iterator(); i.hasNext();) 210 { 211 Attribute att = (Attribute) i.next(); 212 buffer.append(' '); 213 buffer.append(att.name); 214 buffer.append("=\""); 215 buffer.append(att.value); 216 buffer.append('"'); 217 } 218 219 if (element.hasChildren) 220 { 221 buffer.append(">\n"); 222 } 223 else 224 { 225 buffer.append("/>\n"); 226 } 227 228 flushBuffer(); 229 } 230 231 public void closeElement() throws IOException 232 { 233 closeElement(false); 234 } 235 236 public void closeElement(boolean skipIfEmpty) throws IOException 237 { 238 --indent; 239 240 if (skipIfEmpty && lastElement.atts.size() == 0 && !lastElement.hasChildren) 241 { 242 clearBuffer(); 243 } 244 else 245 { 246 writeParents(false); 247 248 if (lastElement.hasChildren) 249 { 250 buffer.append(getIndent(indent)); 251 buffer.append("</"); 252 buffer.append(lastElement.name); 253 buffer.append(">\n"); 254 flushBuffer(); 255 } 256 } 257 258 elementStack.remove(indent); 259 lastElement = indent > 0 ? (StackElement) elementStack.get(indent - 1) : null; 260 } 261 262 protected char[] getIndent(int level) 263 { 264 if (level >= indents.size()) 265 { 266 for (int i = indents.size(); i <= level; ++i) 267 { 268 char[] str = new char[i]; 269 Arrays.fill(str, '\t'); 270 indents.add(str); 271 } 272 } 273 274 return (char[]) indents.get(level); 275 } 276 277 protected void flushBuffer() throws IOException 278 { 279 writer.write(buffer.toString()); 280 clearBuffer(); 281 } 282 283 protected void clearBuffer() 284 { 285 buffer = new StringBuffer (); 286 } 287 288 289 public void writeExpression(String name, JRExpression expression, boolean writeClass) throws IOException 290 { 291 writeExpression(name, expression, writeClass, null); 292 } 293 294 295 public void writeExpression(String name, JRExpression expression, boolean writeClass, String defaultClassName) throws IOException 296 { 297 if (expression != null) 298 { 299 if (writeClass && 300 (defaultClassName == null || !defaultClassName.equals(expression.getValueClassName()))) 301 { 302 writeCDATAElement(name, expression.getText(), "class", expression.getValueClassName()); 303 } 304 else 305 { 306 writeCDATAElement(name, expression.getText()); 307 } 308 } 309 } 310 311 protected void writeAttribute(String name, String value) 312 { 313 lastElement.addAttribute(name, value); 314 } 315 316 public void addAttribute(String name, String value) 317 { 318 if (value != null) 319 { 320 writeAttribute(name, value); 321 } 322 } 323 324 public void addEncodedAttribute(String name, String value) 325 { 326 if (value != null) 327 { 328 writeAttribute(name, JRStringUtil.xmlEncode(value)); 329 } 330 } 331 332 public void addAttribute(String name, String value, String defaultValue) 333 { 334 if (value != null && !value.equals(defaultValue)) 335 { 336 writeAttribute(name, value); 337 } 338 } 339 340 public void addEncodedAttribute(String name, String value, String defaultValue) 341 { 342 if (value != null && !value.equals(defaultValue)) 343 { 344 writeAttribute(name, JRStringUtil.xmlEncode(value)); 345 } 346 } 347 348 public void addAttribute(String name, Object value) 349 { 350 if (value != null) 351 { 352 writeAttribute(name, String.valueOf(value)); 353 } 354 } 355 356 public void addAttribute(String name, int value) 357 { 358 writeAttribute(name, String.valueOf(value)); 359 } 360 361 public void addAttributePositive(String name, int value) 362 { 363 if (value > 0) 364 { 365 writeAttribute(name, String.valueOf(value)); 366 } 367 } 368 369 public void addAttribute(String name, float value) 370 { 371 writeAttribute(name, String.valueOf(value)); 372 } 373 374 public void addAttribute(String name, float value, float defaultValue) 375 { 376 if (value != defaultValue) 377 { 378 writeAttribute(name, String.valueOf(value)); 379 } 380 } 381 382 public void addAttribute(String name, double value) 383 { 384 writeAttribute(name, String.valueOf(value)); 385 } 386 387 public void addAttribute(String name, double value, double defaultValue) 388 { 389 if (value != defaultValue) 390 { 391 writeAttribute(name, String.valueOf(value)); 392 } 393 } 394 395 public void addAttribute(String name, int value, int defaultValue) 396 { 397 if (value != defaultValue) 398 { 399 addAttribute(name, value); 400 } 401 } 402 403 public void addAttribute(String name, boolean value) 404 { 405 writeAttribute(name, String.valueOf(value)); 406 } 407 408 public void addAttribute(String name, boolean value, boolean defaultValue) 409 { 410 if (value != defaultValue) 411 { 412 addAttribute(name, value); 413 } 414 } 415 416 public void addAttribute(String name, Color value) 417 { 418 if (value != null) 419 { 420 writeAttribute(name, "#" + getHexaColor(value)); 421 } 422 } 423 424 public void addAttribute(String name, Color value, Color defaultValue) 425 { 426 if (value != null && value.getRGB() != defaultValue.getRGB()) 427 { 428 addAttribute(name, value); 429 } 430 } 431 432 public void addAttribute(String name, byte value, Map xmlValues) 433 { 434 String xmlValue = (String ) xmlValues.get(new Byte (value)); 435 writeAttribute(name, xmlValue); 436 } 437 438 public void addAttribute(String name, int value, Map xmlValues) 439 { 440 String xmlValue = (String ) xmlValues.get(new Integer (value)); 441 writeAttribute(name, xmlValue); 442 } 443 444 public void addAttribute(String name, byte value, Map xmlValues, byte defaultValue) 445 { 446 if (value != defaultValue) 447 { 448 addAttribute(name, value, xmlValues); 449 } 450 } 451 452 public void addAttribute(String name, Object value, Map xmlValues) 453 { 454 if (value != null) 455 { 456 String xmlValue = (String ) xmlValues.get(value); 457 writeAttribute(name, xmlValue); 458 } 459 } 460 461 public void addAttribute(String name, Object value, Map xmlValues, Object defaultValue) 462 { 463 if (!value.equals(defaultValue)) 464 { 465 addAttribute(name, value, xmlValues); 466 } 467 } 468 469 protected static final int COLOR_MASK = Integer.parseInt("FFFFFF", 16); 470 protected static String getHexaColor(Color color) 471 { 472 String hexa = Integer.toHexString(color.getRGB() & COLOR_MASK).toUpperCase(); 473 return ("000000" + hexa).substring(hexa.length()); 474 } 475 } 476 | Popular Tags |