在控制器与视图之间传递数据
若要呈现视图,则可以调用控制器的 View 方法。若要向视图传递数据,则可以使用 ViewPage 类的 ViewData 属性。此属性将返回一个具有不区分大小写的字符串密钥的ViewDataDictionary 对象。若要向视图传递数据,则可以为字典赋值,如以下示例所示
List<string> petList = new List<string>(); petList.Add("Dog"); petList.Add("Cat"); petList.Add("Hamster"); petList.Add("Parrot"); petList.Add("Gold fish"); petList.Add("Mountain lion"); petList.Add("Elephant"); ViewData["Pets"] = new SelectList(petList);
如果调用不含参数的 View 方法(如前面的示例所示),则控制器对象的 ViewData 属性将传递给与操作方法同名的视图。
在视图页中,您可以访问 ViewData 属性以获得已传递给视图的数据。 ViewData 属性是一个支持索引器的字典,该索引器可接受字典密钥。
下面的示例演示某个视图的标记,该视图在 HTML 窗体中显示数据并使用户能够修改值和做出选择。
<h2><%= Html.Encode(ViewData["Message"]) %></h2> <br /><br /> <% using(Html.BeginForm("HandleForm", "Home")) %> <% { %> Enter your name: <%= Html.TextBox("name") %> <br /><br /> Select your favorite color:<br /> <%= Html.RadioButton("favColor", "Blue", true) %> Blue <br /> <%= Html.RadioButton("favColor", "Purple", false)%> Purple <br /> <%= Html.RadioButton("favColor", "Red", false)%> Red <br /> <%= Html.RadioButton("favColor", "Orange", false)%> Orange <br /> <%= Html.RadioButton("favColor", "Yellow", false)%> Yellow <br /> <%= Html.RadioButton("favColor", "Brown", false)%> Brown <br /> <%= Html.RadioButton("favColor", "Green", false)%> Green <br /><br /> <%= Html.CheckBox("bookType") %> I read more fiction than non-fiction.<br /> <br /><br /> My favorite pet: <%= Html.DropDownList("pets") %> <br /><br /> <input type="submit" value="Submit" /> <% } %>
在控制器与视图之间传递强类型数据
如果您使用 ViewPage 类的 ViewData 属性在视图与控制器之间传递数据,则该数据不是强类型数据。如果要传递强类型数据,请更改视图的 @ Page 声明,以便视图继承自ViewPage<TModel>,而不是继承自 ViewPage,如以下示例所示:
<%@ Page Inherits="System.Web.Mvc.ViewPage<MvcApplication1.Models.PersonTest>" %>
ViewPage<TModel> 是 ViewPage 的强类型版本。ViewPage<TModel> 的 ViewData 属性将返回 ViewDataDictionary<TModel> 对象,该对象包含基于模型的视图的强类型数据。该模型是一个类,其中包含要传递的每个数据项的属性。(比较简单的创建强类型视图页的方法是使用“添加视图”对话框。)
下面的示例演示名为 Person 的典型数据模型类的定义。
using System; using System.ComponentModel.DataAnnotations; namespace MvcApplication1.Models { public class PersonTest { [Required(ErrorMessage = "The Id is required.")] public int Id { get; set; } [Required(ErrorMessage = "The name is required.")] public string Name { get; set; } [Range(1, 200, ErrorMessage = "A number between 1 and 200.")] public int Age { get; set; } [RegularExpression(@"((\(\d{3}\) ?)|(\d{3}-))?\d{3}-\d{4}", ErrorMessage = "Invalid phone number.")] public string Phone { get; set; } [RegularExpression(@"^[\w-\.]+@([\w-]+\.)+[\w-]{2,4}$", ErrorMessage = "Invalid email address.")] public string Email { get; set; } } }
下面分别是使用了PersonTest模型类的视图和控制器代码。
<%@ Page Title="" Language="C#" MasterPageFile="~/Views/Shared/Site.Master" Inherits="System.Web.Mvc.ViewPage<MvcApplication1.Models.PersonTest>" %> <asp:Content ID="Content1" ContentPlaceHolderID="TitleContent" runat="server"> PersonTest </asp:Content> <asp:Content ID="Content2" ContentPlaceHolderID="MainContent" runat="server"> <fieldset> <legend>Person Info</legend> <p> Name: <%=Html.TextBox("Name") %> </p> <p> Age: <%=Html.TextBox("Age")%> </p> <p> Phone: <%=Html.TextBox("Phone")%> </p> <p> Email: <%=Html.TextBox("Email")%> </p> </fieldset> </asp:Content>
public ActionResult PersonTest() { Models.PersonTest p = new Models.PersonTest(); p.Name = "请输入您的姓名"; p.Age = 30; p.Phone = "12345678"; p.Email = "a@a.a"; return View(p); }
效果图:
在操作方法之间传递状态
操作方法可能必须向其他操作传递数据,例如如果发布窗体时出现错误或者方法必须重定向到其他方法,当用户重定向到登录视图然后返回到原始操作方法时可能出现这种情况。
操作方法可以先将数据存储在控制器的 TempDataDictionary 对象中,然后调用控制器的 RedirectToAction 方法以调用下一个操作。 TempData 属性值存储在会话状态中。在设置 TempDataDictionary 值后调用的任何操作方法都可以从对象中获取值,然后处理或显示这些值。 TempData 的值将持续存在,直至读取该值或会话超时。以此方式保存 TempData 将启用重定向等方案,因为 TempData 中的值不只在单个请求中可用。
注意:此行为是 ASP.NET MVC 2 中新增的。在 ASP.NET MVC 的早期版本中,TempData 中的值仅在下一请求之前可用。
下面的示例演示一个用于捕获错误并在操作之间传输数据的数据类。
public class InsertError { public string ErrorMessage { get; set; } public string OriginalFirstName { get; set; } public string OriginalLastName { get; set; } } public ActionResult NewCustomer() { InsertError error = TempData["error"] as InsertError; if (error != null) { // If there is error data from the previous action, display it. ViewData["FirstName"] = error.OriginalFirstName; ViewData["LastName"] = error.OriginalLastName; ViewData["ErrorMessage"] = error.ErrorMessage; } return View(); } public ActionResult InsertCustomer(string firstName, string lastName) { if (string.IsNullOrEmpty(firstName) || string.IsNullOrEmpty(lastName)) { InsertError error = new InsertError(); error.ErrorMessage = "Both names are required."; error.OriginalFirstName = firstName; error.OriginalLastName = lastName; TempData["error"] = error; return RedirectToAction("NewCustomer"); } return View(); }
下面的示例演示某个视图的标记,该视图可接受用户输入并在发生错误时显示错误消息。
<form action="InsertCustomer"> <p style="color:Red;"> <% if (ViewData["ErrorMessage"] != null) { %> The following error occurred while inserting the customer data: <br /> <%=ViewData["ErrorMessage"] %> <br /> <% } %> </p> <fieldset> <legend>New Customer</legend> <p> First Name: <input type="text" name="firstName" value="<%= ViewData["FirstName"] %>" /> </p> <p> Last Name: <input type="text" name="lastName" value="<%= ViewData["LastName"] %>" /> </p> <p> <input type="submit" value="Insert" /> </p> </fieldset> </form>