2012-06-26 2 views
12

Утро все.MVC 4, флажок и я

Я вижу, что это обсуждалось в другом месте, но было интересно, если что-то изменилось или что-то упростилось в MVC 4 для таких простаков, как я ?!

Сценарий

У меня есть следующие, отредактированы модель:

public class CorporateDetails 
{ 

    public Guid? Id { get; set; } 

    [Key] 
    public int CorporateDetailId { get; set; } 

    public int? EmsId { get; set; } 
    public string EmsName { get; set; } 

    public virtual EmsType EmsType { get; set; } 
} 

public class EmsType 
{ 
    [Key] 
    public int? EmsId { get; set; } 
    public string EmsName { get; set; } 

    public virtual ICollection<EmsType> EmsTypes { get; set; } 
} 

следующему стандарту создать вид:

<fieldset> 
    <legend>CorporateDetails</legend> 



    <div class="editor-label"> 
     @Html.LabelFor(model => model.EmsId, "EmsType") 
    </div> 
    <div class="editor-field"> 
     @Html.DropDownList("EmsId", String.Empty) 
     @Html.ValidationMessageFor(model => model.EmsId) 
    </div> 
    <div class="editor-label"> 
     @Html.LabelFor(model => model.EmsName) 
    </div> 
    <div class="editor-field"> 
     @Html.EditorFor(model => model.EmsName) 
     @Html.ValidationMessageFor(model => model.EmsName) 
    </div> 

    <p> 
     <input type="submit" value="Create" /> 
    </p> 
</fieldset> 

Это дает мне, из из коробки, красивая падающая дова n list a la Scott Gu's blog

Теперь мой реальный вопрос: как я могу эффективно преобразовать это раскрывающееся поле в то, что будет эффективно представлять собой список избранных мультиблоков?

Снова извинился за то, что перебрался через землю, но я просто тестировал воду, чтобы увидеть, произошли ли какие-либо обновления.

Обратите внимание, что первый проект MVC так идти мягко, я чувствую себя очень толстый снова: '(

ответ

19

Хорошо, хорошо, у меня есть сортировка - ура! Как вы можете видеть из комментариев, там было несколько вопросов, которые пришли, но, пожалуйста, найти ниже полное решение, которое действительно работает: D

Модель

public class CorporateDetails 
    { 

     public Guid? Id { get; set; } 

     [Key] 
     public int CorporateDetailId { get; set; } 

     public int[] EmsId { get; set; } 

     } 

    public class EmsType 
    { 
     [Key] 
     public int EmsId { get; set; } 
     public string EmsName { get; set; } 

     public virtual ICollection<EmsType> EmsTypes { get; set; } 
    } 

Контроллер

public ActionResult Create() 
    { 
     CorporateDetails corporatedetails = new CorporateDetails(); 
     ViewBag.EmsId = new MultiSelectList(db.EmsTypes, "EmsId", "EmsName"); 
     return View(corporatedetails); 
    } 

Удлинитель (размещен в папке в корне проекта)

public static MvcHtmlString CheckBoxListFor<TModel, TProperty>(this HtmlHelper<TModel> htmlHelper, Expression<Func<TModel, TProperty[]>> expression, MultiSelectList multiSelectList, object htmlAttributes = null) 
    { 
     //Derive property name for checkbox name 
     MemberExpression body = expression.Body as MemberExpression; 
     string propertyName = body.Member.Name; 

     //Get currently select values from the ViewData model 
     TProperty[] list = expression.Compile().Invoke(htmlHelper.ViewData.Model); 

     //Convert selected value list to a List<string> for easy manipulation 
     List<string> selectedValues = new List<string>(); 

     if (list != null) 
     { 
      selectedValues = new List<TProperty>(list).ConvertAll<string>(delegate(TProperty i) { return i.ToString(); }); 
     } 

     //Create div 
     TagBuilder divTag = new TagBuilder("div"); 
     divTag.MergeAttributes(new RouteValueDictionary(htmlAttributes), true); 

     //Add checkboxes 
     foreach (SelectListItem item in multiSelectList) 
     { 
      divTag.InnerHtml += String.Format("<div><input type=\"checkbox\" name=\"{0}\" id=\"{0}_{1}\" " + 
               "value=\"{1}\" {2} /><label for=\"{0}_{1}\">{3}</label></div>", 
               propertyName, 
               item.Value, 
               selectedValues.Contains(item.Value) ? "checked=\"checked\"" : "", 
               item.Text); 
     } 

     return MvcHtmlString.Create(divTag.ToString()); 
    } 

