KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > apache > myfaces > renderkit > html > util > JavascriptUtils


1 /*
2  * Copyright 2004 The Apache Software Foundation.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */

16 package org.apache.myfaces.renderkit.html.util;
17
18 import org.apache.myfaces.config.MyfacesConfig;
19 import org.apache.myfaces.renderkit.html.HTML;
20
21 import org.apache.commons.logging.Log;
22 import org.apache.commons.logging.LogFactory;
23
24 import javax.faces.context.ExternalContext;
25 import javax.faces.context.FacesContext;
26 import javax.faces.context.ResponseWriter;
27 import java.io.IOException JavaDoc;
28 import java.io.UnsupportedEncodingException JavaDoc;
29 import java.util.Arrays JavaDoc;
30 import java.util.HashSet JavaDoc;
31 import java.util.Set JavaDoc;
32
33 /**
34  * @author Manfred Geiler (latest modification by $Author: mmarinschek $)
35  * @author Anton Koinov
36  * @version $Revision: 1.12 $ $Date: 2004/12/27 04:11:11 $
37  * $Log: JavascriptUtils.java,v $
38  * Revision 1.12 2004/12/27 04:11:11 mmarinschek
39  * Data Table stores the state of facets of children; script tag is rendered with type attribute instead of language attribute, popup works better as a column in a data table
40  *
41  * Revision 1.11 2004/12/23 09:15:15 mmarinschek
42  * changes to utils to handle ie better
43  *
44  * Revision 1.10 2004/12/02 21:31:56 svieujot
45  * Bugfix in encodeString
46  *
47  * Revision 1.9 2004/10/13 11:51:01 matze
48  * renamed packages to org.apache
49  *
50  * Revision 1.8 2004/09/10 14:13:52 manolito
51  * trivial change
52  *
53  * Revision 1.7 2004/09/08 15:51:15 manolito
54  * Autoscroll now also for horizontal scrolling
55  *
56  * Revision 1.6 2004/09/08 15:23:11 manolito
57  * Autoscroll feature
58  *
59  * Revision 1.5 2004/09/08 09:31:25 manolito
60  * moved isJavascriptDetected from MyFacesConfig to JavascriptUtils class
61  *
62  * Revision 1.4 2004/07/16 13:06:30 manolito
63  * encode javascript strings for jscook menu labels
64  *
65  * Revision 1.3 2004/07/09 02:44:55 dave0000
66  * More efficient implementation
67  *
68  * Revision 1.2 2004/07/01 22:00:53 mwessendorf
69  * ASF switch
70  *
71  * Revision 1.1 2004/04/29 14:25:22 manolito
72  * javascript function name bugfix
73  *
74  */

