public UIComponent buildWidget( String elementName, Map<String, String> attributes, UIMetawidget metawidget) { // Not for RichFaces? if (TRUE.equals(attributes.get(HIDDEN))) { return null; } // Note: we tried implementing lookups using org.richfaces.ComboBox, but that // allows manual input and if you set enableManualInput=false it behaves a // bit screwy for our liking (ie. if you hit backspace the browser goes back) if (attributes.containsKey(FACES_LOOKUP) || attributes.containsKey(LOOKUP)) { return null; } // Lookup the class Class<?> clazz = WidgetBuilderUtils.getActualClassOrType(attributes, null); if (clazz == null) { return null; } // Primitives if (clazz.isPrimitive()) { // Not for RichFaces if (boolean.class.equals(clazz) || char.class.equals(clazz)) { return null; } // Ranged UIComponent ranged = createRanged(attributes); if (ranged != null) { return ranged; } // Not-ranged HtmlInputNumberSpinner spinner = VERSION_SPECIFIC_WIDGET_BUILDER.createInputNumberSpinner(); // May be ranged in one dimension only. In which case, explictly range the *other* // dimension because RichFaces defaults to 0-100 String minimumValue = attributes.get(MINIMUM_VALUE); if (minimumValue != null && !"".equals(minimumValue)) { spinner.setMinValue(minimumValue); } else if (byte.class.equals(clazz)) { spinner.setMinValue(String.valueOf(Byte.MIN_VALUE)); } else if (short.class.equals(clazz)) { spinner.setMinValue(String.valueOf(Short.MIN_VALUE)); } else if (int.class.equals(clazz)) { spinner.setMinValue(String.valueOf(Integer.MIN_VALUE)); } else if (long.class.equals(clazz)) { spinner.setMinValue(String.valueOf(Long.MIN_VALUE)); } else if (float.class.equals(clazz)) { spinner.setMinValue(String.valueOf(-Float.MAX_VALUE)); } else if (double.class.equals(clazz)) { spinner.setMinValue(String.valueOf(-Double.MAX_VALUE)); } String maximumValue = attributes.get(MAXIMUM_VALUE); if (maximumValue != null && !"".equals(maximumValue)) { spinner.setMaxValue(maximumValue); } else if (byte.class.equals(clazz)) { spinner.setMaxValue(String.valueOf(Byte.MAX_VALUE)); } else if (short.class.equals(clazz)) { spinner.setMaxValue(String.valueOf(Short.MAX_VALUE)); } else if (int.class.equals(clazz)) { spinner.setMaxValue(String.valueOf(Integer.MAX_VALUE)); } else if (long.class.equals(clazz)) { spinner.setMaxValue(String.valueOf(Long.MAX_VALUE)); } else if (float.class.equals(clazz)) { spinner.setMaxValue(String.valueOf(Float.MAX_VALUE)); } else if (double.class.equals(clazz)) { spinner.setMaxValue(String.valueOf(Double.MAX_VALUE)); } // Wraps around? spinner.setCycled(false); // Stepped if (float.class.equals(clazz) || double.class.equals(clazz)) { spinner.setStep("0.1"); } return spinner; } // Dates // // Note: when http://jira.jboss.org/jira/browse/RF-2023 gets implemented, that // would allow external, app-level configuration of this Calendar if (Date.class.isAssignableFrom(clazz)) { UICalendar calendar = FacesUtils.createComponent(HtmlCalendar.COMPONENT_TYPE, "org.richfaces.CalendarRenderer"); if (attributes.containsKey(DATETIME_PATTERN)) { calendar.setDatePattern(attributes.get(DATETIME_PATTERN)); } if (attributes.containsKey(LOCALE)) { calendar.setLocale(new Locale(attributes.get(LOCALE))); } if (attributes.containsKey(TIME_ZONE)) { calendar.setTimeZone(TimeZone.getTimeZone(attributes.get(TIME_ZONE))); } return calendar; } // Object primitives if (Number.class.isAssignableFrom(clazz)) { // Ranged UIComponent ranged = createRanged(attributes); if (ranged != null) { return ranged; } // Not-ranged // // Until https://jira.jboss.org/jira/browse/RF-4450 is fixed, do not use // UIInputNumberSpinner for nullable numbers } // RichFaces version-specific return VERSION_SPECIFIC_WIDGET_BUILDER.buildWidget(elementName, attributes, metawidget); }
public Converter getConverter(ValueHolder valueHolder, Map<String, String> attributes) { // Use existing Converter (if any) Converter converter = valueHolder.getConverter(); if (converter != null) { return converter; } // Create from id FacesContext context = FacesContext.getCurrentInstance(); String converterId = attributes.get(FACES_CONVERTER); if (converterId != null) { converter = context.getApplication().createConverter(converterId); } else if (valueHolder instanceof UISelectOne || valueHolder instanceof UISelectMany) { // Create from parameterized type (eg. a Date converter for List<Date>) String parameterizedType = WidgetBuilderUtils.getComponentType(attributes); if (parameterizedType != null) { Class<?> parameterizedClass = ClassUtils.niceForName(parameterizedType); // The parameterized type might be null, or might not be concrete // enough to be instantiatable (eg. List<? extends Foo>) if (parameterizedClass != null) { converter = context.getApplication().createConverter(parameterizedClass); } } } else { // Create implicit converters // // JSF does not appear to implicitly hook up DateTimeConverters without either an // explicit f:convertDateTime tag or a registered java.util.Date converter. Adding one // fixes both POSTback and display of read-only dates (otherwise JSF uses Date.toString) // // JSF *does* appear to implicitly hook up NumberConverters. String type = attributes.get(TYPE); if (type != null) { Class<?> clazz = ClassUtils.niceForName(type); if (clazz != null) { if (clazz.isAssignableFrom(Date.class)) { converter = getDateTimeConverter(converter); } } } } // Support for DateTimeConverter if (attributes.containsKey(DATE_STYLE)) { converter = getDateTimeConverter(converter); ((DateTimeConverter) converter).setDateStyle(attributes.get(DATE_STYLE)); } if (attributes.containsKey(DATETIME_PATTERN)) { converter = getDateTimeConverter(converter); ((DateTimeConverter) converter).setPattern(attributes.get(DATETIME_PATTERN)); } if (attributes.containsKey(TIME_STYLE)) { converter = getDateTimeConverter(converter); ((DateTimeConverter) converter).setTimeStyle(attributes.get(TIME_STYLE)); } if (attributes.containsKey(TIME_ZONE)) { converter = getDateTimeConverter(converter); ((DateTimeConverter) converter).setTimeZone(TimeZone.getTimeZone(attributes.get(TIME_ZONE))); } if (attributes.containsKey(DATETIME_TYPE)) { converter = getDateTimeConverter(converter); ((DateTimeConverter) converter).setType(attributes.get(DATETIME_TYPE)); } // Support for NumberConverter if (attributes.containsKey(CURRENCY_CODE)) { converter = getNumberConverter(converter); ((NumberConverter) converter).setCurrencyCode(attributes.get(CURRENCY_CODE)); } if (attributes.containsKey(CURRENCY_SYMBOL)) { converter = getNumberConverter(converter); ((NumberConverter) converter).setCurrencySymbol(attributes.get(CURRENCY_SYMBOL)); } if (attributes.containsKey(NUMBER_USES_GROUPING_SEPARATORS)) { converter = getNumberConverter(converter); ((NumberConverter) converter) .setGroupingUsed(Boolean.parseBoolean(attributes.get(NUMBER_USES_GROUPING_SEPARATORS))); } if (attributes.containsKey(MINIMUM_INTEGER_DIGITS)) { converter = getNumberConverter(converter); ((NumberConverter) converter) .setMinIntegerDigits(Integer.parseInt(attributes.get(MINIMUM_INTEGER_DIGITS))); } if (attributes.containsKey(MAXIMUM_INTEGER_DIGITS)) { converter = getNumberConverter(converter); ((NumberConverter) converter) .setMaxIntegerDigits(Integer.parseInt(attributes.get(MAXIMUM_INTEGER_DIGITS))); } if (attributes.containsKey(MINIMUM_FRACTIONAL_DIGITS)) { converter = getNumberConverter(converter); ((NumberConverter) converter) .setMinFractionDigits(Integer.parseInt(attributes.get(MINIMUM_FRACTIONAL_DIGITS))); } if (attributes.containsKey(MAXIMUM_FRACTIONAL_DIGITS)) { converter = getNumberConverter(converter); ((NumberConverter) converter) .setMaxFractionDigits(Integer.parseInt(attributes.get(MAXIMUM_FRACTIONAL_DIGITS))); } if (attributes.containsKey(NUMBER_PATTERN)) { converter = getNumberConverter(converter); ((NumberConverter) converter).setPattern(attributes.get(NUMBER_PATTERN)); } if (attributes.containsKey(NUMBER_TYPE)) { converter = getNumberConverter(converter); ((NumberConverter) converter).setType(attributes.get(NUMBER_TYPE)); } // Locale (applies to both DateTimeConverter and NumberConverter) if (attributes.containsKey(LOCALE)) { if (converter instanceof NumberConverter) { ((NumberConverter) converter).setLocale(new Locale(attributes.get(LOCALE))); } else { converter = getDateTimeConverter(converter); ((DateTimeConverter) converter).setLocale(new Locale(attributes.get(LOCALE))); } } // Return it return converter; }