2011-04-09 40 views
1

如果這是MVC3的問題,那麼會有關於此的帖子,但我找不到任何內容。我一定做錯了什麼。我有一個簡單的視圖(Index.cshtml),它使用for循環遍歷列表。在每次迭代中,我輸出兩個文本輸入,其中一個列表項中的值。MVC3 - 使用編輯器的問題

@{Html.BeginForm();} 
@Html.Encode("\n") 
@for (int i = 0; i < Model.SortOptions.Count; i++) 
{ 
    @Html.TextBoxFor(m => m.SortOptions[i].ColumnName); 
    @Html.Encode("\n"); 
    @Html.TextBoxFor(m => m.SortOptions[i].Direction); 
    @Html.Encode("\n"); 
} 
<input type="submit" value="Submit" /> 
@{Html.EndForm();} 

我有兩個控制器的視圖,一個用於GET請求,一個用於POST。 POST版本將不同的項目添加到列表中的GET版本。這是問題出現的地方。頁面重新加載後,文本框與GET頁面上加載的頁面具有相同的值。

起初我以爲它一定是緩存問題,但如果我修改代碼(如下所示),手動添加文本輸入並將值注入到html中,則新值將發送到瀏覽器。

@{Html.BeginForm();} 
@Html.Encode("\n") 
@for (int i = 0; i < Model.SortOptions.Count; i++) 
{ 
    var columnNameName = string.Format("SortOptions[{0}].ColumnName", i); 
    var columnNameID = string.Format("SortOptions_{0}__ColumnName", i); 
    var directionName = string.Format("SortOptions[{0}].Direction", i); 
    var directionID = string.Format("SortOptions_{0}__Direction", i); 

<input type="hidden" name="@columnNameName" id="@columnNameID" value="@Model.SortOptions[i].ColumnName" /> 
<input type="hidden" name="@directionName" id="@directionID" value="@Model.SortOptions[i].Direction" /> 

} 
<input type="submit" value="Submit" /> 
@{Html.EndForm();} 

我已經通過代碼來確保模型在發送到視圖時包含期望值。我甚至通過查看視圖中的代碼來檢查列表的值。它似乎有正確的值,但是當我在瀏覽器中查看它時,它具有應該與頁面響應GET請求時相對應的值。這是編輯器模板的問題嗎?我剛開始使用mvc3和剃鬚刀引擎,所以有很多我不知道。任何幫助,將不勝感激。

-----更新:新增控制器代碼----

[HttpGet] 
    public ActionResult Index() 
    { 
     var inv = new InventoryEntities(); 
     var model = new IndexModel(inv); 
     model.SortOptions = new List<SortOption>(); 
     model.SortOptions.Add(new SortOption { ColumnName = "Model", Direction = SortDirection.Ascending }); 
     model.SortOptions.Add(new SortOption { ColumnName = "Make", Direction = SortDirection.Ascending }); 
     //Load data 
     model.LoadEquipmentList(); 

     return View(model); 
    } 


    [HttpPost] 
    [OutputCache(Duration = 1)] 
    public ActionResult Index(List<SortOption> sortOptions, SortOption sort) 
    { 
     var inv = new InventoryEntities(); 
     var model = new IndexModel(inv); 
     ModelState.Remove("SortOptions"); 
     model.SortOptions = new List<SortOption>(); 
     model.SortOptions.Add(new SortOption { ColumnName = "Type", Direction = SortDirection.Descending }); 
     model.SortOptions.Add(new SortOption { ColumnName = "SubType", Direction = SortDirection.Descending }); 
     model.EquipmentList = new List<EquipmentListItem>(); 
     model.EquipmentList.Add(new EquipmentListItem { ID = 3, AssignedTo = "Mike", Location = "Home", Make = "Ford", Model = "Pinto", Selected = false, SubType = "Car", Type = "Vehicle" }); 

     return View(model); 
    } 
+0

你能發佈控制器操作代碼嗎? – sarvesh 2011-04-09 00:30:06

+0

現在發佈控制器代碼。 – m9k5j 2011-04-11 18:47:23

回答

0

請記住,Html幫助程序(如TextBoxFor)在綁定值和模型之後首先使用模型狀態。讓我們考慮以一個非常簡單的例子來說明這是什麼意思:

public class HomeController : Controller 
{ 
    public ActionResult Index() 
    { 
     return View(new MyViewModel { Name = "foo" }); 
    } 

    [HttpPost] 
    public ActionResult Index(MyViewModel model) 
    { 
     model.Name = "bar"; 
     return View(model); 
    } 
} 

和視圖:

@model MyViewModel 
@using (Html.BeginForm()) 
{ 
    @Html.TextBoxFor(x => x.Name) 
    <input type="submit" value="OK" /> 
} 

現在,當您提交表單,你會想到的是,在文本框變爲"bar"值因爲這是您在POST操作中所做的,但值不會改變。這是因爲模型狀態下的密鑰Name已經包含用戶輸入內容。所以,如果你想要這個工作,你需要從模型中取出狀態原值:

[HttpPost] 
public ActionResult Index(MyViewModel model) 
{ 
    // remove the original value if you intend to modify it here 
    ModelState.Remove("Name"); 
    model.Name = "bar"; 
    return View(model); 
} 

同樣的事情在您的情況同樣會發生。因此,您可能需要在POST操作中從模型狀態中刪除要修改的值。

+0

我試着用ModelState.Remove,沒有運氣。我得到相同的結果。我將使用兩種控制器方法的代碼更新我的帖子。 – m9k5j 2011-04-11 18:38:12

+0

好的,這基本上是問題所在。我仍然不完全理解模型狀態是如何工作的,但是如果我添加「ModelState.Clear();」在控制器方法的開始,它解決了這個問題。感謝您指點我正確的方向。 – m9k5j 2011-04-11 21:36:50

0

有兩件事情我蹦出來 - 沒有看到多一點很難說,但...這兩種可能如此重寫。額外的@符號不是必需的。

@using(Html.BeginForm()) { 
    Html.Encode("\n") 
    for (int i = 0; i < Model.SortOptions.Count; i++) { 
     Html.TextBoxFor(m => m.SortOptions[i].ColumnName); 
     Html.Encode("\n"); 
     Html.TextBoxFor(m => m.SortOptions[i].Direction); 
     Html.Encode("\n"); 
    } 
    <input type="submit" value="Submit" /> 
} 


@using (Html.BeginForm()) { 
    Html.Encode("\n"); 
    for (int i = 0; i < Model.SortOptions.Count; i++) { 
     var columnNameName = string.Format("SortOptions[{0}].ColumnName", i); 
     var columnNameID = string.Format("SortOptions_{0}__ColumnName", i); 
     var directionName = string.Format("SortOptions[{0}].Direction", i); 
     var directionID = string.Format("SortOptions_{0}__Direction", i); 

     <input type="hidden" name="@columnNameName" id="@columnNameID" value="@Model.SortOptions[i].ColumnName" /> 
     <input type="hidden" name="@directionName" id="@directionID" value="@Model.SortOptions[i].Direction" /> 

    } 
    <input type="submit" value="Submit" /> 
} 

否則你的東西看起來是正確的,我看不出我的頭頂上有什麼錯。

+0

感謝您使用@提示。我已經爲兩個項目使用了MVC2,但這是第一個使用MVC3和剃鬚刀的項目。 – m9k5j 2011-04-11 18:49:58