001: /*
002: * Copyright 2004 The Apache Software Foundation.
003: *
004: * Licensed under the Apache License, Version 2.0 (the "License");
005: * you may not use this file except in compliance with the License.
006: * You may obtain a copy of the License at
007: *
008: * http://www.apache.org/licenses/LICENSE-2.0
009: *
010: * Unless required by applicable law or agreed to in writing, software
011: * distributed under the License is distributed on an "AS IS" BASIS,
012: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013: * See the License for the specific language governing permissions and
014: * limitations under the License.
015: */
016: package org.apache.myfaces.shared_impl.renderkit.html;
017:
018: import org.apache.myfaces.shared_impl.renderkit.JSFAttr;
019:
020: import javax.faces.application.ViewHandler;
021: import javax.faces.component.UIComponent;
022: import javax.faces.component.UIViewRoot;
023: import javax.faces.context.FacesContext;
024: import javax.faces.render.Renderer;
025: import java.io.IOException;
026: import java.util.List;
027:
028: /**
029: * @author Manfred Geiler (latest modification by $Author: baranda $)
030: * @version $Revision: 544646 $ $Date: 2007-06-05 23:51:27 +0200 (Di, 05 Jun 2007) $
031: */
032: public abstract class HtmlRenderer extends Renderer {
033:
034: /**
035: * Return the list of children of the specified component.
036: * <p>
037: * This default implementation simply returns component.getChildren().
038: * However this method should always be used in order to allow
039: * renderer subclasses to override it and provide filtered or
040: * reordered views of the component children to rendering
041: * methods defined in their ancestor classes.
042: * <p>
043: * Any method that overrides this to "hide" child components
044: * should also override the getChildCount method.
045: *
046: * @return a list of UIComponent objects.
047: */
048: public List getChildren(UIComponent component) {
049: return component.getChildren();
050: }
051:
052: /**
053: * Return the number of children of the specified component.
054: * <p>
055: * See {@link #getChildren(UIComponent)} for more information.
056: */
057: public int getChildCount(UIComponent component) {
058: return component.getChildCount();
059: }
060:
061: /**
062: * @param facesContext
063: * @return String A String representing the action URL
064: */
065: protected String getActionUrl(FacesContext facesContext) {
066: ViewHandler viewHandler = facesContext.getApplication()
067: .getViewHandler();
068: String viewId = facesContext.getViewRoot().getViewId();
069: return viewHandler.getActionURL(facesContext, viewId);
070: }
071:
072: /**
073: * Renders the client ID as an "id".
074: */
075: protected void renderId(FacesContext context, UIComponent component)
076: throws IOException {
077: if (shouldRenderId(context, component)) {
078: String clientId = getClientId(context, component);
079: context.getResponseWriter().writeAttribute(HTML.ID_ATTR,
080: clientId, JSFAttr.ID_ATTR);
081: }
082: }
083:
084: /**
085: * Returns the client ID that should be used for rendering (if
086: * {@link #shouldRenderId} returns true).
087: */
088: protected String getClientId(FacesContext context,
089: UIComponent component) {
090: return component.getClientId(context);
091: }
092:
093: /**
094: * Returns true if the component should render an ID. Components
095: * that deliver events should always return "true".
096: * @todo Is this a bottleneck? If so, optimize!
097: */
098: protected boolean shouldRenderId(FacesContext context,
099: UIComponent component) {
100: String id = component.getId();
101:
102: // Otherwise, if ID isn't set, don't bother
103: if (id == null)
104: return false;
105:
106: // ... or if the ID was generated, don't bother
107: if (id.startsWith(UIViewRoot.UNIQUE_ID_PREFIX))
108: return false;
109:
110: return true;
111: }
112:
113: /**
114: * Coerces an object into a URI, accounting for JSF rules
115: * with initial slashes.
116: */
117: static public String toUri(Object o) {
118: if (o == null)
119: return null;
120:
121: String uri = o.toString();
122: if (uri.startsWith("/")) {
123: // Treat two slashes as server-relative
124: if (uri.startsWith("//")) {
125: uri = uri.substring(1);
126: } else {
127: FacesContext fContext = FacesContext
128: .getCurrentInstance();
129: uri = fContext.getExternalContext()
130: .getRequestContextPath()
131: + uri;
132: }
133: }
134:
135: return uri;
136: }
137: }
|