public static String getValue(FacesContext context, UICalendar calendar, Object value, String pattern, boolean ignoreConverter) {
        if (!ignoreConverter) {
            //first ask the converter
            Converter converter = calendar.getConverter();
            // always use the user-applied converter first
            if (converter != null) {
                return converter.getAsString(context, calendar, value);
            }
        }

        if (value instanceof String) {
            return (String) value;
        }
        //Use built-in converter
        else if (value instanceof Date) {
            SimpleDateFormat format = new SimpleDateFormat(pattern, calendar.calculateLocale(context));
            format.setTimeZone(calculateTimeZone(calendar.getTimeZone()));

            return format.format((Date) value);
        }
        else if (value instanceof LocalDate || value instanceof LocalDateTime || value instanceof LocalTime || value instanceof YearMonth) {
            DateTimeFormatter dateTimeFormatter = DateTimeFormatter.ofPattern(pattern, calendar.calculateLocale(context));
            if (value instanceof LocalDate) {
                return ((LocalDate) value).format(dateTimeFormatter);
            }
            else if (value instanceof LocalDateTime) {
                return ((LocalDateTime) value).format(dateTimeFormatter);
            }
            else if (value instanceof LocalTime) {
                if (calendar instanceof UICalendar) {
                    return LocalDateTime.of(LocalDate.now(), (LocalTime) value).format(dateTimeFormatter);
                }
                return ((LocalTime) value).format(dateTimeFormatter);
            }
            else { //if (value instanceof YearMonth)
                return ((YearMonth) value).format(dateTimeFormatter);
            }
        }
        else {
            //Delegate to global defined converter (e.g. joda)
            Class<?> type = ELUtils.getType(context, calendar.getValueExpression("value"));
            if (type != null && type != Object.class && type != Date.class &&
                    type != LocalDate.class && type != LocalDateTime.class && type != LocalTime.class && type != YearMonth.class) {
                Converter converter = context.getApplication().createConverter(type);
                if (converter != null) {
                    return converter.getAsString(context, calendar, value);
                }
            }

            throw new FacesException("Value could be either String, LocalDate, LocalDateTime, LocalTime, YearMonth or java.util.Date (deprecated)");
        }
    }
Try to convert the given value to an {@link Instant} or return <code>null</code> if there is no appropriate converter for doing so.
The type of the value must be one of {@link LocalDateTime}, {@link LocalDate}, {@link LocalTime}, {@link Date} (deprecated),
or a parsable date or time {@link String}. For any other this method throws a {@link FacesException}.
@param context the faces context
@param calendar the calendar component
@param value the value to convert
@param attributeName the attribute name of the value (e.g. mindate, or maxdate)
@return the {@link Instant} object or <code>null</code>
@throws FacesException if value type is not supported
primefaces/src/main/java/org/primefaces/util/CalendarUtils.java