【发布时间】:2013-11-19 05:12:33
【问题描述】:
简单的问题,但我无法弄清楚缺少什么。我有一个简单的 ViewModel(它会变得更大):
public class TigerTrackingViewModel
{
public TigerTrackingViewModel()
{
this.TigerTrail = new TigerTrail();
}
public Guid YouthGuid { get; set; }
public string FirstName { get; set; }
public string LastName { get; set; }
public TigerTrail TigerTrail { get; set; }
}
TigerTrail 是一个嵌套对象。以下是所有属性和子属性:
public class TigerTrail
{
public TigerTrail()
{
DoneDate = new DateTime(1950, 01, 01);
TigerTrailRequiredBadges = new Collection<TigerTrailRequiredBadge>();
TigerTrailElectivedBadges = new Collection<TigerTrailElectiveBadge>();
}
[Key]
[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
public int Id { get; set; }
public string Name { get; set; }
public virtual ICollection<TigerTrailRequiredBadge> TigerTrailRequiredBadges { get; set; }
public virtual ICollection<TigerTrailElectiveBadge> TigerTrailElectivedBadges { get; set; }
//public virtual ICollection<Youth> Youth { get; set; }
public bool? Done { get; set; }
public DateTime? DoneDate { get; set; }
}
所以它有 TigerTrailRequiredBadges:
public class TigerTrailRequiredBadge
{
public TigerTrailRequiredBadge()
{
DoneDate = new DateTime(1950, 01, 01);
TigerTrailRequiredBadgeSubRequirements = new Collection<TigerTrailRequiredBadgeSubRequirement>();
}
[Key]
[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
public int Id { get; set; }
public string Name { get; set; }
public string Description { get; set; }
public virtual ICollection<TigerTrailRequiredBadgeSubRequirement> TigerTrailRequiredBadgeSubRequirements { get; set; }
public bool Done { get; set; }
public DateTime DoneDate { get; set; }
}
里面有 TigerTrailRequiredBadgeSubRequirement(s):
public class TigerTrailRequiredBadgeSubRequirement
{
public TigerTrailRequiredBadgeSubRequirement()
{
DoneDate = new DateTime(1950, 01, 01);
}
[Key]
[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
public int Id { get; set; }
public string Name { get; set; }
public string ShortCode { get; set; }
public string Type { get; set; } //Family, Den, Go See It
public string Description { get; set; }
public bool Done { get; set; }
public DateTime DoneDate { get; set; }
}
在 TigerTrail.cs 类中,还有 Elective Badge 类:
public class TigerTrailElectiveBadge
{
public TigerTrailElectiveBadge()
{
DoneDate = new DateTime(1950, 01, 01);
}
[Key]
[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
public int Id { get; set; }
public int Number { get; set; }
public string Name { get; set; }
public string Requirement { get; set; }
public bool Done { get; set; }
public DateTime DoneDate { get; set; }
}
所以所有的属性都可以通过我的 ViewModel 使用。不幸的是,大多数情况下都需要。它又大又丑,但我必须让它发挥作用。
在Controller GET方法中:
public ActionResult TigerTrail()
{
var vm = new List<TigerTrackingViewModel>();
var pack = Ctx.CubPacks.FirstOrDefault(x => x.Id == PackId);
var permTrail = Ctx.TigerTrails.FirstOrDefault(x => x.Name.Contains("PERM"));
foreach (var youth in pack.Youths)
{
//if anyone does not have this trail set up, make a new one.
if (youth.TigerTrail == null)
{
youth.TigerTrail = new TigerTrail();
if (youth.TigerTrail.TigerTrailElectivedBadges == null)
{
youth.TigerTrail.TigerTrailElectivedBadges = new Collection<TigerTrailElectiveBadge>();
}
if (youth.TigerTrail.TigerTrailRequiredBadges == null)
{
youth.TigerTrail.TigerTrailRequiredBadges = new Collection<TigerTrailRequiredBadge>();
}
youth.TigerTrail = permTrail;
}
youth.TigerTrail.Name = youth.FirstName + " " + youth.LastName + " Tiger Trail";
vm.Add(new TigerTrackingViewModel
{
FirstName = youth.FirstName,
LastName = youth.LastName,
YouthGuid = youth.YouthGuid,
TigerTrail = youth.TigerTrail
});
}
return View(vm);
}
在post方法中:
[HttpPost]
public ActionResult TigerTrail(List<TigerTrackingViewModel> youths)
{
return View();
}
回发每次都返回 null。这是视图:
@model List<eTrail.Cubs.ViewModels.TigerTrackingViewModel>
@{
ViewBag.Title = "Award Tracking";
Layout = "~/Areas/App/Views/Shared/_BackendDashboard.cshtml";
}
<h1>Award Tracking</h1>
<hr />
<div class="row">
<div class="span12">
@using (Html.BeginForm("TigerTrail", "Awards", FormMethod.Post, new { @class = "form-horizontal" }))
{
for (int i = 0; i < Model.Count; i++)
{
@Html.HiddenFor(x => Model[i].TigerTrail)
foreach (var item in Model[i].TigerTrail.TigerTrailElectivedBadges)
{
@Html.DisplayFor(x => item.Done)
@Html.DisplayFor(x => item.DoneDate)
@Html.DisplayFor(x => item.Id)
@Html.DisplayFor(x => item.Name)
@Html.DisplayFor(x => item.Number)
@Html.DisplayFor(x => item.Requirement)
}
}
<input type="submit" value="submit" />
}
</div>
</div>
我在整个过程中添加了所有 HiddenFor 字段,因为有人建议它们都需要在那里才能回发。仍然没有运气。如果我在页面上查看源代码,则 id/name(s) 会像这样显示:
<li>
<input id="elec_Done" name="elec.Done" type="checkbox" value="true"><input name="elec.Done" type="hidden" value="false">
<b>Pet Care</b>
Visit a veterinarian or animal groomer
<input id="elec_Number" name="elec.Number" type="hidden" value="43">
<input id="elec_DoneDate" name="elec.DoneDate" type="hidden" value="1/1/1950 12:00:00 AM">
</li>
翻译中丢失了什么?如何将列表返回给控制器?
编辑
基于赏金以来的两个答案,我需要澄清这一点:在 httppost 方法中,我应该收到的列表为空。
[HttpPost]
public ActionResult TigerTrail(List<TigerTrackingViewModel> youths) //this is what is null on postback.
{
. . . Do work with youths . .
return RedirectToAction(...);
}
【问题讨论】:
-
您的所有 Pack 属性都必须在表单内。隐藏或其他方式。
-
@SimonWhitehead 那么你会说什么是好的策略。包装模型相当大,我正在使用它的零碎部分,但不是全部。那么,a)创建一个只有这些项目的不同虚拟机,或者 b)在表单中抛出一堆隐藏字段?
-
创建一个仅包含您需要的字段的视图模型。然后在发布时,从您的数据库中加载当前状态,并从您的缩减视图模型中应用您的更改。
-
如果您试图获取所有要传回的数据,那么它们都需要隐藏起来。您显示的字段的显示不会传回(所有其他帮助者都会)。您不能将整个类放入 for 中。如果您希望tigertails 回发,您需要将每个属性放入for 中。发回 id 并重新查询可能更容易
标签: c# asp.net-mvc asp.net-mvc-4 asp.net-mvc-viewmodel