001 package com.thaiopensource.relaxng.impl; 002 003 import com.thaiopensource.xml.util.Name; 004 005 class StartTagOpenDerivFunction extends AbstractPatternFunction { 006 private final Name name; 007 private final ValidatorPatternBuilder builder; 008 009 StartTagOpenDerivFunction(Name name, ValidatorPatternBuilder builder) { 010 this.name = name; 011 this.builder = builder; 012 } 013 014 public Object caseChoice(ChoicePattern p) { 015 return builder.makeChoice(memoApply(p.getOperand1()), 016 memoApply(p.getOperand2())); 017 } 018 019 public Object caseGroup(GroupPattern p) { 020 final Pattern p1 = p.getOperand1(); 021 final Pattern p2 = p.getOperand2(); 022 Pattern tem = memoApply(p1).applyForPattern( 023 new ApplyAfterFunction(builder) { 024 Pattern apply(Pattern x) { 025 return builder.makeGroup(x, p2); 026 } 027 }); 028 return p1.isNullable() ? builder.makeChoice(tem, memoApply(p2)) : tem; 029 } 030 031 public Object caseInterleave(InterleavePattern p) { 032 final Pattern p1 = p.getOperand1(); 033 final Pattern p2 = p.getOperand2(); 034 return builder.makeChoice( 035 memoApply(p1).applyForPattern(new ApplyAfterFunction(builder) { 036 Pattern apply(Pattern x) { 037 return builder.makeInterleave(x, p2); 038 } 039 }), 040 memoApply(p2).applyForPattern(new ApplyAfterFunction(builder) { 041 Pattern apply(Pattern x) { 042 return builder.makeInterleave(p1, x); 043 } 044 })); 045 } 046 047 public Object caseAfter(AfterPattern p) { 048 final Pattern p1 = p.getOperand1(); 049 final Pattern p2 = p.getOperand2(); 050 return memoApply(p1).applyForPattern( 051 new ApplyAfterFunction(builder) { 052 Pattern apply(Pattern x) { 053 return builder.makeAfter(x, p2); 054 } 055 }); 056 } 057 058 public Object caseOneOrMore(final OneOrMorePattern p) { 059 final Pattern p1 = p.getOperand(); 060 return memoApply(p1).applyForPattern( 061 new ApplyAfterFunction(builder) { 062 Pattern apply(Pattern x) { 063 return builder.makeGroup(x, 064 builder.makeOptional(p)); 065 } 066 }); 067 } 068 069 070 public Object caseElement(ElementPattern p) { 071 if (!p.getNameClass().contains(name)) 072 return builder.makeNotAllowed(); 073 return builder.makeAfter(p.getContent(), builder.makeEmpty()); 074 } 075 076 public Object caseOther(Pattern p) { 077 return builder.makeNotAllowed(); 078 } 079 080 final Pattern memoApply(Pattern p) { 081 return apply(builder.getPatternMemo(p)).getPattern(); 082 } 083 084 PatternMemo apply(PatternMemo memo) { 085 return memo.startTagOpenDeriv(this); 086 } 087 088 Name getName() { 089 return name; 090 } 091 092 ValidatorPatternBuilder getPatternBuilder() { 093 return builder; 094 } 095 }