1 package org.jicengine.element; 2 import org.jicengine.element.impl.CdataConverterInvocationOperation; 3 import org.jicengine.expression.ClassParser; 4 import org.jicengine.io.Resource; 5 import org.jicengine.operation.Operation; 6 import org.jicengine.operation.OperationException; 7 import org.jicengine.operation.StaticValue; 8 import org.jicengine.operation.Context; 9 10 import java.math.BigDecimal ; 11 import java.math.BigInteger ; 12 import java.net.*; 13 import java.util.Arrays ; 14 import java.util.Collection ; 15 import java.util.HashMap ; 16 import java.util.HashSet ; 17 import java.util.Locale ; 18 import java.util.Map ; 19 import java.util.TimeZone ; 20 import java.awt.Color ; 21 import java.awt.Dimension ; 22 import java.awt.Font ; 23 import java.awt.Point ; 24 import java.io.*; 25 import org.jicengine.util.StringConverter; 26 39 public class CdataHandler { 40 41 private static final String CDATA_TRUE = "true"; 42 private static final String CDATA_FALSE = "false"; 43 44 50 public static Class resolveInstanceClassFromCdata(String cdata) 51 { 52 Class instanceClass = null; 53 54 char[] chars = cdata.toCharArray(); 55 56 if( chars.length == 0){ 57 instanceClass = String .class; 58 } 59 60 if( instanceClass == null){ 61 instanceClass = getNumberClass(chars); 63 } 64 65 if( instanceClass == null){ 66 if( cdata.equals(CDATA_TRUE)){ 68 instanceClass = Boolean.TYPE; 69 } 70 else if( cdata.equals(CDATA_FALSE)){ 71 instanceClass = Boolean.TYPE; 72 } 73 } 74 75 if( instanceClass == null){ 76 instanceClass = String .class; 78 } 79 80 return instanceClass; 81 } 82 83 private static Class getNumberClass(char[] cdata) 84 { 85 int decimalIndex = -1; 86 for( int i = 0 ; i < cdata.length ; i++ ) { 87 if( Character.isDigit(cdata[i])){ 88 continue; 89 } 90 else if( cdata[i] == '.' && (decimalIndex == -1 && i > 0) ){ 91 decimalIndex = i; 93 continue; 94 } 95 else if( cdata[i] == '-' && i == 0){ 96 continue; 97 } 98 else { 99 return null; 101 } 102 } 103 104 if( decimalIndex == -1){ 105 return Integer.TYPE; 106 } 107 else { 108 return Double.TYPE; 109 } 110 } 111 112 private static Collection defaultTargetClasses; 113 private static Map constructorFactories = new HashMap (); 114 115 static { 116 defaultTargetClasses= new HashSet (); 117 defaultTargetClasses.addAll(Arrays.asList(new Object []{ 118 String .class, 119 Integer.TYPE, 120 Integer .class, 121 Double .class, 122 Double.TYPE, 123 Boolean .class, 124 Boolean.TYPE, 125 Long .class, 126 Long.TYPE, 127 Float .class, 128 Float.TYPE, 129 Short .class, 130 Short.TYPE, 131 Resource.class, 132 java.awt.Color .class, 133 Font .class, 134 java.awt.Dimension .class, 135 java.awt.Point .class, 136 java.net.URL .class, 137 java.util.TimeZone .class, 138 java.util.Locale .class, 139 java.lang.Class .class 140 })); 141 142 constructorFactories.put(String .class, new StringConstructorFactory()); 143 constructorFactories.put(Integer .class, new IntConstructorFactory()); 144 constructorFactories.put(Integer.TYPE, new IntConstructorFactory()); 145 constructorFactories.put(Double .class, new DoubleConstructorFactory()); 146 constructorFactories.put(Double.TYPE, new DoubleConstructorFactory()); 147 constructorFactories.put(Boolean .class, new BooleanConstructorFactory()); 148 constructorFactories.put(Boolean.TYPE, new BooleanConstructorFactory()); 149 constructorFactories.put(Character .class, new CharacterConstructorFactory()); 150 constructorFactories.put(Character.TYPE, new CharacterConstructorFactory()); 151 constructorFactories.put(Long .class, new LongConstructorFactory()); 152 constructorFactories.put(Long.TYPE, new LongConstructorFactory()); 153 constructorFactories.put(Short .class, new ShortConstructorFactory()); 154 constructorFactories.put(Short.TYPE, new ShortConstructorFactory()); 155 constructorFactories.put(Float .class, new FloatConstructorFactory()); 156 constructorFactories.put(Float.TYPE, new FloatConstructorFactory()); 157 constructorFactories.put(BigDecimal .class, new BigDecimalConstructorFactory()); 158 constructorFactories.put(BigInteger .class, new BigIntegerConstructorFactory()); 159 constructorFactories.put(Resource.class, new ResourceConstructorFactory()); 160 constructorFactories.put(Color .class, new ColorConstructorFactory()); 161 constructorFactories.put(Font .class, new FontConstructorFactory()); 162 constructorFactories.put(Dimension .class, new DimensionConstructorFactory()); 163 constructorFactories.put(Point .class, new PointConstructorFactory()); 164 constructorFactories.put(URL.class, new UrlConstructorFactory()); 165 constructorFactories.put(TimeZone .class, new TimeZoneConstructorFactory()); 166 constructorFactories.put(Locale .class, new LocaleConstructorFactory()); 167 constructorFactories.put(Class .class, new ClassConstructorFactory()); 168 } 169 170 public static boolean isDefaultCdataConversionType(Class targetClass) 171 { 172 return defaultTargetClasses.contains(targetClass.getName()); 173 } 174 175 186 public static Operation getClassBasedCdataConversionConstructor(Class targetClass, String cdata) throws Exception 187 { 188 if( targetClass == null ){ 189 throw new IllegalArgumentException ("Target class required in CDATA conversions"); 190 } 191 192 ConstructorFactory factory = (ConstructorFactory) constructorFactories.get(targetClass); 193 194 if( factory != null){ 195 return factory.getConstructor(cdata); 196 } 197 else { 198 return new CdataConverterInvocationOperation(targetClass, cdata); 201 } 202 } 203 204 static interface ConstructorFactory { 205 public Operation getConstructor(String stringValue) throws OperationException; 206 } 207 208 static class StringConstructorFactory implements ConstructorFactory { 209 public Operation getConstructor(String stringValue) throws OperationException 210 { 211 return new StaticValue(stringValue); 212 } 213 } 214 215 static class ClassConstructorFactory implements ConstructorFactory { 216 public Operation getConstructor(String stringValue) throws OperationException 217 { 218 try { 219 return new StaticValue(ClassParser.toClass(stringValue)); 220 } catch (ClassNotFoundException e){ 221 throw new OperationException("Failed to load class '" + stringValue + "'"); 222 } 223 } 224 } 225 226 227 static class IntConstructorFactory implements ConstructorFactory { 228 229 public Operation getConstructor(String stringValue) throws OperationException 230 { 231 try { 232 return new StaticValue(Integer.valueOf(stringValue)); 233 } catch (NumberFormatException e){ 234 throw new OperationException("Failed to convert '" + stringValue + "' to int"); 235 } 236 } 237 } 238 239 static class DoubleConstructorFactory implements ConstructorFactory { 240 241 public Operation getConstructor(String stringValue) throws OperationException 242 { 243 try { 244 return new StaticValue(Double.valueOf(stringValue)); 245 } catch (NumberFormatException e){ 246 throw new OperationException("Failed to convert '" + stringValue + "' to double."); 247 } 248 } 249 } 250 251 252 static class BooleanConstructorFactory implements ConstructorFactory { 253 public Operation getConstructor(String stringValue) throws OperationException 254 { 255 try { 256 return new StaticValue(Boolean.valueOf(stringValue)); 257 } catch (NumberFormatException e){ 258 throw new OperationException("Failed to convert '" + stringValue + "' to boolean."); 259 } 260 } 261 } 262 263 static class CharacterConstructorFactory implements ConstructorFactory { 264 public Operation getConstructor(String stringValue) throws OperationException 265 { 266 if( stringValue.length() == 1){ 267 return new StaticValue(new Character (stringValue.charAt(0))); 268 } 269 else { 270 throw new OperationException("Too many characters in '" + stringValue + "'"); 271 } 272 } 273 } 274 275 static class LongConstructorFactory implements ConstructorFactory { 276 public Operation getConstructor(String stringValue) throws OperationException 277 { 278 try { 279 return new StaticValue(Long.valueOf(stringValue)); 280 } catch (NumberFormatException e){ 281 throw new OperationException("Failed to convert '" + stringValue + "' to long."); 282 } 283 } 284 } 285 286 static class ShortConstructorFactory implements ConstructorFactory { 287 public Operation getConstructor(String stringValue) throws OperationException 288 { 289 try { 290 return new StaticValue(Short.valueOf(stringValue)); 291 } catch (NumberFormatException e){ 292 throw new OperationException("Failed to convert '" + stringValue + "' to short."); 293 } 294 } 295 } 296 297 static class FloatConstructorFactory implements ConstructorFactory { 298 299 public Operation getConstructor(String stringValue) throws OperationException 300 { 301 try { 302 return new StaticValue(Float.valueOf(stringValue)); 303 } catch (NumberFormatException e) { 304 throw new OperationException("Failed to convert '" + stringValue + "' to float."); 305 } 306 } 307 } 308 309 static class BigDecimalConstructorFactory implements ConstructorFactory { 310 311 public Operation getConstructor(String stringValue) throws OperationException 312 { 313 try { 314 return new StaticValue(new BigDecimal (stringValue)); 315 } catch (NumberFormatException e) { 316 throw new OperationException("Failed to convert '" + stringValue + "' to BigDecimal",e); 317 } 318 } 319 } 320 321 static class BigIntegerConstructorFactory implements ConstructorFactory { 322 private BigInteger value; 323 public Operation getConstructor(String stringValue) throws OperationException 324 { 325 try { 326 return new StaticValue(new BigInteger (stringValue)); 327 } catch (NumberFormatException e) { 328 throw new OperationException("Failed to convert '" + stringValue + "' to BigInteger",e); 329 } 330 } 331 } 332 333 static class ColorConstructorFactory implements ConstructorFactory { 334 public Operation getConstructor(String stringValue) throws OperationException 335 { 336 try { 337 return new StaticValue(StringConverter.toColor(stringValue)); 338 } catch (IllegalArgumentException e) { 339 throw new OperationException(e.getMessage(), e); 340 } 341 } 342 } 343 344 static class FontConstructorFactory implements ConstructorFactory { 345 public Operation getConstructor(String stringValue) throws OperationException 346 { 347 return new FontConstructor(stringValue); 348 } 349 } 350 351 static class FontConstructor implements Operation { 352 private String stringValue; 353 354 361 public FontConstructor(String stringValue) 362 { 363 this.stringValue = stringValue; 364 } 365 366 public boolean needsParameters() 367 { 368 return false; 369 } 370 public boolean needsParameter(String name) 371 { 372 return false; 373 } 374 public Object execute(Context context) throws OperationException 375 { 376 return java.awt.Font.decode(this.stringValue); 377 } 378 } 379 380 static class UrlConstructorFactory implements ConstructorFactory { 381 public Operation getConstructor(String stringValue) throws OperationException 382 { 383 try { 384 return new StaticValue(new java.net.URL (stringValue)); 385 } catch (MalformedURLException ex) { 386 throw new OperationException(ex.getMessage(), ex); 387 } 388 } 389 } 390 391 static class DimensionConstructorFactory implements ConstructorFactory { 392 public Operation getConstructor(String stringValue) throws OperationException 393 { 394 return new DimensionConstructor(stringValue); 395 } 396 } 397 398 static class DimensionConstructor implements Operation { 399 private String stringValue; 400 406 public DimensionConstructor(String stringValue) 407 { 408 this.stringValue = stringValue; 409 } 410 public boolean needsParameters() 411 { 412 return false; 413 } 414 public boolean needsParameter(String name) 415 { 416 return false; 417 } 418 public Object execute(Context context) throws OperationException 419 { 420 try { 421 return StringConverter.toDimension(this.stringValue); 422 } catch (IllegalArgumentException e){ 423 throw new OperationException(e.getMessage(), e); 424 } 425 } 426 } 427 428 static class PointConstructorFactory implements ConstructorFactory { 429 public Operation getConstructor(String stringValue) throws OperationException 430 { 431 return new PointConstructor(stringValue); 432 } 433 } 434 435 static class PointConstructor implements Operation { 436 private String stringValue; 437 443 public PointConstructor(String stringValue) 444 { 445 this.stringValue = stringValue; 446 } 447 public boolean needsParameters() 448 { 449 return false; 450 } 451 public boolean needsParameter(String name) 452 { 453 return false; 454 } 455 public Object execute(Context context) throws OperationException 456 { 457 try { 458 return StringConverter.toPoint(this.stringValue); 459 } catch (IllegalArgumentException e){ 460 throw new OperationException(e.getMessage(), e); 461 } 462 } 463 } 464 465 static class LocaleConstructorFactory implements ConstructorFactory { 466 public Operation getConstructor(String stringValue) throws OperationException 467 { 468 return new LocaleConstructor(stringValue); 469 } 470 } 471 472 static class LocaleConstructor implements Operation { 473 private String stringValue; 474 public LocaleConstructor(String stringValue) 475 { 476 this.stringValue = stringValue; 477 } 478 public boolean needsParameters() 479 { 480 return false; 481 } 482 public boolean needsParameter(String name) 483 { 484 return false; 485 } 486 public Object execute(Context context) throws OperationException 487 { 488 try { 489 return StringConverter.toLocale(this.stringValue); 490 } catch (IllegalArgumentException e){ 491 throw new OperationException(e.getMessage(), e); 492 } 493 } 494 } 495 496 static class TimeZoneConstructorFactory implements ConstructorFactory { 497 public Operation getConstructor(String stringValue) throws OperationException 498 { 499 return new TimeZoneConstructor(stringValue); 500 } 501 } 502 503 static class TimeZoneConstructor implements Operation { 504 private String stringValue; 505 public TimeZoneConstructor(String stringValue) 506 { 507 this.stringValue = stringValue; 508 } 509 public boolean needsParameters() 510 { 511 return false; 512 } 513 public boolean needsParameter(String name) 514 { 515 return false; 516 } 517 public Object execute(Context context) throws OperationException 518 { 519 return java.util.TimeZone.getTimeZone(this.stringValue); 520 } 521 } 522 523 static class ResourceConstructorFactory implements ConstructorFactory { 524 public Operation getConstructor(String stringValue) throws OperationException 525 { 526 return new ResourceConstructor(stringValue); 527 } 528 } 529 static class ResourceConstructor implements Operation { 530 private String stringValue; 531 public ResourceConstructor(String stringValue) 532 { 533 this.stringValue = stringValue; 534 } 535 public boolean needsParameters() 536 { 537 return false; 538 } 539 540 public boolean needsParameter(String name) 541 { 542 return false; 543 } 544 public Object execute(Context context) throws OperationException 545 { 546 org.jicengine.BuildContext buildContext = (org.jicengine.BuildContext) context.getObject(org.jicengine.BuildContext.VARIABLE_NAME); 547 548 try { 549 return buildContext.getCurrentFile().getResource(this.stringValue); 550 } catch (IOException ex) { 551 throw new OperationException(ex.getMessage(), ex); 552 } 553 } 554 } 555 556 } 557 | Popular Tags |