1 package org.apache.velocity.app.tools; 2 3 /* 4 * Licensed to the Apache Software Foundation (ASF) under one 5 * or more contributor license agreements. See the NOTICE file 6 * distributed with this work for additional information 7 * regarding copyright ownership. The ASF licenses this file 8 * to you under the Apache License, Version 2.0 (the 9 * "License"); you may not use this file except in compliance 10 * with the License. You may obtain a copy of the License at 11 * 12 * http://www.apache.org/licenses/LICENSE-2.0 13 * 14 * Unless required by applicable law or agreed to in writing, 15 * software distributed under the License is distributed on an 16 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 17 * KIND, either express or implied. See the License for the 18 * specific language governing permissions and limitations 19 * under the License. 20 */ 21 22 import java.lang.reflect.Array; 23 import java.text.DateFormat; 24 import java.util.Date; 25 import java.util.List; 26 27 import org.apache.velocity.context.Context; 28 29 /** 30 * Formatting tool for inserting into the Velocity WebContext. Can 31 * format dates or lists of objects. 32 * 33 * <p>Here's an example of some uses: 34 * 35 * <code><pre> 36 * $formatter.formatShortDate($object.Date) 37 * $formatter.formatLongDate($db.getRecord(232).getDate()) 38 * $formatter.formatArray($array) 39 * $formatter.limitLen(30, $object.Description) 40 * </pre></code> 41 * 42 * @deprecated This class has been replaced by NumberTool, DateTool, 43 * DisplayTool, and AlternatorTool available from the Velocity-Tools sub-project. 44 * VelocityFormatter will be removed in a future version of Velocity. 45 * 46 * @author <a href="sean@somacity.com">Sean Legassick</a> 47 * @author <a href="dlr@collab.net">Daniel Rall</a> 48 * @version $Id: VelocityFormatter.java 544641 2007-06-05 21:30:22Z nbubna $ 49 */ 50 public class VelocityFormatter 51 { 52 Context context = null; 53 54 /** 55 * Constructor needs a backpointer to the context. 56 * 57 * @param context A Context. 58 */ 59 public VelocityFormatter(Context context) 60 { 61 this.context = context; 62 } 63 64 /** 65 * Formats a date in <code>DateFormat.SHORT</code> style. 66 * 67 * @param date The date to format. 68 * @return The formatted date as text. 69 */ 70 public String formatShortDate(Date date) 71 { 72 return DateFormat.getDateInstance(DateFormat.SHORT).format(date); 73 } 74 75 /** 76 * Formats a date in <code>DateFormat.LONG</code> style. 77 * 78 * @param date The date to format. 79 * @return The formatted date as text. 80 */ 81 public String formatLongDate(Date date) 82 { 83 return DateFormat.getDateInstance(DateFormat.LONG).format(date); 84 } 85 86 /** 87 * Formats a date/time in 'short' style. 88 * 89 * @param date The date to format. 90 * @return The formatted date as text. 91 */ 92 public String formatShortDateTime(Date date) 93 { 94 return DateFormat 95 .getDateTimeInstance(DateFormat.SHORT, 96 DateFormat.SHORT).format(date); 97 } 98 99 /** 100 * Formats a date/time in 'long' style. 101 * 102 * @param date The date to format. 103 * @return The formatted date as text. 104 */ 105 public String formatLongDateTime(Date date) 106 { 107 return DateFormat.getDateTimeInstance( 108 DateFormat.LONG, DateFormat.LONG).format(date); 109 } 110 111 /** 112 * Formats an array into the form "A, B and C". 113 * 114 * @param array An Object. 115 * @return A String. 116 */ 117 public String formatArray(Object array) 118 { 119 return formatArray(array, ", ", " and "); 120 } 121 122 /** 123 * Formats an array into the form 124 * "A<delim>B<delim>C". 125 * 126 * @param array An Object. 127 * @param delim A String. 128 * @return A String. 129 */ 130 public String formatArray(Object array, 131 String delim) 132 { 133 return formatArray(array, delim, delim); 134 } 135 136 /** 137 * Formats an array into the form 138 * "A<delim>B<finaldelim>C". 139 * 140 * @param array An Object. 141 * @param delim A String. 142 * @param finaldelim A String. 143 * @return A String. 144 */ 145 public String formatArray(Object array, 146 String delim, 147 String finaldelim) 148 { 149 StringBuffer sb = new StringBuffer(); 150 int arrayLen = Array.getLength(array); 151 for (int i = 0; i < arrayLen; i++) 152 { 153 // Use the Array.get method as this will automatically 154 // wrap primitive types in a suitable Object-derived 155 // wrapper if necessary. 156 sb.append(Array.get(array, i).toString()); 157 if (i < arrayLen - 2) 158 { 159 sb.append(delim); 160 } 161 else if (i < arrayLen - 1) 162 { 163 sb.append(finaldelim); 164 } 165 } 166 return sb.toString(); 167 } 168 169 /** 170 * Formats a vector into the form "A, B and C". 171 * 172 * @param list The list of elements to format. 173 * @return A String. 174 */ 175 public String formatVector(List list) 176 { 177 return formatVector(list, ", ", " and "); 178 } 179 180 /** 181 * Formats a vector into the form "A<delim>B<delim>C". 182 * 183 * @param list The list of elements to format. 184 * @param delim A String. 185 * @return A String. 186 */ 187 public String formatVector(List list, 188 String delim) 189 { 190 return formatVector(list, delim, delim); 191 } 192 193 /** 194 * Formats a list into the form 195 * "Adelim>B<finaldelim>C". 196 * 197 * @param list The list of elements to format. 198 * @param delim A String. 199 * @param finaldelim A String. 200 * @return A String. 201 */ 202 public String formatVector(List list, 203 String delim, 204 String finaldelim) 205 { 206 StringBuffer sb = new StringBuffer(); 207 int size = list.size(); 208 for (int i = 0; i < size; i++) 209 { 210 sb.append(list.get(i)); 211 if (i < size - 2) 212 { 213 sb.append(delim); 214 } 215 else if (i < size - 1) 216 { 217 sb.append(finaldelim); 218 } 219 } 220 return sb.toString(); 221 } 222 223 /** 224 * Limits 'string' to 'maxlen' characters. If the string gets 225 * curtailed, "..." is appended to it. 226 * 227 * @param maxlen An int with the maximum length. 228 * @param string A String. 229 * @return A String. 230 */ 231 public String limitLen(int maxlen, 232 String string) 233 { 234 return limitLen(maxlen, string, "..."); 235 } 236 237 /** 238 * Limits 'string' to 'maxlen' character. If the string gets 239 * curtailed, 'suffix' is appended to it. 240 * 241 * @param maxlen An int with the maximum length. 242 * @param string A String. 243 * @param suffix A String. 244 * @return A String. 245 */ 246 public String limitLen(int maxlen, 247 String string, 248 String suffix) 249 { 250 String ret = string; 251 if (string.length() > maxlen) 252 { 253 ret = string.substring(0, maxlen - suffix.length()) + suffix; 254 } 255 return ret; 256 } 257 258 /** 259 * Class that returns alternating values in a template. It stores 260 * a list of alternate Strings, whenever alternate() is called it 261 * switches to the next in the list. The current alternate is 262 * retrieved through toString() - i.e. just by referencing the 263 * object in a Velocity template. For an example of usage see the 264 * makeAlternator() method below. 265 */ 266 public class VelocityAlternator 267 { 268 /** 269 * 270 */ 271 protected String[] alternates = null; 272 /** 273 * 274 */ 275 protected int current = 0; 276 277 /** 278 * Constructor takes an array of Strings. 279 * 280 * @param alternates A String[]. 281 */ 282 public VelocityAlternator(String[] alternates) 283 { 284 this.alternates = alternates; 285 } 286 287 /** 288 * Alternates to the next in the list. 289 * 290 * @return The current alternate in the sequence. 291 */ 292 public String alternate() 293 { 294 current++; 295 current %= alternates.length; 296 return ""; 297 } 298 299 /** 300 * Returns the current alternate. 301 * 302 * @return A String. 303 */ 304 public String toString() 305 { 306 return alternates[current]; 307 } 308 } 309 310 /** 311 * As VelocityAlternator, but calls <code>alternate()</code> 312 * automatically on rendering in a template. 313 */ 314 public class VelocityAutoAlternator extends VelocityAlternator 315 { 316 /** 317 * Constructor takes an array of Strings. 318 * 319 * @param alternates A String[]. 320 */ 321 public VelocityAutoAlternator(String[] alternates) 322 { 323 super(alternates); 324 } 325 326 /** 327 * Returns the current alternate, and automatically alternates 328 * to the next alternate in its sequence (trigged upon 329 * rendering). 330 * 331 * @return The current alternate in the sequence. 332 */ 333 public final String toString() 334 { 335 String s = alternates[current]; 336 alternate(); 337 return s; 338 } 339 } 340 341 /** 342 * Makes an alternator object that alternates between two values. 343 * 344 * <p>Example usage in a Velocity template: 345 * 346 * <code><pre> 347 * <table> 348 * $formatter.makeAlternator("rowcolor", "#c0c0c0", "#e0e0e0") 349 * #foreach $item in $items 350 * #begin 351 * <tr><td bgcolor="$rowcolor">$item.Name</td></tr> 352 * $rowcolor.alternate() 353 * #end 354 * </table> 355 * </pre></code> 356 * 357 * @param name The name for the alternator int the context. 358 * @param alt1 The first alternate. 359 * @param alt2 The second alternate. 360 * @return The newly created instance. 361 */ 362 public String makeAlternator(String name, 363 String alt1, 364 String alt2) 365 { 366 String[] alternates = { alt1, alt2 }; 367 context.put(name, new VelocityAlternator(alternates)); 368 return ""; 369 } 370 371 /** 372 * Makes an alternator object that alternates between three 373 * values. 374 * @param name 375 * @param alt1 376 * @param alt2 377 * @param alt3 378 * @return alternated object. 379 * 380 * @see #makeAlternator(String name, String alt1, String alt2) 381 */ 382 public String makeAlternator(String name, 383 String alt1, 384 String alt2, 385 String alt3) 386 { 387 String[] alternates = { alt1, alt2, alt3 }; 388 context.put(name, new VelocityAlternator(alternates)); 389 return ""; 390 } 391 392 /** 393 * Makes an alternator object that alternates between four values. 394 * @param name 395 * @param alt1 396 * @param alt2 397 * @param alt3 398 * @param alt4 399 * @return Alternated object. 400 * 401 * @see #makeAlternator(String name, String alt1, String alt2) 402 */ 403 public String makeAlternator(String name, String alt1, String alt2, 404 String alt3, String alt4) 405 { 406 String[] alternates = { alt1, alt2, alt3, alt4 }; 407 context.put(name, new VelocityAlternator(alternates)); 408 return ""; 409 } 410 411 /** 412 * Makes an alternator object that alternates between two values 413 * automatically. 414 * @param name 415 * @param alt1 416 * @param alt2 417 * @return Alternated object. 418 * 419 * @see #makeAlternator(String name, String alt1, String alt2) 420 */ 421 public String makeAutoAlternator(String name, String alt1, String alt2) 422 { 423 String[] alternates = { alt1, alt2 }; 424 context.put(name, new VelocityAutoAlternator(alternates)); 425 return ""; 426 } 427 428 /** 429 * Returns a default value if the object passed is null. 430 * @param o 431 * @param dflt 432 * @return Object or default value when object is null. 433 */ 434 public Object isNull(Object o, Object dflt) 435 { 436 if ( o == null ) 437 { 438 return dflt; 439 } 440 else 441 { 442 return o; 443 } 444 } 445 }