En su carpeta Views/Shared/EditorTemplates
cree una vista parcial llamada DateTime.ascx
.
El código para esta EditorTemplate debe ser algo como
<%@ Control Language="C#" Inherits="System.Web.Mvc.ViewUserControl<DateTime?>" %>
<%
string controlId = ViewData.TemplateInfo.HtmlFieldPrefix.Replace('.', '_');
%>
<script type="text/javascript">
$(function() {
$('#<%: controlId %>_Day, #<%: controlId %>_Month, #<%: controlId %>_Year').live('change', function() { updateHiddenDate('<%: controlId %>'); });
$('#<%: controlId %>_Day').val('<%: Model.HasValue ? Model.Value.Day.ToString() : "" %>');
$('#<%: controlId %>_Month').val('<%: Model.HasValue ? Model.Value.Month.ToString() : "" %>');
$('#<%: controlId %>_Year').val('<%: Model.HasValue ? Model.Value.Year.ToString() : "" %>');
updateHiddenDate('<%: controlId %>');
});
function updateHiddenDate(hiddenDateId) {
$('#' + hiddenDateId).val($('#' + hiddenDateId + '_Year').val() + "-" + $('#' + hiddenDateId + '_Month').val() + "-" + $('#' + hiddenDateId + '_Day').val());
}
</script>
<select id="<%: controlId %>_Day">
<% for (int dayOrdinal = 1; dayOrdinal <= 31; dayOrdinal++)
{
Response.Write(string.Format("<option value=\"{0}\">{0}</option>", dayOrdinal));
}
%>
</select>
<select id="<%: controlId %>_Month">
<% for (int monthOrdinal = 1; monthOrdinal <= 12; monthOrdinal++)
{
Response.Write(string.Format("<option value=\"{0}\">{1}</option>", monthOrdinal, System.Globalization.DateTimeFormatInfo.CurrentInfo.MonthNames[monthOrdinal - 1]));
}
%>
</select>
<select id="<%: controlId %>_Year">
<% for (int yearOrdinal = DateTime.Now.Year - 5; yearOrdinal <= DateTime.Now.Year + 5; yearOrdinal++)
{
Response.Write(string.Format("<option value=\"{0}\">{0}</option>", yearOrdinal));
}
%>
</select>
<%: Html.Hidden("", Model.HasValue ? String.Format("{0:yyyy-MM-dd}", Model) : "") %>
que crea un editor de plantillas con un campo oculto que contiene una representación de la norma ISO 8601 a la fecha la cual el MVC ModelBinder puede analizar.
jQuery actualiza el campo oculto cada vez que cambian las listas desplegables. Tenga en cuenta el uso del ViewData.TemplateInfo.HtmlFieldPrefix
que uso para obtener el id
generado del campo oculto.
Note que esta solución se aplica fácilmente sin que se dañe con Custom ModelBinders porque construimos un único valor de formulario que contiene la fecha y hora completa.Sin embargo, esto no quiere decir que
- Usted confía en que el cliente tenga activado Javascript, y
- Es necesario incluir una referencia de script a la biblioteca jQuery en su masterpage (por ejemplo
<script type="text/javascript" src="../../Scripts/jquery-1.4.1.min.js"></script>
)
Si eso no es aceptable, tendrá que mirar Custom ModelBinders como @Jon ha señalado.