Extension зарегистрирован в веб-конфигурации из соображений

<pages pageBaseType="System.Web.Mvc.WebViewPage"> 
    <namespaces> 
    <add namespace="System.Web.Mvc" /> 
    <add namespace="System.Web.Mvc.Ajax" /> 
    <add namespace="System.Web.Mvc.Html" /> 
    <add namespace="System.Web.Optimization"/> 
    <add namespace="System.Web.Routing" /> 
    <add namespace="MyProject.Extensions" /> 
    </namespaces> 
</pages> 

Посмотреть

@model Valpak.Websites.HealthChecker.Models.CorporateDetails 
@{ 
    ViewBag.Title = "Create"; 
} 
<h2>Create</h2> 
@using (Html.BeginForm()) 
{ 
    @Html.ValidationSummary(true) 

    <fieldset> 
     <legend>CorporateDetails</legend> 

      <div class="editor-label"> 
      @Html.CheckBoxListFor(model => model.EmsId, (MultiSelectList) ViewBag.EmsId) 
      </div>   
     <p> 
      <input type="submit" value="Create" /> 
     </p> 
    </fieldset> 
} 
<div> 
    @Html.ActionLink("Back to List", "Index") 
</div> 
@section Scripts { 
    @Scripts.Render("~/bundles/jqueryval") 
} 

Который дает мне прекрасный список флажков. Ура!

Спасибо Дарин за вашу помощь, я отметил это как ответ, но +50 для вашего времени и усилий.

+0

Действительно полезно, но было бы даже лучше, если бы была включена проверка. В настоящее время все мои текстовые поля получают красную рамку, если есть проблема проверки, есть ли у вас какие-либо идеи о том, как включить эту функцию? – Owen

2

Никаких изменений не произошло в ASP.NET MVC 4 RC в этом аспекте, и вряд ли произойдет, когда она попадает RTM .

Но вы могли бы еще implement a custom helper для достижения этой цели. И вы могли бы даже улучшить этот помощник так, что он принимает лямбда-выражение в качестве первого аргумента вместо строки, чтобы иметь сильно типизированных версию.

И если вы не используют перечисления здесь another example.

+0

Спасибо Дарина - с расширением exmaple, я должен просто добавить что как нигде в моем проекте или конкретно в представлениях? (Извините за глупый вопрос, см. Предыдущую сноску первого проекта MVC) –

+0

Вы можете создать папку 'Extensions' и в ней будет' 'HtmlExtensions.cs'', в котором вы их объявите. –

+0

Это имело бы смысл: D –

1

Если передать выбранное значение MultiSelected (параметр # 4)

ViewBag.VfonctionIds = new MultiSelectList(db.tbIntervenantFonctionTypes, "intervenantFonctionType_id", "Nom", fonctionSelected); 

Изменение Helper для

 public static MvcHtmlString CheckBoxListFor<TModel, TProperty>(this HtmlHelper<TModel> htmlHelper, Expression<Func<TModel, TProperty[]>> expression, MultiSelectList multiSelectList, object htmlAttributes = null) 
    { 
     //Derive property name for checkbox name 
     MemberExpression body = expression.Body as MemberExpression; 
     string propertyName = body.Member.Name; 

     //Create div 
     TagBuilder divTag = new TagBuilder("div"); 
     divTag.MergeAttributes(new RouteValueDictionary(htmlAttributes), true); 

     //Add checkboxes 
     foreach (SelectListItem item in multiSelectList) 
     { 
      divTag.InnerHtml += String.Format("<div><input type=\"checkbox\" name=\"{0}\" id=\"{0}_{1}\" " + 
               "value=\"{1}\" {2} /><label for=\"{0}_{1}\">{3}</label></div>", 
               propertyName, 
               item.Value, 
               (item.Selected) ? "checked=\"checked\"" : "",              
               item.Text); 
     } 

     return MvcHtmlString.Create(divTag.ToString()); 
    }