1 package org.apache.turbine.util; 2 3 4 /* 5 * Licensed to the Apache Software Foundation (ASF) under one 6 * or more contributor license agreements. See the NOTICE file 7 * distributed with this work for additional information 8 * regarding copyright ownership. The ASF licenses this file 9 * to you under the Apache License, Version 2.0 (the 10 * "License"); you may not use this file except in compliance 11 * with the License. You may obtain a copy of the License at 12 * 13 * http://www.apache.org/licenses/LICENSE-2.0 14 * 15 * Unless required by applicable law or agreed to in writing, 16 * software distributed under the License is distributed on an 17 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 18 * KIND, either express or implied. See the License for the 19 * specific language governing permissions and limitations 20 * under the License. 21 */ 22 23 24 import java.text.DateFormatSymbols; 25 import java.util.Calendar; 26 27 import org.apache.ecs.ConcreteElement; 28 import org.apache.ecs.ElementContainer; 29 import org.apache.ecs.html.Input; 30 import org.apache.ecs.html.Option; 31 import org.apache.ecs.html.Select; 32 33 /** 34 * DateSelector is a utility class to handle the creation of a set of 35 * date popup menus. The code is broken into a set of static methods 36 * for quick and easy access to the individual select objects: 37 * 38 * <pre> 39 * ElementContainer ec dateSelect = new ElementContainer(); 40 * String myName = "mydate"; 41 * ec.addElement(DateSelector.getMonthSelector(myName)); 42 * ec.addElement(DateSelector.getDaySelector(myName)); 43 * ec.addElement(DateSelector.getYearSelector(myName)); 44 * </pre> 45 * 46 * There are also methods which will use attributes to build a 47 * complete month,day,year selector: 48 * 49 * <pre> 50 * DateSelector ds = new DateSelector(myName); 51 * dateSelect = ds.ecsOutput(); 52 * </pre> 53 * 54 * The above element container would use the onChange setting and may 55 * hide the selected day if set via showDays().<br> 56 * 57 * @author <a href="mailto:ekkerbj@netscape.net">Jeffrey D. Brekke</a> 58 * @author <a href="mailto:jon@clearink.com">Jon S. Stevens</a> 59 * @author <a href="mailto:leon@clearink.com">Leon Atkinson</a> 60 * @version $Id: DateSelector.java 1706239 2015-10-01 13:18:35Z tv $ 61 */ 62 public class DateSelector 63 { 64 /** Prefix for date names. */ 65 public static final String DEFAULT_PREFIX = "DateSelector"; 66 67 /** Suffix for day parameter. */ 68 public static final String DAY_SUFFIX = "_day"; 69 70 /** Suffix for month parameter. */ 71 public static final String MONTH_SUFFIX = "_month"; 72 73 /** Suffix for year parameter. */ 74 public static final String YEAR_SUFFIX = "_year"; 75 76 private Calendar useDate = null; 77 private String selName = null; 78 private static final String[] monthName = 79 new DateFormatSymbols().getMonths(); 80 private String onChange = null; 81 private boolean onChangeSet = false; 82 private boolean showDays = true; 83 private int setDay = 0; 84 private boolean useYears = false; 85 private int firstYear = 0; 86 private int lastYear = 0; 87 private int selectedYear = 0; 88 89 /** 90 * Constructor defaults to current date and uses the default 91 * prefix: <pre>DateSelector.DEFAULT</pre> 92 */ 93 public DateSelector() 94 { 95 this(DEFAULT_PREFIX); 96 } 97 98 /** 99 * Constructor defaults to current date. 100 * 101 * @param selName A String with the selector name. 102 */ 103 public DateSelector(String selName) 104 { 105 this(selName, Calendar.getInstance()); 106 } 107 108 /** 109 * Constructor, uses the date set in a calendar that has been 110 * already passed in (with the date set correctly). 111 * 112 * @param selName A String with the selector name. 113 * @param useDate A Calendar with a date. 114 */ 115 public DateSelector(String selName, Calendar useDate) 116 { 117 this.useDate = useDate; 118 this.selName = selName; 119 } 120 121 /** 122 * Adds the onChange to all of <SELECT> tags. This is limited to 123 * one function for all three popups and is only used when the 124 * output() methods are used. Individual getMonth, getDay, 125 * getYear static methods will not use this setting. 126 * 127 * @param onChange A String to use for onChange attribute. If null, 128 * then nothing will be set. 129 * @return A DateSelector (self). 130 */ 131 public DateSelector setOnChange(String onChange) 132 { 133 if (onChange != null) 134 { 135 this.onChange = onChange; 136 this.onChangeSet = true; 137 } 138 else 139 { 140 this.onChange = null; 141 this.onChangeSet = false; 142 } 143 return this; 144 } 145 146 /** 147 * Select the day to be selected if the showDays(false) behavior 148 * is used. Individual getMonth, getDay, getYear static methods 149 * will not use this setting. 150 * 151 * @param day The day. 152 * @return A DateSelector (self). 153 */ 154 public DateSelector setDay(int day) 155 { 156 this.setDay = day; 157 this.showDays = false; 158 return this; 159 } 160 161 /** 162 * Whether or not to show the days as a popup menu. The days will 163 * be a hidden parameter and the value set with setDay is used. 164 * Individual getMonth, getDay, getYear static methods will not 165 * use this setting. 166 * 167 * @param show True if the day should be shown. 168 * @return A DateSelector (self). 169 */ 170 public DateSelector setShowDay(boolean show) 171 { 172 this.showDays = false; 173 return this; 174 } 175 176 /** 177 * Set the selector name prefix. Individual getMonth, getDay, 178 * getYear static methods will not use this setting. 179 * 180 * @param selName A String with the select name prefix. 181 */ 182 public void setSelName(String selName) 183 { 184 this.selName = selName; 185 } 186 187 /** 188 * Get the selector name prefix. 189 * 190 * @return A String with the select name prefix. 191 */ 192 public String getSelName() 193 { 194 return selName; 195 } 196 197 /** 198 * Return a month selector. 199 * 200 * @param name The name to use for the selected month. 201 * @return A select object with all the months. 202 */ 203 public static Select getMonthSelector(String name) 204 { 205 return (getMonthSelector(name, Calendar.getInstance())); 206 } 207 208 /** 209 * Return a month selector. 210 * 211 * Note: The values of the month placed into the select list are 212 * the month integers starting at 0 (ie: if the user selects 213 * February, the selected value will be 1). 214 * 215 * @param name The name to use for the selected month. 216 * @param now Calendar to start with. 217 * @return A select object with all the months. 218 */ 219 public static Select getMonthSelector(String name, Calendar now) 220 { 221 Select monthSelect = new Select().setName(name); 222 223 for (int curMonth = 0; curMonth <= 11; curMonth++) 224 { 225 Option o = new Option(); 226 o.addElement(monthName[curMonth]); 227 o.setValue(curMonth); 228 if ((now.get(Calendar.MONTH)) == curMonth) 229 { 230 o.setSelected(true); 231 } 232 monthSelect.addElement(o); 233 } 234 return (monthSelect); 235 } 236 237 /** 238 * Return a day selector. 239 * 240 * @param name The name to use for the selected day. 241 * @return A select object with all the days in a month. 242 */ 243 public static Select getDaySelector(String name) 244 { 245 return (getDaySelector(name, Calendar.getInstance())); 246 } 247 248 /** 249 * Return a day selector. 250 * 251 * @param name The name to use for the selected day. 252 * @param now Calendar to start with. 253 * @return A select object with all the days in a month. 254 */ 255 public static Select getDaySelector(String name, Calendar now) 256 { 257 Select daySelect = new Select().setName(name); 258 259 for (int currentDay = 1; currentDay <= 31; currentDay++) 260 { 261 Option o = new Option(); 262 o.addElement(Integer.toString(currentDay)); 263 o.setValue(currentDay); 264 if (now.get(Calendar.DAY_OF_MONTH) == currentDay) 265 { 266 o.setSelected(true); 267 } 268 daySelect.addElement(o); 269 } 270 return (daySelect); 271 } 272 273 /** 274 * Return a year selector. 275 * 276 * @param name The name to use for the selected year. 277 * @return A select object with all the years starting five years 278 * from now and five years before this year. 279 */ 280 public static Select getYearSelector(String name) 281 { 282 return (getYearSelector(name, Calendar.getInstance())); 283 } 284 285 /** 286 * Return a year selector. 287 * 288 * @param name The name to use for the selected year. 289 * @param now Calendar to start with. 290 * @return A select object with all the years starting five years 291 * from now and five years before this year. 292 */ 293 public static Select getYearSelector(String name, Calendar now) 294 { 295 int startYear = now.get(Calendar.YEAR); 296 return (getYearSelector(name, startYear - 5, startYear + 5, startYear)); 297 } 298 299 /** 300 * Return a year selector. 301 * 302 * @param name The name to use for the selected year. 303 * @param firstYear the first (earliest) year in the selector. 304 * @param lastYear the last (latest) year in the selector. 305 * @param selectedYear the year initially selected in the Select html. 306 * @return A select object with all the years from firstyear 307 * to lastyear.. 308 */ 309 public static Select getYearSelector(String name, 310 int firstYear, int lastYear, 311 int selectedYear) 312 { 313 Select yearSelect = new Select().setName(name); 314 315 for (int currentYear = firstYear; 316 currentYear <= lastYear; 317 318 currentYear++) 319 { 320 Option o = new Option(); 321 o.addElement(Integer.toString(currentYear)); 322 o.setValue(currentYear); 323 if (currentYear == selectedYear) 324 { 325 o.setSelected(true); 326 } 327 yearSelect.addElement(o); 328 } 329 return (yearSelect); 330 } 331 332 /** 333 * Set a year range to be displayed 334 * @param firstYear start of year range 335 * @param lastYear end of year range 336 * @param selectedYear entry to select 337 * @return true if the range settings are valid 338 */ 339 public boolean setYear(int firstYear, int lastYear, int selectedYear) 340 { 341 if (firstYear <= lastYear && firstYear <= selectedYear 342 && selectedYear <= lastYear) 343 { 344 this.useYears = true; 345 this.firstYear = firstYear; 346 this.lastYear = lastYear; 347 this.selectedYear = selectedYear; 348 return true; 349 } 350 else 351 { 352 return false; 353 } 354 } 355 356 /** 357 * Used to build the popupmenu in HTML. The properties set in the 358 * object are used to generate the correct HTML. The selName 359 * attribute is used to seed the names of the select lists. The 360 * names will be generated as follows: 361 * 362 * <ul> 363 * <li>selName + "_month"</li> 364 * <li>selName + "_day"</li> 365 * <li>selName + "_year"</li> 366 * </ul> 367 * 368 * If onChange was set it is also used in the generation of the 369 * output. The output HTML will list the select lists in the 370 * following order: month day year. 371 * 372 * @return A String with the correct HTML for the date selector. 373 */ 374 public String output() 375 { 376 return (ecsOutput().toString()); 377 } 378 379 /** 380 * Used to build the popupmenu in HTML. The properties set in the 381 * object are used to generate the correct HTML. The selName 382 * attribute is used to seed the names of the select lists. The 383 * names will be generated as follows: 384 * 385 * <ul> 386 * <li>selName + "_month"</li> 387 * <li>selName + "_day"</li> 388 * <li>selName + "_year"</li> 389 * </ul> 390 * 391 * The output HTML will list the select lists in the following 392 * order: month day year. 393 * 394 * @return A String with the correct HTML for the date selector. 395 */ 396 @Override 397 public String toString() 398 { 399 return (ecsOutput().toString()); 400 } 401 402 /** 403 * Return an ECS container with the month, day, and year select 404 * objects inside. 405 * 406 * @return An ECS container. 407 */ 408 public ElementContainer ecsOutput() 409 { 410 if (this.useDate == null) 411 { 412 this.useDate = Calendar.getInstance(); 413 } 414 415 Select monthSelect = getMonthSelector(selName + MONTH_SUFFIX, useDate); 416 ConcreteElement daySelect = null; 417 if (!showDays) 418 { 419 daySelect = new Input(Input.hidden, selName + DAY_SUFFIX, setDay); 420 } 421 else 422 { 423 Select tmp = getDaySelector(selName + DAY_SUFFIX, useDate); 424 if (onChangeSet) 425 { 426 tmp.setOnChange(onChange); 427 } 428 daySelect = tmp; 429 } 430 Select yearSelect = null; 431 if (useYears) 432 { 433 yearSelect = getYearSelector(selName + YEAR_SUFFIX, 434 firstYear, lastYear, selectedYear); 435 } 436 else 437 { 438 yearSelect = getYearSelector(selName + YEAR_SUFFIX, useDate); 439 } 440 if (onChangeSet) 441 { 442 monthSelect.setOnChange(onChange); 443 yearSelect.setOnChange(onChange); 444 } 445 ElementContainer ec = new ElementContainer(); 446 // ec.addElement(new Comment("== BEGIN org.apache.turbine.util.DateSelector.ecsOutput() ==")); 447 ec.addElement(monthSelect); 448 ec.addElement(daySelect); 449 ec.addElement(yearSelect); 450 // ec.addElement(new Comment("== END org.apache.turbine.util.DateSelector.ecsOutput() ==")); 451 return (ec); 452 } 453 }