我有这堂课:
public class SortOrderModel
{
public string IdSort { get; set; }
public List<ContentPage> ContentPages { get; set; }
}
具有listpropery的上述类是此类的列表:
public class ContentPage
{
public string Id { get; set; }
public string ParentReference { get; set; }
public string Title { get; set; }
public string SortOrder { get; set; }
}
让我们说我将SortOrderModel作为@model发送到视图。
在视图中:Model.ContentPages是一个包含5个ContentPage的List,其值为:
var home = new ContentPage()
{
Id = "ContentPages/1",
Title = "Home",
ParentReference = "/",
SortOrder = "0"
};
var about = new ContentPage()
{
Id = "ContentPages/2",
Title = "About",
ParentReference = "ContentPages/1",
SortOrder = "1"
};
var contactinfo = new ContentPage()
{
Id = "ContentPages/3",
Title = "ContactInfo",
ParentReference = "ContentPages/2",
SortOrder = "0"
};
var allProducts = new ContentPage()
{
Id = "ContentPages/4",
Title = "AllProducts",
ParentReference = "ContentPages/1",
SortOrder = "2"
};
var product1 = new ContentPage()
{
Id = "ContentPages/5",
Title = "Product1",
ParentReference = "ContentPages/4",
SortOrder = "0"
};
var product2 = new ContentPage()
{
Id = "ContentPages/6",
Title = "Product1",
ParentReference = "ContentPages/4",
SortOrder = "1"
};
如何使用for循环渲染具有这些值的树视图,所以它看起来像这样:
> Home
> About
> ContactInfo
> AllProducts
> Product1
> Product2
使用for循环非常重要,因为我将在带有@ Html.TextBoxFor的视图中使用它来获取SortOrder-Properties,这样我就可以更改每个对象的sortOrder值。据我所知,我需要使用for循环而不是foreach来使模型绑定工作,因为我将值发送到[HttpPost]方法。
这是我的尝试:
@model CMS_Affiliate_Web.Models.SortOrderModel
@{
string startPageId = "";
foreach (var pageId in Model.ContentPages.Where(o => o.Url == "/").Select(o => o.Id))
{
startPageId = pageId;
}
}
<ul>
<li>
<div>
@using (Html.BeginForm("SortOrderMenu", "secure", Model.ContentPages, FormMethod.Post))
{
@Html.HiddenFor(o => Model.IdSort)
var contentPages = Model.ContentPages.ToList();
for (int i = 0; i < contentPages.Count(); i++)
{
<ul>
@if (Model.ContentPages[i].Url == "/" || Model.ContentPages[i].ParentReference == startPageId)
{
<li>@Model.ContentPages[i].Title @Html.TextBoxFor(o => Model.ContentPages[i].SortOrder, new {@class = "sortBox"})</li>
}
else if (contentPages.Any(m => m.Id == contentPages[i].ParentReference))
{
<li style="padding-left: 80px; color: red;">@Model.ContentPages[i].Title @Html.TextBoxFor(o => Model.ContentPages[i].SortOrder, new {@class = "sortBox"})</li>
}
</ul>
}
<div class="activity-desk">
<input type="submit" value="Spara ny sortering" class="btn btn-primary" name="saveSliders" />
</div>
}
</div>
</li>
但它会像这样呈现,而不是我想要的:
> Home
> About
> AllProducts
> Product1
> Product2
> ContactInfo
EDIT!
@model Models.SortOrderModel
@{
ViewBag.Title = "SortOrderMenu";
Layout = "~/Views/Shared/_Layout.cshtml";
}
@helper RenderItems(string parentID, int indent = 0)
{
@Html.HiddenFor(o => Model.IdSort)
int index = ViewBag.ItemIndex ?? 0;
foreach (var contentPage in Model.ContentPages
.Where(p => p.ParentReference == parentID)
.OrderBy(p => p.SortOrder))
{
<li style="padding-left: @(indent)px; color: red;">
@Html.TextBoxFor(o => Model.ContentPages[index].Id)
@contentPage.Title
@Html.TextBoxFor(o => Model.ContentPages[index].SortOrder,
new {@class = "sortBox"})
</li>
ViewBag.ItemIndex = ++index;
@RenderItems(contentPage.Id, indent + 20)
;
index = ViewBag.ItemIndex;
}
}
@using (Html.BeginForm("SortOrderMenu", "secure", Model.ContentPages, FormMethod.Post))
{
@RenderItems("ContentPages/6401")
<div class="activity-desk">
<input type="submit" value="Spara ny sortering" class="btn btn-primary" name="saveSliders" />
</div>
}
编辑2 ---------------
@helper RenderItems(string parentID, int indent = 0)
{
@Html.HiddenFor(o => Model.IdSort)
int index = ViewBag.ItemIndex ?? 0;
foreach (var contentPage in Model.ContentPages
.Where(p => p.ParentReference == parentID)
.OrderBy(p => p.SortOrder))
{
<li style="padding-left: @(indent)px; color: red;">
@Html.TextBoxFor(o => Model.ContentPages[index].Id)
@contentPage.Title
@Html.TextBoxFor(o => Model.ContentPages[index].SortOrder,
new { @class = "sortBox" })
</li>
ViewBag.ItemIndex = ++index;
@RenderItems(contentPage.Id, indent + 20);
index = ViewBag.ItemIndex;
}
}
@using (Html.BeginForm("SortOrderMenu", "secure", Model.ContentPages, FormMethod.Post))
{
@RenderItems("/")
<div class="activity-desk">
<input type="submit" value="Spara ny sortering" class="btn btn-primary" name="saveSliders" />
</div>
}
ControllerMethods:
[HttpGet]
public ActionResult SortOrderMenu()
{
var allContentPages = RavenSession.Query<ContentPage>().ToList();
var sortOrderModel = new SortOrderModel();
sortOrderModel.ContentPages = allContentPages;
return View(sortOrderModel);
}
[HttpPost]
public ActionResult SortOrderMenu(SortOrderModel model)
{
foreach (var page in model.ContentPages)
{
var contPage = RavenSession.Load<ContentPage>(page.Id);
contPage.SortOrder = page.SortOrder;
RavenSession.SaveChanges();
}
return RedirectToAction("SortOrderMenu");
}
答案 0 :(得分:1)
你最终会得到以下递归助手:
@helper RenderItems(string parentID, int indent = 0)
{
foreach (var contentPage in Model.ContentPages
.Where(p => p.ParentReference == parentID)
.OrderBy(p => p.SortOrder))
{
var index = Model.ContentPages.IndexOf(contentPage);
<li style="padding-left: @(indent)px; color: red;">
@Html.TextBoxFor(o => Model.ContentPages[index].Id)
@contentPage.Title
@Html.TextBoxFor(o => Model.ContentPages[index].SortOrder,
new { @class = "sortBox" })
</li>
@RenderItems(contentPage.Id, indent + 20)
}
}
如需使用,只需在您的视图中调用它:
@RenderItems("/");
编辑: 或者,您可以使用隐藏输入和Model.ContentPages.Index作为名称来定义索引:
@helper RenderItems(string parentID, int indent = 0)
{
foreach (var contentPage in Model.ContentPages
.Where(p => p.ParentReference == parentID)
.OrderBy(p => p.SortOrder))
{
var index = Guid.NewGuid();
<input type="hidden" name="Model.ContentPages.Index" value="@(index)" />
<li style="padding-left: @(indent)px; color: red;">
@contentPage.Title
<input type="text" class="sortBox"
name="Model.ContentPages[@(index)].SortOrder"
value="@contentPage.SortOrder" />
</li>
@RenderItems(contentPage.Id, indent + 20)
}
}
More details about it in Phil Haack's great blog post about collection binding