나는 ASP.NET과 MVC에 상당히 익숙하며 인터넷 검색 및 실험에도 불구하고이 문제를 해결하는 가장 좋은 방법은 비어 있습니다. .ASP.NET MVC - 3 개의 드롭 다운 목록이있는 유효하지 않은 DateTime 선택 유지
EmailAddressAttribute와 비슷한 방식으로 작업하려는 BirthdayAttribute를 작성했습니다. birthday 속성은 UI 힌트를 설정하여 생일 DateTime이 3 개의 드롭 다운 목록이있는 편집기 템플릿을 사용하여 렌더링되도록합니다. 이 속성은 연도 드롭 다운에 몇 년 동안 표시해야 하는지를 알려주는 몇 가지 추가 메타 데이터를 설정하는 데 사용할 수도 있습니다.
jQuery의 날짜 선택 도구를 사용할 수 있다는 것을 알고 있지만, 생일의 경우 3 개의 드롭 다운이 훨씬 유용하다는 것을 알게되었습니다.
@model DateTime
@using System;
@using System.Web.Mvc;
@{
UInt16 numberOfVisibleYears = 100;
if (ViewData.ModelMetadata.AdditionalValues.ContainsKey("NumberOfVisibleYears"))
{
numberOfVisibleYears = Convert.ToUInt16(ViewData.ModelMetadata.AdditionalValues["NumberOfVisibleYears"]);
}
var now = DateTime.Now;
var years = Enumerable.Range(0, numberOfVisibleYears).Select(x => new SelectListItem { Value = (now.Year - x).ToString(), Text = (now.Year - x).ToString() });
var months = Enumerable.Range(1, 12).Select(x => new SelectListItem{ Text = new DateTime(now.Year, x, 1).ToString("MMMM"), Value = x.ToString() });
var days = Enumerable.Range(1, 31).Select(x => new SelectListItem { Value = x.ToString("00"), Text = x.ToString() });
}
@Html.DropDownList("Year", years, "<Year>")/
@Html.DropDownList("Month", months, "<Month>")/
@Html.DropDownList("Day", days, "<Day>")
나중에 내 날짜를 다시 작성하려면 ModelBinder가 있어야합니다. 내가 간략하게하기 위해 도우미 함수의 내용을 제거했지만, 모든 것이이 시점까지 훌륭하게 작동합니다. 정상이며 유효한 날짜는 회원을 만들거나 편집 할 때 잘 작동합니다.
public class DateSelector_DropdownListBinder : DefaultModelBinder
{
public override object BindModel(ControllerContext controllerContext, ModelBindingContext bindingContext)
{
if (controllerContext == null)
throw new ArgumentNullException("controllerContext");
if (bindingContext == null)
throw new ArgumentNullException("bindingContext");
if (IsDropdownListBound(bindingContext))
{
int year = GetData(bindingContext, "Year");
int month = GetData(bindingContext, "Month");
int day = GetData(bindingContext, "Day");
DateTime result;
if (!DateTime.TryParse(string.Format("{0}/{1}/{2}", year, month, day), out result))
{
//TODO: SOMETHING MORE USEFUL???
bindingContext.ModelState.AddModelError("", string.Format("Not a valid date."));
}
return result;
}
else
{
return base.BindModel(controllerContext, bindingContext);
}
}
private int GetData(ModelBindingContext bindingContext, string propertyName)
{
// parse the int using the correct value provider
}
private bool IsDropdownListBound(ModelBindingContext bindingContext)
{
//check model meta data UI hint for above editor template
}
}
이제 살펴볼 것이므로 nullable DateTime을 사용해야 할 것입니다.하지만 여기에는 물론 여기에도 없습니다.
내가 겪고있는 문제는 2 월 30 일 또는 9 월 31 일과 같은 유효하지 않은 날짜의 매우 기본적인 유효성 검사와 관련되어 있습니다. 유효성 검사 자체는 훌륭하게 작동하지만 유효하지 않은 날짜는 양식이 다시로드 될 때 저장되고 지속되지 않습니다.
내가 원하는 것은 2 월 30 일의 잘못된 날짜를 기억하고 드롭 다운을 기본값으로 다시 설정하는 대신 유효성 검사 메시지로 다시 표시하는 것입니다. 전자 메일 주소 (EmailAddressAttribute로 장식 됨)와 같은 다른 필드는 유효하지 않은 항목을 그대로 유지합니다.
현재 서버 측 유효성 검사를 받으려고하고 있습니다. 솔직히 클라이언트 측 유효성 검사에 대해서 아직 생각조차하지 못했습니다.
나는이 문제를 논점으로 만들기 위해 자바 스크립트와 아약스로 할 수있는 일이 많이 있다는 것을 알고있다. 그러나 나는 여전히 올바른 서버 측 유효성 검사를 사용하여 다시 실패 할 것이다.
변경 이벤트를 드롭 다운에 추가하고 숨김 필드에 전체 날짜를 생성하고 유효성을 검사하면 숨겨진 텍스트 상자 값의 드롭 다운에서 값을 다시 선택할 수 있습니다. 클라이언트 측 코드 – davethecoder