001: package org.araneaframework.jsp.tag.uilib.form.element.date;
002:
003: import java.io.IOException;
004: import java.io.Writer;
005: import java.text.ParseException;
006: import java.util.Calendar;
007: import javax.servlet.jsp.JspException;
008: import org.apache.commons.lang.StringUtils;
009: import org.araneaframework.http.util.FileImportUtil;
010: import org.araneaframework.http.util.ServletUtil;
011: import org.araneaframework.jsp.AraneaAttributes;
012: import org.araneaframework.jsp.UiUpdateEvent;
013: import org.araneaframework.jsp.util.JspUtil;
014: import org.araneaframework.jsp.util.JspWidgetCallUtil;
015: import org.araneaframework.uilib.event.OnChangeEventListener;
016: import org.araneaframework.uilib.form.control.DateControl;
017: import org.araneaframework.uilib.form.control.DateTimeControl;
018: import org.araneaframework.uilib.form.control.TimestampControl.ViewModel;
019:
020: /**
021: * Date/time input form element tag.
022: *
023: * @author Marko Muts
024: * @jsp.tag
025: * name = "dateTimeInput"
026: * body-content = "JSP"
027: * description = "Form date and time input field (custom control), represents UiLib "DateTimeControl"."
028: */
029: public class FormDateTimeInputHtmlTag extends
030: BaseFormDateTimeInputHtmlTag {
031: protected String timeStyleClass;
032: protected String dateStyleClass;
033:
034: protected boolean showTimeSelect = true;
035:
036: public FormDateTimeInputHtmlTag() {
037: timeStyleClass = "aranea-time";
038: dateStyleClass = "aranea-date";
039: }
040:
041: public String getDateStyleClass() {
042: return dateStyleClass;
043: }
044:
045: protected int doEndTag(Writer out) throws Exception {
046: assertControlType("DateTimeControl");
047:
048: // Prepare
049: String name = this .getFullFieldId();
050: DateTimeControl.ViewModel viewModel = ((DateTimeControl.ViewModel) controlViewModel);
051:
052: Long timeInputSize = DEFAULT_TIME_INPUT_SIZE;
053: Long dateInputSize = DEFAULT_DATE_INPUT_SIZE;
054:
055: // Write
056: out
057: .write("<table border='0' cellpadding='0' cellspacing='0'><tr><td nowrap='true'>\n");
058:
059: this .writeDateInput(out, name, name + ".date", viewModel
060: .getDate(), localizedLabel, viewModel.isMandatory(),
061: formElementViewModel.isValid(), dateInputSize,
062: viewModel.isDisabled(), getDateStyleClass(), accessKey,
063: viewModel.getDateViewModel());
064:
065: out.write(" ");
066: writeTimeInput(out, name, viewModel.getTime(), localizedLabel,
067: timeInputSize, viewModel.isDisabled());
068:
069: Integer minute = null, hour = null;
070: try {
071: ViewModel timeViewModel = viewModel.getTimeViewModel();
072: if (timeViewModel.getSimpleValue() != null) {
073: Calendar calendar = Calendar.getInstance();
074: calendar.setTime(timeViewModel
075: .getCurrentSimpleDateTimeFormat().parse(
076: timeViewModel.getSimpleValue()));
077:
078: hour = new Integer(calendar.get(Calendar.HOUR_OF_DAY));
079: minute = new Integer(calendar.get(Calendar.MINUTE));
080: }
081: } catch (ParseException e) {
082: // try to preserve the contents of selects anyway
083: if (showTimeSelect) {
084: String strHour = ServletUtil.getRequest(
085: getOutputData().getInputData()).getParameter(
086: name + ".select1");
087: if (strHour != null && !(strHour.trim().length() == 0))
088: hour = Integer.valueOf(strHour.trim());
089: String strMinute = ServletUtil.getRequest(
090: getOutputData().getInputData()).getParameter(
091: name + ".select2");
092: if (strMinute != null
093: && !(strMinute.trim().length() == 0))
094: minute = Integer.valueOf(strMinute);
095: }
096: }
097:
098: if (showTimeSelect) {
099: writeHourSelect(out, name, viewModel.isDisabled(), hour);
100: writeMinuteSelect(out, name, viewModel.isDisabled(), minute);
101: }
102:
103: out.write("</td></tr></table>\n");
104:
105: super .doEndTag(out);
106: return EVAL_PAGE;
107: }
108:
109: public String getTimeStyleClass() {
110: return timeStyleClass;
111: }
112:
113: /* ***********************************************************************************
114: * Tag attributes
115: * ***********************************************************************************/
116:
117: /**
118: * @jsp.attribute
119: * type = "java.lang.String"
120: * required = "false"
121: * description = "Css class for date."
122: */
123: public void setDateStyleClass(String dateCssClass)
124: throws JspException {
125: this .dateStyleClass = (String) evaluate("dateStyleClass",
126: dateCssClass, String.class);
127: }
128:
129: /**
130: * @jsp.attribute
131: * type = "java.lang.String"
132: * required = "false"
133: * description = "Css class for time."
134: */
135: public void setTimeStyleClass(String timeCssClass)
136: throws JspException {
137: this .timeStyleClass = (String) evaluate("timeStyleClass",
138: timeCssClass, String.class);
139: }
140:
141: /* ***********************************************************************************
142: * Helper functions, mostly javascript.
143: * ***********************************************************************************/
144:
145: protected void writeMinuteSelect(Writer out, String name,
146: boolean disabled, Integer minute) throws IOException {
147: DateTimeControl.ViewModel viewModel = ((DateTimeControl.ViewModel) controlViewModel);
148: out
149: .write("<select id=\""
150: + name
151: + ".select2\" name=\""
152: + name
153: + ".select2\" onChange=\""
154: + fillXJSCallConstructor(
155: "Aranea.UI.fillTimeText", name)
156: + ";"
157: + ((!disabled && events && viewModel
158: .isOnChangeEventRegistered()) ? JspWidgetCallUtil
159: .getSubmitScriptForEvent()
160: : "") + "\"");
161:
162: if (disabled)
163: out.write(" disabled=\"true\"");
164:
165: if (!disabled && events
166: && viewModel.isOnChangeEventRegistered()) {
167: UiUpdateEvent event = new UiUpdateEvent(
168: OnChangeEventListener.ON_CHANGE_EVENT, name, null,
169: updateRegionNames);
170: event
171: .setEventPrecondition(getMinuteSelectOnChangePrecondition(name
172: + ".time"));
173: out.write(" ");
174: out.write(event.getEventAttributes().toString());
175: }
176: out.write(">\n");
177:
178: JspUtil.writeStartTag_SS(out, "script");
179: out.write(getTimeSelectScript(name + ".select2", minute, 60));
180: JspUtil.writeEndTag_SS(out, "script");
181:
182: JspUtil.writeEndTag_SS(out, "select");
183: }
184:
185: protected void writeHourSelect(Writer out, String name,
186: boolean disabled, Integer hour) throws IOException {
187: DateTimeControl.ViewModel viewModel = ((DateTimeControl.ViewModel) controlViewModel);
188: out
189: .write("<select id=\""
190: + name
191: + ".select1\" name=\""
192: + name
193: + ".select1\" onChange=\""
194: + fillXJSCallConstructor(
195: "Aranea.UI.fillTimeText", name)
196: + ";"
197: + ((!disabled && events && viewModel
198: .isOnChangeEventRegistered()) ? JspWidgetCallUtil
199: .getSubmitScriptForEvent()
200: : "") + "\"");
201: if (disabled)
202: out.write(" disabled=\"true\"");
203:
204: if (!disabled && events
205: && viewModel.isOnChangeEventRegistered()) {
206: UiUpdateEvent event = new UiUpdateEvent(
207: OnChangeEventListener.ON_CHANGE_EVENT, name, null,
208: updateRegionNames);
209: event
210: .setEventPrecondition(getHourSelectOnChangePrecondition(name
211: + ".time"));
212: out.write(" ");
213: out.write(event.getEventAttributes().toString());
214: }
215: out.write(">\n");
216:
217: JspUtil.writeStartTag_SS(out, "script");
218: out.write(getTimeSelectScript(name + ".select1", hour, 24));
219: JspUtil.writeEndTag_SS(out, "script");
220:
221: JspUtil.writeEndTag_SS(out, "select");
222: }
223:
224: /**
225: * Writes out time input
226: */
227: protected void writeTimeInput(Writer out, String name,
228: String value, String label, Long size, boolean disabled)
229: throws Exception {
230: DateTimeControl.ViewModel viewModel = ((DateTimeControl.ViewModel) controlViewModel);
231:
232: if (viewModel.getTimeViewModel().getInputFilter() != null) {
233: attributes
234: .put(
235: AraneaAttributes.FilteredInputControl.CHARACTER_FILTER,
236: viewModel.getTimeViewModel()
237: .getInputFilter()
238: .getCharacterFilter());
239: }
240:
241: JspUtil.writeOpenStartTag(out, "input");
242: JspUtil.writeAttribute(out, "id", name + ".time");
243: JspUtil.writeAttribute(out, "name", name + ".time");
244: JspUtil.writeAttribute(out, "class", getTimeStyleClass());
245: JspUtil.writeAttribute(out, "type", "text");
246: JspUtil.writeAttribute(out, "value", value);
247: JspUtil.writeAttribute(out, "size", size);
248: JspUtil.writeAttribute(out, "tabindex", tabindex);
249:
250: if (!disabled && events
251: && viewModel.isOnChangeEventRegistered()) {
252: JspUtil.writeAttribute(out, "onfocus",
253: "Aranea.UI.saveValue(this)");
254: UiUpdateEvent event = new UiUpdateEvent(
255: OnChangeEventListener.ON_CHANGE_EVENT, name, null,
256: updateRegionNames);
257: event
258: .setEventPrecondition(getTimeInputOnChangePrecondition(name
259: + ".time"));
260: out.write(" ");
261: out.write(event.getEventAttributes().toString());
262: }
263:
264: StringBuffer onBlur = new StringBuffer();
265: if (showTimeSelect)
266: onBlur.append(fillXJSCallConstructor(
267: "Aranea.UI.fillTimeSelect", name)
268: + ";");
269: if (!disabled && events
270: && viewModel.isOnChangeEventRegistered())
271: onBlur.append(JspWidgetCallUtil.getSubmitScriptForEvent());
272: JspUtil.writeAttribute(out, "onBlur", onBlur.toString());
273:
274: if (disabled)
275: JspUtil.writeAttribute(out, "disabled", "true");
276: JspUtil.writeAttributes(out, attributes);
277: JspUtil.writeCloseStartEndTag_SS(out);
278: }
279:
280: /**
281: * Writes out date input.
282: *
283: * If just super.writeDateInput is called then date's viewmodel does not have
284: * correct information about whether onchange listeners are registered and who has registered them.
285: */
286: protected void writeDateInput(Writer out, String id, String name,
287: String value, String label, boolean isMandatory,
288: boolean isValid, Long size, boolean disabled,
289: String styleClass, String accessKey,
290: DateControl.ViewModel viewModel) throws Exception {
291: DateTimeControl.ViewModel dateTimeViewModel = ((DateTimeControl.ViewModel) controlViewModel);
292: // Write input tag
293:
294: if (dateTimeViewModel.getDateViewModel().getInputFilter() != null) {
295: attributes
296: .put(
297: AraneaAttributes.FilteredInputControl.CHARACTER_FILTER,
298: dateTimeViewModel.getDateViewModel()
299: .getInputFilter()
300: .getCharacterFilter());
301: }
302:
303: JspUtil.writeOpenStartTag(out, "input");
304: if (!StringUtils.isBlank(id))
305: JspUtil.writeAttribute(out, "id", id);
306: JspUtil.writeAttribute(out, "name", name);
307: JspUtil.writeAttribute(out, "class", styleClass);
308: JspUtil.writeAttribute(out, "style", getStyle());
309: JspUtil.writeAttribute(out, "type", "text");
310: JspUtil.writeAttribute(out, "value", value);
311: JspUtil.writeAttribute(out, "size", size);
312: JspUtil.writeAttribute(out, "tabindex", tabindex);
313: if (!StringUtils.isBlank(accessKey))
314: JspUtil.writeAttribute(out, "accesskey", accessKey);
315:
316: if (disabled) {
317: JspUtil.writeAttribute(out, "disabled", "true");
318: }
319: // dateTimeViewModel's event listeners are these to look out for
320: else if (events
321: && dateTimeViewModel.isOnChangeEventRegistered()) {
322: writeSubmitScriptForUiEvent(out, "onchange",
323: this .derivedId, "onChanged", onChangePrecondition,
324: updateRegionNames);
325: }
326:
327: JspUtil.writeAttributes(out, attributes);
328: JspUtil.writeCloseStartEndTag_SS(out);
329:
330: if (!disabled) {
331:
332: JspUtil.writeOpenStartTag(out, "a");
333: JspUtil.writeAttribute(out, "href", "javascript:;");
334: JspUtil.writeCloseStartTag_SS(out);
335:
336: String calendarImgId = id + CALENDAR_BUTTON_ID_SUFFIX;
337: JspUtil.writeOpenStartTag(out, "img");
338: out.write(" src=\"");
339: out.write(FileImportUtil.getImportString(
340: "gfx/ico_calendar.gif", pageContext.getRequest()));
341: out.write("\" ");
342: JspUtil.writeAttribute(out, "id", calendarImgId);
343: JspUtil.writeAttribute(out, "class", calendarIconClass);
344: JspUtil.writeCloseStartEndTag_SS(out);
345:
346: JspUtil.writeEndTag_SS(out, "a");
347:
348: writeCalendarScript(out, id, "%d.%m.%Y");
349: }
350: }
351:
352: protected String fillXJSCallConstructor(String function,
353: String element) {
354: return FormTimeInputHtmlTag.staticFillXJSCall(function, element
355: + ".time", element + ".select1", element + ".select2");
356: }
357:
358: /**
359: * @jsp.attribute
360: * type = "java.lang.String"
361: * required = "false"
362: * description = "Boolean, specifying whether HTML <select&;gt;'s should be shown for foolproof hour/minute selection."
363: *
364: * @since 1.0.3
365: */
366: public void setShowTimeSelect(String showTimeSelect)
367: throws JspException {
368: this .showTimeSelect = ((Boolean) evaluate("showTimeSelect",
369: showTimeSelect, Boolean.class)).booleanValue();
370: }
371: }
|