001 /*
002 * Licensed to the Apache Software Foundation (ASF) under one
003 * or more contributor license agreements. See the NOTICE file
004 * distributed with this work for additional information
005 * regarding copyright ownership. The ASF licenses this file
006 * to you under the Apache License, Version 2.0 (the "License");
007 * you may not use this file except in compliance with the License.
008 * You may obtain a copy of the License at
009 *
010 * http://www.apache.org/licenses/LICENSE-2.0
011 *
012 * Unless required by applicable law or agreed to in writing, software
013 * distributed under the License is distributed on an "AS IS" BASIS,
014 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
015 * See the License for the specific language governing permissions and
016 * limitations under the License.
017 */
018 /*
019 * $Id: ElemChoose.java 468643 2006-10-28 06:56:03Z minchau $
020 */
021 package org.apache.xalan.templates;
022
023 import javax.xml.transform.TransformerException;
024
025 import org.apache.xalan.res.XSLTErrorResources;
026 import org.apache.xalan.transformer.TransformerImpl;
027 import org.apache.xpath.XPathContext;
028 import org.apache.xpath.objects.XObject;
029
030 /**
031 * Implement xsl:choose.
032 * <pre>
033 * <!ELEMENT xsl:choose (xsl:when+, xsl:otherwise?)>
034 * <!ATTLIST xsl:choose %space-att;>
035 * </pre>
036 * @see <a href="http://www.w3.org/TR/xslt#section-Conditional-Processing-with-xsl:choose">XXX in XSLT Specification</a>
037 * @xsl.usage advanced
038 */
039 public class ElemChoose extends ElemTemplateElement
040 {
041 static final long serialVersionUID = -3070117361903102033L;
042
043 /**
044 * Get an int constant identifying the type of element.
045 * @see org.apache.xalan.templates.Constants
046 *
047 * @return The token ID for this element
048 */
049 public int getXSLToken()
050 {
051 return Constants.ELEMNAME_CHOOSE;
052 }
053
054 /**
055 * Return the node name.
056 *
057 * @return The element's name
058 */
059 public String getNodeName()
060 {
061 return Constants.ELEMNAME_CHOOSE_STRING;
062 }
063
064 /**
065 * Constructor ElemChoose
066 *
067 */
068 public ElemChoose(){}
069
070 /**
071 * Execute the xsl:choose transformation.
072 *
073 *
074 * @param transformer non-null reference to the the current transform-time state.
075 *
076 * @throws TransformerException
077 */
078 public void execute(TransformerImpl transformer) throws TransformerException
079 {
080
081 if (transformer.getDebug())
082 transformer.getTraceManager().fireTraceEvent(this);
083
084 boolean found = false;
085
086 for (ElemTemplateElement childElem = getFirstChildElem();
087 childElem != null; childElem = childElem.getNextSiblingElem())
088 {
089 int type = childElem.getXSLToken();
090
091 if (Constants.ELEMNAME_WHEN == type)
092 {
093 found = true;
094
095 ElemWhen when = (ElemWhen) childElem;
096
097 // must be xsl:when
098 XPathContext xctxt = transformer.getXPathContext();
099 int sourceNode = xctxt.getCurrentNode();
100
101 // System.err.println("\""+when.getTest().getPatternString()+"\"");
102
103 // if(when.getTest().getPatternString().equals("COLLECTION/icuser/ictimezone/LITERAL='GMT +13:00 Pacific/Tongatapu'"))
104 // System.err.println("Found COLLECTION/icuser/ictimezone/LITERAL");
105
106 if (transformer.getDebug())
107 {
108 XObject test = when.getTest().execute(xctxt, sourceNode, when);
109
110 if (transformer.getDebug())
111 transformer.getTraceManager().fireSelectedEvent(sourceNode, when,
112 "test", when.getTest(), test);
113
114 if (test.bool())
115 {
116 transformer.getTraceManager().fireTraceEvent(when);
117
118 transformer.executeChildTemplates(when, true);
119
120 transformer.getTraceManager().fireTraceEndEvent(when);
121
122 return;
123 }
124
125 }
126 else if (when.getTest().bool(xctxt, sourceNode, when))
127 {
128 transformer.executeChildTemplates(when, true);
129
130 return;
131 }
132 }
133 else if (Constants.ELEMNAME_OTHERWISE == type)
134 {
135 found = true;
136
137 if (transformer.getDebug())
138 transformer.getTraceManager().fireTraceEvent(childElem);
139
140 // xsl:otherwise
141 transformer.executeChildTemplates(childElem, true);
142
143 if (transformer.getDebug())
144 transformer.getTraceManager().fireTraceEndEvent(childElem);
145 return;
146 }
147 }
148
149 if (!found)
150 transformer.getMsgMgr().error(
151 this, XSLTErrorResources.ER_CHOOSE_REQUIRES_WHEN);
152
153 if (transformer.getDebug())
154 transformer.getTraceManager().fireTraceEndEvent(this);
155 }
156
157 /**
158 * Add a child to the child list.
159 *
160 * @param newChild Child to add to this node's child list
161 *
162 * @return The child that was just added to the child list
163 *
164 * @throws DOMException
165 */
166 public ElemTemplateElement appendChild(ElemTemplateElement newChild)
167 {
168
169 int type = ((ElemTemplateElement) newChild).getXSLToken();
170
171 switch (type)
172 {
173 case Constants.ELEMNAME_WHEN :
174 case Constants.ELEMNAME_OTHERWISE :
175
176 // TODO: Positional checking
177 break;
178 default :
179 error(XSLTErrorResources.ER_CANNOT_ADD,
180 new Object[]{ newChild.getNodeName(),
181 this.getNodeName() }); //"Can not add " +((ElemTemplateElement)newChild).m_elemName +
182
183 //" to " + this.m_elemName);
184 }
185
186 return super.appendChild(newChild);
187 }
188
189 /**
190 * Tell if this element can accept variable declarations.
191 * @return true if the element can accept and process variable declarations.
192 */
193 public boolean canAcceptVariables()
194 {
195 return false;
196 }
197
198 }