2014-10-07 50 views
0

我一直試圖讓兩個模型出現在使用ViewModels的單個視圖中,但是失敗了。無法將兩個模型合併到一個ViewModel中

我現在有3個字段的簡單視圖(評論,姓名,部門)以及與之匹配的模型。我有一個控制器返回一個空視圖,當你提交表單時,空模型被填充並傳回給控制器。我現在想要將部門字段變成一個下拉列表,並推導出(也許不正確?),我應該創建另一個模型,其中包含靜態值,然後通過控制器將ViewModel傳遞給視圖,但是當我嘗試執行此操作時,它失敗:

查看:

@using (Html.BeginForm()) { 
    @Html.AntiForgeryToken() 
    @Html.ValidationSummary(true) 

    <div class="fieldset"> 
     <fieldset> 
      <legend>CommentDb</legend> 

      <div class="editor-label"> 
       @Html.LabelFor(model => model.Comment) 
      </div> 
      <div> 
       @Html.TextAreaFor(model => model.Comment, new {style = "width: 900px; height:200px;", autocomplete = "off" }) 
       @Html.ValidationMessageFor(model => model.Comment) 
      </div> 

      <div class="editor-label"> 
       @Html.Label("Your Name") 
       @*@Html.LabelFor(model => model.CommentByName)*@ 
       @Html.TextBoxFor(model => model.CommentByName, new { autocomplete = "off", placeholder = "Optional" }) 
       @Html.ValidationMessageFor(model => model.CommentByName) 
      </div> 

      <div class="editor-label"> 
       @Html.Label("Your Department", new { @class = "display-label" }) 
       @*@Html.LabelFor(model => model.Department)*@ 
       @Html.TextBoxFor(model => model.Department, new { autocomplete = "off", placeholder = "Optional" }) 
       @Html.ValidationMessageFor(model => model.Department) 
      </div> 
     </fieldset> 
     <br /> 
     <br /> 
    </div> 

    <div> 
     <input type="submit" value="Create" id="submit"/> 
    </div> 

} 

部下拉模式:

namespace SuggestionBox.Models 
{ 
    public class DropDownModel 
    { 
     public String Departments { get; set; } 

     public String SetDropDownList() 
     { 
      Departments = "Engineering"; 

      return Departments; 
     } 
    } 
} 

數據基本型號:

namespace SuggestionBox.Models 
{ 
    public class CommentModel 
    { 
     [Key] 
     public int CommentiD { get; set; } 
     public string CommentByName { get; set; } 
     public string Department { get; set; } 
     [Required] 
     public string Comment { get; set; } 
     public DateTime InsertDate { get; set; } 
    } 
} 

namespace SuggestionBox.Models 
{ 
    public class CommentDbContext : DbContext 
    { 

     public CommentDbContext() : base() 
     { 
      Database.SetInitializer(new MigrateDatabaseToLatestVersion<CommentDbContext, SuggestionBox.Migrations.Configuration>()); 
     } 

     public DbSet<CommentModel> Comments { get; set; } 
    } 
} 

我試圖視圖模型:

namespace SuggestionBox.ViewModels 
{ 
    public class SuggestionBoxViewModel 
    { 
     public CommentModel Comments { get; set; } 
     public DropDownModel Departments { get; set; } 

     public SuggestionBoxViewModel() 
     { 
      Departments = new DropDownModel(); 
      Departments.SetDropDownList(); 

      Comments = new CommentModel(); 
     } 
    } 
} 

控制器:

public ViewResult Index() 
    { 
     SuggestionBoxViewModel vm = new SuggestionBoxViewModel(); 

     return View(vm); 
    } 

return View(vm);,在IDE說:Arguement型「SuggestionBox.ViewModels .SuggestionBoxViewModel'不是可分配給模型類型'SuggestionBox.Models.CommentModel'

任何想法我在這裏做錯了嗎?

乾杯。

+0

你好像在視圖中指定CommentModel'的'模型類型,而不是SuggestionBoxViewModel'的'。 – 2014-10-07 20:27:02

+0

謝謝傑森。就是這樣! DUH! :-) – 2014-10-07 21:01:09

回答

2

