001/* AnimTimeParser.java */ 002/* Generated By:JavaCC: Do not edit this line. AnimTimeParser.java */ 003package com.kitfox.svg.animation.parser; 004 005import com.kitfox.svg.SVGConst; 006import com.kitfox.svg.animation.TimeBase; 007import com.kitfox.svg.animation.TimeCompound; 008import com.kitfox.svg.animation.TimeDiscrete; 009import com.kitfox.svg.animation.TimeIndefinite; 010import com.kitfox.svg.animation.TimeLookup; 011import com.kitfox.svg.animation.TimeSum; 012import java.io.StringReader; 013import java.util.ArrayList; 014import java.util.logging.Level; 015import java.util.logging.Logger; 016 017public class AnimTimeParser implements AnimTimeParserConstants { 018 /** 019 * Test the parser 020 */ 021 public static void main(String args[]) throws ParseException 022 { 023// AnimTimeParser parser = new AnimTimeParser(System.in); 024 StringReader reader; 025 026 reader = new StringReader("1:30 + 5ms"); 027 AnimTimeParser parser = new AnimTimeParser(reader); 028 TimeBase tc; 029 030 tc = parser.Expr(); 031 System.err.println("AnimTimeParser eval to " + tc.evalTime()); 032 033 reader = new StringReader("19"); 034 parser.ReInit(reader); 035 tc = parser.Expr(); 036 System.err.println("AnimTimeParser eval to " + tc.evalTime()); 037 } 038 039/** 040 * Expression structure 041 */ 042 final public 043 044TimeBase Expr() throws ParseException {TimeBase term; 045 ArrayList list = new ArrayList(); 046 switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) { 047 case INTEGER: 048 case FLOAT: 049 case INDEFINITE: 050 case MOUSE_OVER: 051 case WHEN_NOT_ACTIVE: 052 case IDENTIFIER:{ 053 term = Sum(); 054list.add(term); 055 break; 056 } 057 default: 058 jj_la1[0] = jj_gen; 059 ; 060 } 061 label_1: 062 while (true) { 063 if (jj_2_1(2)) { 064 ; 065 } else { 066 break label_1; 067 } 068 jj_consume_token(15); 069 term = Sum(); 070list.add(term); 071 } 072 switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) { 073 case 15:{ 074 jj_consume_token(15); 075 break; 076 } 077 default: 078 jj_la1[1] = jj_gen; 079 ; 080 } 081switch (list.size()) 082 { 083 case 0: 084 {if ("" != null) return new TimeIndefinite();} 085 case 1: 086 {if ("" != null) return (TimeBase)list.get(0);} 087 default: 088 {if ("" != null) return new TimeCompound(list);} 089 } 090 throw new Error("Missing return statement in function"); 091} 092 093 final public TimeBase Sum() throws ParseException {Token t = null; 094 TimeBase t1; 095 TimeBase t2 = null; 096 t1 = Term(); 097 switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) { 098 case 16: 099 case 17:{ 100 switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) { 101 case 16:{ 102 t = jj_consume_token(16); 103 break; 104 } 105 case 17:{ 106 t = jj_consume_token(17); 107 break; 108 } 109 default: 110 jj_la1[2] = jj_gen; 111 jj_consume_token(-1); 112 throw new ParseException(); 113 } 114 t2 = Term(); 115 break; 116 } 117 default: 118 jj_la1[3] = jj_gen; 119 ; 120 } 121if (t2 == null) {if ("" != null) return t1;} 122 123 if (t.image.equals("-")) 124 { 125 {if ("" != null) return new TimeSum(t1, t2, false);} 126 } 127 else 128 { 129 {if ("" != null) return new TimeSum(t1, t2, true);} 130 } 131 throw new Error("Missing return statement in function"); 132} 133 134 final public TimeBase Term() throws ParseException {TimeBase base; 135 switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) { 136 case INDEFINITE:{ 137 base = IndefiniteTime(); 138{if ("" != null) return base;} 139 break; 140 } 141 case INTEGER: 142 case FLOAT:{ 143 base = LiteralTime(); 144{if ("" != null) return base;} 145 break; 146 } 147 case IDENTIFIER:{ 148 base = LookupTime(); 149{if ("" != null) return base;} 150 break; 151 } 152 case MOUSE_OVER: 153 case WHEN_NOT_ACTIVE:{ 154 base = EventTime(); 155{if ("" != null) return base;} 156 break; 157 } 158 default: 159 jj_la1[4] = jj_gen; 160 jj_consume_token(-1); 161 throw new ParseException(); 162 } 163 throw new Error("Missing return statement in function"); 164} 165 166 final public TimeIndefinite IndefiniteTime() throws ParseException { 167 jj_consume_token(INDEFINITE); 168{if ("" != null) return new TimeIndefinite();} 169 throw new Error("Missing return statement in function"); 170} 171 172 final public TimeDiscrete EventTime() throws ParseException { 173 switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) { 174 case MOUSE_OVER:{ 175 jj_consume_token(MOUSE_OVER); 176 break; 177 } 178 case WHEN_NOT_ACTIVE:{ 179 jj_consume_token(WHEN_NOT_ACTIVE); 180 break; 181 } 182 default: 183 jj_la1[5] = jj_gen; 184 jj_consume_token(-1); 185 throw new ParseException(); 186 } 187//For now, map all events to the zero time 188 {if ("" != null) return new TimeDiscrete(0);} 189 throw new Error("Missing return statement in function"); 190} 191 192 final public TimeDiscrete LiteralTime() throws ParseException {double t1, t2, t3 = Double.NaN, value; 193 Token t; 194 t1 = Number(); 195value = t1; 196 switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) { 197 case UNITS: 198 case 18:{ 199 switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) { 200 case 18:{ 201 jj_consume_token(18); 202 t2 = Number(); 203 switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) { 204 case 18:{ 205 jj_consume_token(18); 206 t3 = Number(); 207 break; 208 } 209 default: 210 jj_la1[6] = jj_gen; 211 ; 212 } 213//Return clock time format (convert to seconds) 214 if (Double.isNaN(t3)) 215 { 216 value = t1 * 60 + t2; 217 } 218 else 219 { 220 value = t1 * 3600 + t2 * 60 + t3; 221 } 222 break; 223 } 224 case UNITS:{ 225 t = jj_consume_token(UNITS); 226//Return units format (convert to seconds) 227 if (t.image.equals("ms")) value = t1 / 1000; 228 if (t.image.equals("min")) value = t1 * 60; 229 if (t.image.equals("h")) value = t1 * 3600; 230 break; 231 } 232 default: 233 jj_la1[7] = jj_gen; 234 jj_consume_token(-1); 235 throw new ParseException(); 236 } 237 break; 238 } 239 default: 240 jj_la1[8] = jj_gen; 241 ; 242 } 243{if ("" != null) return new TimeDiscrete(value);} 244 throw new Error("Missing return statement in function"); 245} 246 247 final public TimeLookup LookupTime() throws ParseException {double paramNum = 0.0; 248 Token node, event; 249 node = jj_consume_token(IDENTIFIER); 250 jj_consume_token(19); 251 event = jj_consume_token(IDENTIFIER); 252 switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) { 253 case 20:{ 254 paramNum = ParamList(); 255 break; 256 } 257 default: 258 jj_la1[9] = jj_gen; 259 ; 260 } 261{if ("" != null) return new TimeLookup(null, node.image, event.image, "" + paramNum);} 262 throw new Error("Missing return statement in function"); 263} 264 265 final public double ParamList() throws ParseException {double num; 266 jj_consume_token(20); 267 num = Number(); 268 jj_consume_token(21); 269{if ("" != null) return num;} 270 throw new Error("Missing return statement in function"); 271} 272 273 final public double Number() throws ParseException {Token t; 274 switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) { 275 case FLOAT:{ 276 t = jj_consume_token(FLOAT); 277try { 278 {if ("" != null) return Double.parseDouble(t.image);} 279 } 280 catch (Exception e) { 281 Logger.getLogger(SVGConst.SVG_LOGGER).log(Level.WARNING, 282 "Could not parse double '" + t.image + "'", e); 283 } 284 285 {if ("" != null) return 0.0;} 286 break; 287 } 288 case INTEGER:{ 289 t = jj_consume_token(INTEGER); 290try { 291 {if ("" != null) return Double.parseDouble(t.image);} 292 } 293 catch (Exception e) { 294 Logger.getLogger(SVGConst.SVG_LOGGER).log(Level.WARNING, 295 "Could not parse double '" + t.image + "'", e); 296 } 297 298 {if ("" != null) return 0.0;} 299 break; 300 } 301 default: 302 jj_la1[10] = jj_gen; 303 jj_consume_token(-1); 304 throw new ParseException(); 305 } 306 throw new Error("Missing return statement in function"); 307} 308 309 final public int Integer() throws ParseException {Token t; 310 t = jj_consume_token(INTEGER); 311try { 312 {if ("" != null) return Integer.parseInt(t.image);} 313 } 314 catch (Exception e) { 315 Logger.getLogger(SVGConst.SVG_LOGGER).log(Level.WARNING, 316 "Could not parse int '" + t.image + "'", e); 317 } 318 319 {if ("" != null) return 0;} 320 throw new Error("Missing return statement in function"); 321} 322 323 private boolean jj_2_1(int xla) 324 { 325 jj_la = xla; jj_lastpos = jj_scanpos = token; 326 try { return (!jj_3_1()); } 327 catch(LookaheadSuccess ls) { return true; } 328 finally { jj_save(0, xla); } 329 } 330 331 private boolean jj_3R_10() 332 { 333 if (jj_scan_token(IDENTIFIER)) return true; 334 return false; 335 } 336 337 private boolean jj_3R_13() 338 { 339 if (jj_scan_token(FLOAT)) return true; 340 return false; 341 } 342 343 private boolean jj_3R_12() 344 { 345 Token xsp; 346 xsp = jj_scanpos; 347 if (jj_3R_13()) { 348 jj_scanpos = xsp; 349 if (jj_3R_14()) return true; 350 } 351 return false; 352 } 353 354 private boolean jj_3R_7() 355 { 356 if (jj_3R_11()) return true; 357 return false; 358 } 359 360 private boolean jj_3R_6() 361 { 362 if (jj_3R_10()) return true; 363 return false; 364 } 365 366 private boolean jj_3R_5() 367 { 368 if (jj_3R_9()) return true; 369 return false; 370 } 371 372 private boolean jj_3R_2() 373 { 374 if (jj_3R_3()) return true; 375 return false; 376 } 377 378 private boolean jj_3_1() 379 { 380 if (jj_scan_token(15)) return true; 381 if (jj_3R_2()) return true; 382 return false; 383 } 384 385 private boolean jj_3R_3() 386 { 387 Token xsp; 388 xsp = jj_scanpos; 389 if (jj_3R_4()) { 390 jj_scanpos = xsp; 391 if (jj_3R_5()) { 392 jj_scanpos = xsp; 393 if (jj_3R_6()) { 394 jj_scanpos = xsp; 395 if (jj_3R_7()) return true; 396 } 397 } 398 } 399 return false; 400 } 401 402 private boolean jj_3R_4() 403 { 404 if (jj_3R_8()) return true; 405 return false; 406 } 407 408 private boolean jj_3R_14() 409 { 410 if (jj_scan_token(INTEGER)) return true; 411 return false; 412 } 413 414 private boolean jj_3R_11() 415 { 416 Token xsp; 417 xsp = jj_scanpos; 418 if (jj_scan_token(11)) { 419 jj_scanpos = xsp; 420 if (jj_scan_token(12)) return true; 421 } 422 return false; 423 } 424 425 private boolean jj_3R_8() 426 { 427 if (jj_scan_token(INDEFINITE)) return true; 428 return false; 429 } 430 431 private boolean jj_3R_9() 432 { 433 if (jj_3R_12()) return true; 434 return false; 435 } 436 437 /** Generated Token Manager. */ 438 public AnimTimeParserTokenManager token_source; 439 SimpleCharStream jj_input_stream; 440 /** Current token. */ 441 public Token token; 442 /** Next token. */ 443 public Token jj_nt; 444 private int jj_ntk; 445 private Token jj_scanpos, jj_lastpos; 446 private int jj_la; 447 private int jj_gen; 448 final private int[] jj_la1 = new int[11]; 449 static private int[] jj_la1_0; 450 static { 451 jj_la1_init_0(); 452 } 453 private static void jj_la1_init_0() { 454 jj_la1_0 = new int[] {0x5f00,0x8000,0x30000,0x30000,0x5f00,0x1800,0x40000,0x42000,0x42000,0x100000,0x300,}; 455 } 456 final private JJCalls[] jj_2_rtns = new JJCalls[1]; 457 private boolean jj_rescan = false; 458 private int jj_gc = 0; 459 460 /** Constructor with InputStream. */ 461 public AnimTimeParser(java.io.InputStream stream) { 462 this(stream, null); 463 } 464 /** Constructor with InputStream and supplied encoding */ 465 public AnimTimeParser(java.io.InputStream stream, String encoding) { 466 try { jj_input_stream = new SimpleCharStream(stream, encoding, 1, 1); } catch(java.io.UnsupportedEncodingException e) { throw new RuntimeException(e); } 467 token_source = new AnimTimeParserTokenManager(jj_input_stream); 468 token = new Token(); 469 jj_ntk = -1; 470 jj_gen = 0; 471 for (int i = 0; i < 11; i++) jj_la1[i] = -1; 472 for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls(); 473 } 474 475 /** Reinitialise. */ 476 public void ReInit(java.io.InputStream stream) { 477 ReInit(stream, null); 478 } 479 /** Reinitialise. */ 480 public void ReInit(java.io.InputStream stream, String encoding) { 481 try { jj_input_stream.ReInit(stream, encoding, 1, 1); } catch(java.io.UnsupportedEncodingException e) { throw new RuntimeException(e); } 482 token_source.ReInit(jj_input_stream); 483 token = new Token(); 484 jj_ntk = -1; 485 jj_gen = 0; 486 for (int i = 0; i < 11; i++) jj_la1[i] = -1; 487 for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls(); 488 } 489 490 /** Constructor. */ 491 public AnimTimeParser(java.io.Reader stream) { 492 jj_input_stream = new SimpleCharStream(stream, 1, 1); 493 token_source = new AnimTimeParserTokenManager(jj_input_stream); 494 token = new Token(); 495 jj_ntk = -1; 496 jj_gen = 0; 497 for (int i = 0; i < 11; i++) jj_la1[i] = -1; 498 for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls(); 499 } 500 501 /** Reinitialise. */ 502 public void ReInit(java.io.Reader stream) { 503 if (jj_input_stream == null) { 504 jj_input_stream = new SimpleCharStream(stream, 1, 1); 505 } else { 506 jj_input_stream.ReInit(stream, 1, 1); 507 } 508 if (token_source == null) { 509 token_source = new AnimTimeParserTokenManager(jj_input_stream); 510 } 511 512 token_source.ReInit(jj_input_stream); 513 token = new Token(); 514 jj_ntk = -1; 515 jj_gen = 0; 516 for (int i = 0; i < 11; i++) jj_la1[i] = -1; 517 for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls(); 518 } 519 520 /** Constructor with generated Token Manager. */ 521 public AnimTimeParser(AnimTimeParserTokenManager tm) { 522 token_source = tm; 523 token = new Token(); 524 jj_ntk = -1; 525 jj_gen = 0; 526 for (int i = 0; i < 11; i++) jj_la1[i] = -1; 527 for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls(); 528 } 529 530 /** Reinitialise. */ 531 public void ReInit(AnimTimeParserTokenManager tm) { 532 token_source = tm; 533 token = new Token(); 534 jj_ntk = -1; 535 jj_gen = 0; 536 for (int i = 0; i < 11; i++) jj_la1[i] = -1; 537 for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls(); 538 } 539 540 private Token jj_consume_token(int kind) throws ParseException { 541 Token oldToken; 542 if ((oldToken = token).next != null) token = token.next; 543 else token = token.next = token_source.getNextToken(); 544 jj_ntk = -1; 545 if (token.kind == kind) { 546 jj_gen++; 547 if (++jj_gc > 100) { 548 jj_gc = 0; 549 for (int i = 0; i < jj_2_rtns.length; i++) { 550 JJCalls c = jj_2_rtns[i]; 551 while (c != null) { 552 if (c.gen < jj_gen) c.first = null; 553 c = c.next; 554 } 555 } 556 } 557 return token; 558 } 559 token = oldToken; 560 jj_kind = kind; 561 throw generateParseException(); 562 } 563 564 @SuppressWarnings("serial") 565 static private final class LookaheadSuccess extends java.lang.Error { } 566 final private LookaheadSuccess jj_ls = new LookaheadSuccess(); 567 private boolean jj_scan_token(int kind) { 568 if (jj_scanpos == jj_lastpos) { 569 jj_la--; 570 if (jj_scanpos.next == null) { 571 jj_lastpos = jj_scanpos = jj_scanpos.next = token_source.getNextToken(); 572 } else { 573 jj_lastpos = jj_scanpos = jj_scanpos.next; 574 } 575 } else { 576 jj_scanpos = jj_scanpos.next; 577 } 578 if (jj_rescan) { 579 int i = 0; Token tok = token; 580 while (tok != null && tok != jj_scanpos) { i++; tok = tok.next; } 581 if (tok != null) jj_add_error_token(kind, i); 582 } 583 if (jj_scanpos.kind != kind) return true; 584 if (jj_la == 0 && jj_scanpos == jj_lastpos) throw jj_ls; 585 return false; 586 } 587 588 589/** Get the next Token. */ 590 final public Token getNextToken() { 591 if (token.next != null) token = token.next; 592 else token = token.next = token_source.getNextToken(); 593 jj_ntk = -1; 594 jj_gen++; 595 return token; 596 } 597 598/** Get the specific Token. */ 599 final public Token getToken(int index) { 600 Token t = token; 601 for (int i = 0; i < index; i++) { 602 if (t.next != null) t = t.next; 603 else t = t.next = token_source.getNextToken(); 604 } 605 return t; 606 } 607 608 private int jj_ntk_f() { 609 if ((jj_nt=token.next) == null) 610 return (jj_ntk = (token.next=token_source.getNextToken()).kind); 611 else 612 return (jj_ntk = jj_nt.kind); 613 } 614 615 private java.util.List<int[]> jj_expentries = new java.util.ArrayList<int[]>(); 616 private int[] jj_expentry; 617 private int jj_kind = -1; 618 private int[] jj_lasttokens = new int[100]; 619 private int jj_endpos; 620 621 private void jj_add_error_token(int kind, int pos) { 622 if (pos >= 100) { 623 return; 624 } 625 626 if (pos == jj_endpos + 1) { 627 jj_lasttokens[jj_endpos++] = kind; 628 } else if (jj_endpos != 0) { 629 jj_expentry = new int[jj_endpos]; 630 631 for (int i = 0; i < jj_endpos; i++) { 632 jj_expentry[i] = jj_lasttokens[i]; 633 } 634 635 for (int[] oldentry : jj_expentries) { 636 if (oldentry.length == jj_expentry.length) { 637 boolean isMatched = true; 638 639 for (int i = 0; i < jj_expentry.length; i++) { 640 if (oldentry[i] != jj_expentry[i]) { 641 isMatched = false; 642 break; 643 } 644 645 } 646 if (isMatched) { 647 jj_expentries.add(jj_expentry); 648 break; 649 } 650 } 651 } 652 653 if (pos != 0) { 654 jj_lasttokens[(jj_endpos = pos) - 1] = kind; 655 } 656 } 657 } 658 659 /** Generate ParseException. */ 660 public ParseException generateParseException() { 661 jj_expentries.clear(); 662 boolean[] la1tokens = new boolean[22]; 663 if (jj_kind >= 0) { 664 la1tokens[jj_kind] = true; 665 jj_kind = -1; 666 } 667 for (int i = 0; i < 11; i++) { 668 if (jj_la1[i] == jj_gen) { 669 for (int j = 0; j < 32; j++) { 670 if ((jj_la1_0[i] & (1<<j)) != 0) { 671 la1tokens[j] = true; 672 } 673 } 674 } 675 } 676 for (int i = 0; i < 22; i++) { 677 if (la1tokens[i]) { 678 jj_expentry = new int[1]; 679 jj_expentry[0] = i; 680 jj_expentries.add(jj_expentry); 681 } 682 } 683 jj_endpos = 0; 684 jj_rescan_token(); 685 jj_add_error_token(0, 0); 686 int[][] exptokseq = new int[jj_expentries.size()][]; 687 for (int i = 0; i < jj_expentries.size(); i++) { 688 exptokseq[i] = jj_expentries.get(i); 689 } 690 return new ParseException(token, exptokseq, tokenImage); 691 } 692 693 private int trace_indent = 0; 694 private boolean trace_enabled; 695 696/** Trace enabled. */ 697 final public boolean trace_enabled() { 698 return trace_enabled; 699 } 700 701 /** Enable tracing. */ 702 final public void enable_tracing() { 703 } 704 705 /** Disable tracing. */ 706 final public void disable_tracing() { 707 } 708 709 private void jj_rescan_token() { 710 jj_rescan = true; 711 for (int i = 0; i < 1; i++) { 712 try { 713 JJCalls p = jj_2_rtns[i]; 714 715 do { 716 if (p.gen > jj_gen) { 717 jj_la = p.arg; jj_lastpos = jj_scanpos = p.first; 718 switch (i) { 719 case 0: jj_3_1(); break; 720 } 721 } 722 p = p.next; 723 } while (p != null); 724 725 } catch(LookaheadSuccess ls) { } 726 } 727 jj_rescan = false; 728 } 729 730 private void jj_save(int index, int xla) { 731 JJCalls p = jj_2_rtns[index]; 732 while (p.gen > jj_gen) { 733 if (p.next == null) { p = p.next = new JJCalls(); break; } 734 p = p.next; 735 } 736 737 p.gen = jj_gen + xla - jj_la; 738 p.first = token; 739 p.arg = xla; 740 } 741 742 static final class JJCalls { 743 int gen; 744 Token first; 745 int arg; 746 JJCalls next; 747 } 748 749}