View Javadoc

1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one
3    * or more contributor license agreements.  See the NOTICE file
4    * distributed with this work for additional information
5    * regarding copyright ownership.  The ASF licenses this file
6    * to you under the Apache License, Version 2.0 (the
7    * "License"); you may not use this file except in compliance
8    * with the License.  You may obtain a copy of the License at
9    *
10   *   http://www.apache.org/licenses/LICENSE-2.0
11   *
12   * Unless required by applicable law or agreed to in writing,
13   * software distributed under the License is distributed on an
14   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   * KIND, either express or implied.  See the License for the
16   * specific language governing permissions and limitations
17   * under the License.
18   */
19  package javax.faces.component;
20  
21  import java.util.HashMap;
22  import java.util.Iterator;
23  import java.util.List;
24  import java.util.Map;
25  
26  import javax.el.ELException;
27  import javax.el.ValueExpression;
28  import javax.faces.FacesException;
29  import javax.faces.context.FacesContext;
30  import javax.faces.el.ValueBinding;
31  import javax.faces.event.AbortProcessingException;
32  
33  import org.apache.myfaces.buildtools.maven2.plugin.builder.annotation.JSFComponent;
34  
35  /**
36   * see Javadoc of <a href="http://java.sun.com/javaee/javaserverfaces/1.2/docs/api/index.html">JSF Specification</a>
37   *
38   * @author Manfred Geiler (latest modification by $Author: skitching $)
39   * @version $Revision: 676298 $ $Date: 2008-07-13 05:31:48 -0500 (Sun, 13 Jul 2008) $
40   */
41  @JSFComponent(
42          type="javax.faces.Component",
43          family="javax.faces.Component",
44          desc = "abstract base component",
45          configExcluded = true
46          )
47  public abstract class UIComponent
48          implements StateHolder
49  {
50      
51      protected Map<String,ValueExpression> bindings;
52      
53      public UIComponent()
54      {
55      }
56  
57      public abstract java.util.Map<String, Object> getAttributes();
58  
59      /**
60       * @deprecated Replaced by getValueExpression
61       */
62      public abstract javax.faces.el.ValueBinding getValueBinding(java.lang.String name);
63  
64      public ValueExpression getValueExpression(String name)
65      {
66          if (name == null)
67              throw new NullPointerException("name can not be null");
68  
69          if (bindings == null)
70          {
71              if (!(this instanceof UIComponentBase))
72              {
73                  // if the component does not inherit from UIComponentBase and don't implements JSF 1.2 or later
74                  ValueBinding vb = getValueBinding(name);
75                  if (vb != null)
76                  {
77                      bindings = new HashMap<String, ValueExpression>();
78                      ValueExpression ve = new _ValueBindingToValueExpression(vb);
79                      bindings.put(name, ve);
80                      return ve;
81                  }
82              }
83          }
84          else
85          {
86              return bindings.get(name);
87          }
88  
89          return null;
90      }
91      
92      /**
93       * @deprecated Replaced by setValueExpression
94       */
95      public abstract void setValueBinding(java.lang.String name,
96                                           javax.faces.el.ValueBinding binding);
97  
98      public void setValueExpression(String name, ValueExpression expression)
99      {
100         if (name == null)
101             throw new NullPointerException("name");
102         if (name.equals("id"))
103             throw new IllegalArgumentException("Can't set a ValueExpression for the 'id' property.");
104         if (name.equals("parent"))
105             throw new IllegalArgumentException("Can't set a ValueExpression for the 'parent' property.");
106         
107         if (expression == null)
108         {
109             if (bindings != null)
110             {
111                 bindings.remove(name);
112                 if(bindings.isEmpty())
113                     bindings = null;
114             }
115         }
116         else
117         {
118             if (expression.isLiteralText())
119             {
120                 try
121                 {
122                     Object value = expression.getValue(getFacesContext().getELContext());
123                     getAttributes().put(name, value);
124                     return;
125                 }
126                 catch (ELException e)
127                 {
128                     throw new FacesException(e);
129                 }
130             }
131 
132             if (bindings == null)
133             {
134                 bindings = new HashMap<String, ValueExpression>();
135             }
136 
137             bindings.put(name, expression);
138         }
139     }
140     
141     /**
142      * Invokes the <code>invokeContextCallback</code> method with the component, specified by <code>clientId</code>.
143      * @param context <code>FacesContext</code> for the current request
144      * @param clientId the id of the desired <code>UIComponent</code> clazz 
145      * @param callback Implementation of the <code>ContextCallback</code> to be called
146      * @return has component been found ?
147      * @throws javax.faces.FacesException
148      */
149     public boolean invokeOnComponent(javax.faces.context.FacesContext context, String clientId, javax.faces.component.ContextCallback callback) throws javax.faces.FacesException
150     {
151         //java.lang.NullPointerException - if any of the arguments are null
152         if(context == null || clientId == null || callback == null)
153         {
154             throw new NullPointerException();
155         }
156         
157         //searching for this component?
158         boolean found = clientId.equals(this.getClientId(context)); 
159         if(found)
160         {
161             try
162             {
163                 callback.invokeContextCallback(context, this);
164             } catch(Exception e)
165             {
166                 throw new FacesException(e);
167             }
168             return found;
169         }
170         //Searching for this component's children/facets 
171         for (Iterator<UIComponent> it = this.getFacetsAndChildren(); !found && it.hasNext();){
172             found = it.next().invokeOnComponent(context, clientId, callback);
173         }
174             
175         return found;
176     }
177 
178     public abstract java.lang.String getClientId(javax.faces.context.FacesContext context);
179 
180     public abstract java.lang.String getFamily();
181 
182     public abstract java.lang.String getId();
183 
184     public abstract void setId(java.lang.String id);
185 
186     /**
187      * Returns the parent of the component.
188      * Children can be added to or removed from a component even if this method returns null
189      * for the child.
190      */
191     public abstract javax.faces.component.UIComponent getParent();
192 
193     /**
194      * For JSF-framework internal use only.   Don't call this method to
195      * add components to the component tree.
196      * Use <code>parent.getChildren().add(child)</code> instead.
197      */
198     public abstract void setParent(javax.faces.component.UIComponent parent);
199 
200     public abstract boolean isRendered();
201 
202     public abstract void setRendered(boolean rendered);
203 
204     public abstract java.lang.String getRendererType();
205 
206     public abstract void setRendererType(java.lang.String rendererType);
207 
208     public abstract boolean getRendersChildren();
209 
210     public abstract java.util.List<UIComponent> getChildren();
211 
212     public abstract int getChildCount();
213 
214     public abstract javax.faces.component.UIComponent findComponent(java.lang.String expr);
215 
216     public abstract java.util.Map<String, UIComponent> getFacets();
217 
218     public abstract javax.faces.component.UIComponent getFacet(java.lang.String name);
219 
220     public abstract java.util.Iterator<UIComponent> getFacetsAndChildren();
221 
222     public abstract void broadcast(javax.faces.event.FacesEvent event)
223             throws AbortProcessingException;
224 
225     public abstract void decode(javax.faces.context.FacesContext context);
226 
227     public abstract void encodeBegin(javax.faces.context.FacesContext context)
228             throws java.io.IOException;
229 
230     public abstract void encodeChildren(javax.faces.context.FacesContext context)
231             throws java.io.IOException;
232 
233     public abstract void encodeEnd(javax.faces.context.FacesContext context)
234             throws java.io.IOException;
235 
236     public void encodeAll(javax.faces.context.FacesContext context) throws java.io.IOException
237     {
238         if(context == null)
239         {
240             throw new NullPointerException();
241         }
242         
243         if(isRendered())
244         {
245             this.encodeBegin(context);
246             
247             //rendering children
248             if(this.getRendersChildren())
249             {
250                 this.encodeChildren(context);
251             }
252             //let children render itself
253             else
254             {
255           if(this.getChildCount()>0) {
256                   for (UIComponent comp : this.getChildren()) {
257                         comp.encodeAll(context);
258                     }
259           }
260             }
261             this.encodeEnd(context);
262         }
263     }
264 
265 
266 
267     protected abstract void addFacesListener(javax.faces.event.FacesListener listener);
268 
269     protected abstract javax.faces.event.FacesListener[] getFacesListeners(java.lang.Class clazz);
270 
271     protected abstract void removeFacesListener(javax.faces.event.FacesListener listener);
272 
273     public abstract void queueEvent(javax.faces.event.FacesEvent event);
274 
275     public abstract void processRestoreState(javax.faces.context.FacesContext context,
276                                              java.lang.Object state);
277 
278     public abstract void processDecodes(javax.faces.context.FacesContext context);
279 
280     public abstract void processValidators(javax.faces.context.FacesContext context);
281 
282     public abstract void processUpdates(javax.faces.context.FacesContext context);
283 
284     public abstract java.lang.Object processSaveState(javax.faces.context.FacesContext context);
285 
286     protected abstract javax.faces.context.FacesContext getFacesContext();
287 
288     protected abstract javax.faces.render.Renderer getRenderer(javax.faces.context.FacesContext context);
289 
290     /**
291      * @since 1.2
292      */
293     
294     public int getFacetCount()
295     {
296         // not sure why the RI has this method in both 
297         // UIComponent and UIComponentBase
298         Map<String, UIComponent> facets = getFacets();
299         return facets == null ? 0 : facets.size();
300     }
301     
302     /**
303      * @since 1.2
304      */
305     
306     public String getContainerClientId(FacesContext ctx)
307     {
308         if( ctx == null )
309             throw new NullPointerException("FacesContext ctx");
310         
311         return getClientId(ctx);
312     }
313 }