75 public final class JavascriptUtils
76 {
77     private static final Log log = LogFactory.getLog(JavascriptUtils.class);
78
79     public static final String JavaDoc JAVASCRIPT_DETECTED = JavascriptUtils.class.getName() + ".JAVASCRIPT_DETECTED";
80
81     private static final String JavaDoc AUTO_SCROLL_PARAM = "autoScroll";
82     private static final String JavaDoc AUTO_SCROLL_FUNCTION = "getScrolling()";
83
84     private static final String JavaDoc OLD_VIEW_ID = JavascriptUtils.class + ".OLD_VIEW_ID";
85
86
87     private JavascriptUtils()
88     {
89         // utility class, do not instantiate
90
}
91     
92     private static final Set JavaDoc RESERVED_WORDS =
93         new HashSet JavaDoc(Arrays.asList(new String JavaDoc[]{
94             "abstract",
95             "boolean",
96             "break",
97             "byte",
98             "case",
99             "catch",
100             "char",
101             "class",
102             "const",
103             "continue",
104             "default",
105             "delete",
106             "do",
107             "double",
108             "else",
109             "export",
110             "extends",
111             "false",
112             "final",
113             "finally",
114             "float",
115             "for",
116             "function",
117             "goto",
118             "if",
119             "implements",
120             "in",
121             "instanceof",
122             "int",
123             "long",
124             "native",
125             "new",
126             "null",
127             "package",
128             "private",
129             "protected",
130             "public",
131             "return",
132             "short",
133             "static",
134             "super",
135             "switch",
136             "synchronized",
137             "this",
138             "throw",
139             "throws",
140             "transient",
141             "true",
142             "try",
143             "typeof",
144             "var",
145             "void",
146             "while",
147             "with"
148         }));
149     
150     public static String JavaDoc getValidJavascriptName(String JavaDoc s, boolean checkForReservedWord)
151     {
152         if (checkForReservedWord && RESERVED_WORDS.contains(s))
153         {
154             return s + "_";
155         }
156         
157         StringBuffer JavaDoc buf = null;
158         for (int i = 0, len = s.length(); i < len; i++)
159         {
160             char c = s.charAt(i);
161             
162             if (Character.isLetterOrDigit(c))
163             {
164                 // allowed char
165
if (buf != null) buf.append(c);
166             }
167             else
168             {
169                 if (buf == null)
170                 {
171                     buf = new StringBuffer JavaDoc(s.length() + 10);
172                     buf.append(s.substring(0, i));
173                 }
174                 
175                 buf.append('_');
176                 if (c < 16)
177                 {
178                     // pad single hex digit values with '0' on the left
179
buf.append('0');
180                 }
181                 
182                 if (c < 128)
183                 {
184                     // first 128 chars match their byte representation in UTF-8
185
buf.append(Integer.toHexString(c).toUpperCase());
186                 }
187                 else
188                 {
189                     byte[] bytes;
190                     try
191                     {
192                         bytes = Character.toString(c).getBytes("UTF-8");
193                     }
194                     catch (UnsupportedEncodingException JavaDoc e)
195                     {
196                         throw new RuntimeException JavaDoc(e);
197                     }
198                     
199                     for (int j = 0; j < bytes.length; j++)
200                     {
201                         int intVal = bytes[j];
202                         if (intVal < 0)
203                         {
204                             // intVal will be >= 128
205
intVal = 256 + intVal;
206                         }
207                         else if (intVal < 16)
208                         {
209                             // pad single hex digit values with '0' on the left
210
buf.append('0');
211                         }
212                         buf.append(Integer.toHexString(intVal).toUpperCase());
213                     }
214                 }
215             }
216             
217         }
218         
219         return buf == null ? s : buf.toString();
220     }
221
222
223     public static String JavaDoc encodeString(String JavaDoc string)
224     {
225         if (string == null)
226         {
227             return "";
228         }
229         StringBuffer JavaDoc sb = null; //create later on demand
230
String JavaDoc app;
231         char c;
232         for (int i = 0; i < string.length (); ++i)
233         {
234             app = null;
235             c = string.charAt(i);
236             switch (c)
237             {
238                 case '\\' : app = "\\"; break;
239                 case '"' : app = "\\\""; break;
240                 case '\'' : app = "\\'"; break;
241                 case '\n' : app = "\\n"; break;
242                 case '\r' : app = "\\r"; break;
243             }
244             if (app != null)
245             {
246                 if (sb == null)
247                 {
248                     sb = new StringBuffer JavaDoc(string.substring(0, i));
249                 }
250                 sb.append(app);
251             } else {
252                 if (sb != null)
253                 {
254                     sb.append(c);
255                 }
256             }
257         }
258
259         if (sb == null)
260         {
261             return string;
262         }
263         else
264         {
265             return sb.toString();
266         }
267     }
268
269
270     public static boolean isJavascriptAllowed(ExternalContext externalContext)
271     {
272         MyfacesConfig myfacesConfig = MyfacesConfig.getCurrentInstance(externalContext);
273         if (myfacesConfig.isAllowJavascript())
274         {
275             if (myfacesConfig.isDetectJavascript())
276             {
277                 return isJavascriptDetected(externalContext);
278             }
279             else
280             {
281                 return true;
282             }
283         }
284         else
285         {
286             return false;
287         }
288     }
289
290
291     public static void setJavascriptDetected(ExternalContext externalContext, boolean value)
292     {
293         externalContext.getSessionMap().put(JAVASCRIPT_DETECTED, Boolean.valueOf(value));
294     }
295
296     public static boolean isJavascriptDetected(ExternalContext externalContext)
297     {
298         //TODO/FIXME (manolito): This info should be better stored in the viewroot component and not in the session
299
Boolean JavaDoc sessionValue = (Boolean JavaDoc)externalContext.getSessionMap().get(JAVASCRIPT_DETECTED);
300         return sessionValue == null ? false : sessionValue.booleanValue();
301     }
302
303
304     /**
305      * Adds the hidden form input value assignment that is necessary for the autoscroll
306      * feature to an html link or button onclick attribute.
307      */

308     public static void appendAutoScrollAssignment(StringBuffer JavaDoc onClickValue, String JavaDoc formName)
309     {
310         onClickValue.append("document.forms['").append(formName).append("']");
311         onClickValue.append(".elements['").append(AUTO_SCROLL_PARAM).append("']");
312         onClickValue.append(".value=").append(AUTO_SCROLL_FUNCTION).append(";");
313     }
314
315     /**
316      * Renders the hidden form input that is necessary for the autoscroll feature.
317      */

318     public static void renderAutoScrollHiddenInput(ResponseWriter writer) throws IOException JavaDoc
319     {
320         writer.startElement(HTML.INPUT_ELEM, null);
321         writer.writeAttribute(HTML.TYPE_ATTR, "hidden", null);
322         writer.writeAttribute(HTML.NAME_ATTR, AUTO_SCROLL_PARAM, null);
323         writer.endElement(HTML.INPUT_ELEM);
324     }
325
326     /**
327      * Renders the autoscroll javascript function.
328      */

329     public static void renderAutoScrollFunction(FacesContext facesContext,
330                                                 ResponseWriter writer) throws IOException JavaDoc
331     {
332         writer.write("\n<script type=\"text/javascript\">\n" +
333                      "<!--\n" +
334                      "function " + AUTO_SCROLL_FUNCTION + " {\n" +
335                      " var x = 0; var y = 0;\n" +
336                      " if (document.body && document.body.scrollLeft && !isNaN(document.body.scrollLeft)) {\n" +
337                      " x = document.body.scrollLeft;\n" +
338                      " } else if (window.pageXOffset && !isNaN(window.pageXOffset)) {\n" +
339                      " x = window.pageXOffset;\n" +
340                      " }\n" +
341                      " if (document.body && document.body.scrollTop && !isNaN(document.body.scrollTop)) {\n" +
342                      " y = document.body.scrollTop;\n" +
343                      " } else if (window.pageYOffset && !isNaN(window.pageYOffset)) {\n" +
344                      " y = window.pageYOffset;\n" +
345                      " }\n" +
346                      " return x + \",\" + y;\n" +
347                      "}\n");
348         ExternalContext externalContext = facesContext.getExternalContext();
349         String JavaDoc oldViewId = getOldViewId(externalContext);
350         if (oldViewId != null && oldViewId.equals(facesContext.getViewRoot().getViewId()))
351         {
352             //ok, we stayed on the same page, so let's scroll it to the former place
353
String JavaDoc scrolling = (String JavaDoc)externalContext.getRequestParameterMap().get(AUTO_SCROLL_PARAM);
354             if (scrolling != null && scrolling.length() > 0)
355             {
356                 String JavaDoc x = "0";
357                 String JavaDoc y = "0";
358                 int comma = scrolling.indexOf(',');
359                 if (comma == -1)
360                 {
361                     log.warn("Illegal autoscroll request parameter: " + scrolling);
362                 }
363                 else
364                 {
365                     x = scrolling.substring(0, comma);
366                     if (x.equals("undefined")) x = "0";
367                     y = scrolling.substring(comma + 1);
368                     if (y.equals("undefined")) y = "0";
369                 }
370                 writer.write("window.scrollTo(" + x + "," + y + ");\n");
371             }
372         }
373         writer.write("//-->\n" +
374                      "</script>\n");
375     }
376
377
378     public static void setOldViewId(ExternalContext externalContext, String JavaDoc viewId)
379     {
380         externalContext.getRequestMap().put(OLD_VIEW_ID, viewId);
381     }
382
383     public static String JavaDoc getOldViewId(ExternalContext externalContext)
384     {
385         return (String JavaDoc)externalContext.getRequestMap().get(OLD_VIEW_ID);
386     }
387 }
388
Popular Tags