你正在將一件簡單的事情變成過於複雜的事情。您的視圖模型應該只包含視圖中使用的屬性,並且不應該包含方法。填充視圖模型屬性是控制器的職責。

視圖模型

public class CommentModelVM 
{ 
    [Required] 
    public string Comment { get; set; } 
    public string CommentByName { get; set; } 
    [Display(Name="Your Department")] // add attributes associated with the view 
    public string Department { get; set; } 
    public SelectList DepartmentList { get; set } // to populate the dropdown options 
} 

控制器

public ActionResult Create() 
{ 
    CommentModelVM model = new CommentModelVM(); 
    ConfigureViewModel(model); 
    return View(model); 
} 

public ActionResult Create(CommentModelVM model) 
{ 
    if (!ModelState.IsValid()) 
    { 
    // Repopulate options and return view 
    ConfigureViewModel(model); 
    return View(model); 
    } 
    // Save and redirect 
} 

private void ConfigureViewModel(CommentModelVM model) 
{ 
    List<string> departments = // create your list of departments here (from database or static list) 
    model.DepartmentList = new SelectList(departments); 
} 

查看

.... 
@Html.LabelFor(m => m.Department)  
@Html.DropDownListFor(m => m.Department, Model.DepartmentList) 
.... 
0

您的觀點似乎期望評論模型。

如果你想綁定到一個ViewModel,那麼你將不得不實現評論公開的所有屬性。

所以你的視圖模型可能是這樣的:

namespace SuggestionBox.ViewModels 
{ 
    public class SuggestionBoxViewModel 
    { 
     public CommentModel Comments { get; set; } 
     public DropDownModel Departments { get; set; } 

     public SuggestionBoxViewModel() 
     { 
      Departments = new DropDownModel(); 
      Departments.SetDropDownList(); 

      Comments = new CommentModel(); 
     } 

     public int CommentiD 
     { 
      get { return Comments.CommentiD; } 
     } 

     public string CommentByName 
     { 
      get { return Comments.CommentByName; } 
     } 

     ...etc. 
    } 
} 
1

我只想說,通常它是一個壞主意來命名,我們的ViewModels性質或班列視圖控件,他們必然要開始。例如:DropDownModel。這樣做會造成混淆,因爲模型和視圖模型不代表UI組件,它們代表視圖用於呈現其UI控件的實體和數據。

有人說,回答你的問題,我沒有看到需要一個ViewModel類來代表您的下拉列表的部門的靜態列表。我想你應該只需添加部門的一個新的列表,你SuggestionBoxViewModel類是這樣的:

namespace SuggestionBox.ViewModels 
{ 
    public class SuggestionBoxViewModel 
    { 
     public CommentModel Comments { get; set; } 

     public IEnumerable<string> Departments { get; set; } 

     public string SelectedDepartment { get; set; } 

     public SuggestionBoxViewModel() 
     { 
      Departments = new [] {"Engineering","Sales"}; 

      Comments = new CommentModel(); 
     } 

     public int CommentiD 
     { 
      get { return Comments.CommentiD; } 
     } 

     public string CommentByName 
     { 
      get { return Comments.CommentByName; } 
     }   
    } 
} 

然後在您的視圖所有你需要做的就是下拉結合部門的名單。就像這樣:

在您的視圖的頂部:

@model SuggestionBox.ViewModels.SuggestionBoxViewModel 

然後在您想要的下拉菜單顯示:

@Html.DropDownListFor(m => m.SelectedDepartment, new SelectList(Model.Departments)) 

就是這樣!我希望這有幫助。

+0

感謝@alejosoft。這非常有幫助。但是,你能解釋你的第一段嗎?我想確保我的命名約定對未來是正確的。 – 2014-10-07 21:31:33

+0

我的意思是說,你應該保持你的數據對象(模型和視圖模型)和UI元素(如下拉菜單,文本框等)之間的清晰分離...因此,使用類似GenderRadioButtonViewModel的名稱命名ViewModel是一種不好的做法,或者DropDownViewModel。是否有意義? – alejosoft 2014-10-07 21:37:37

+0

我相信是的。你所說的是,不是調用Model:DropDown ...,而應該是關於數據的東西,而不是數據將出現的UI元素,例如, DepartmentModel。 – 2014-10-08 18:17:29

相關問題