我有一个嵌套的列表视图,目标是从外部列表视图中提取ID并将其作为CurrentCategoryId
传递给下面的方法。这将允许我的第二个列表视图正确填充。根据我的阅读,这应该使用事件处理程序OnItemDataBound
完成,但我无法理解它是如何工作的?
如果您有任何疑问,请与我们联系
<asp:ListView ID="ListView1"
ItemType="E_Store_Template.Models.Category"
runat="server"
SelectMethod="GetCategories"
OnItemDataBound="brandList_ItemDataBound">
<ItemTemplate>
<ul>
<li style="list-style-type: none; text-align: left;">
<b style="font-size: large; font-style: normal">
<a href="<%#: GetRouteUrl("ProductsByCategoryRoute", new {categoryName = Item.CategoryName}) %>">
<%#: Item.CategoryName %>
</a>
<asp:ListView ID="brandList" runat="server" ItemType="E_Store_Template.Models.Brand">
<ItemTemplate>
<ul style="list-style-type: none; text-align: left;">
<li>
<a href="<%#: GetRouteUrl("ProductsByCatBrandRoute", new {brandName = Item.BrandName}) %>">
<%#: Item.BrandName %>
</a>
</li>
</ul>
</ItemTemplate>
</asp:ListView>
</b>
</li>
</ul>
</ItemTemplate>
</asp:ListView>
我认为事件处理程序需要看起来像这样
protected List<Brand> brandList_ItemDataBound(object sender, ListViewItemEventArgs e)
{
ListViewDataItem dataItem = (ListViewDataItem)e.Item;
if (e.Item.ItemType == ListViewItemType.DataItem)
{
Category mydata = (Category)dataItem.DataItem;
int CurrentCategoryId = mydata.CategoryID;
var query = _db.Products.Where(p => p.Category.CategoryID == CurrentCategoryId).Select(p => p.Brand).Distinct();
return query.ToList<Brand>();
}
else
{
return null;
}
}
但是给了我错误:
'System.Collections.Generic.List<E_Store_Template.Models.Brand> E_Store_Template.SiteMaster.brandList_ItemDataBound(object, System.Web.UI.WebControls.ListViewItemEventArgs)' has the wrong return type
答案 0 :(得分:1)
ItemDataBound不是为返回数据而设计的,它旨在处理事件。在这种情况下,事件将呈现一个类别以及需要作为子事件发生的任何事情。正确的做法是从父项中获取子ListView并将数据绑定到它。标记:
<asp:ListView ID="categoryList" runat="server"
OnItemDataBound="brandList_ItemDataBound" ItemType="E_Store_Template.Models.Category" SelectMethod="GetCategories">
<LayoutTemplate>
<ul style="list-style-type: none;">
<asp:PlaceHolder runat="server" ID="itemPlaceholder" />
</ul>
</LayoutTemplate>
<ItemTemplate>
<li style="text-align: left;">
<b style="font-size: large; font-style: normal">
<a href="<%#: GetRouteUrl("ProductsByCategoryRoute", new {categoryName = Item.CategoryName}) %>">
<%#: Item.CategoryName %>
</a>
</b>
<asp:ListView ID="brandList" runat="server">
<LayoutTemplate>
<ul style="list-style-type: none; text-align: left;">
<asp:PlaceHolder runat="server" ID="itemPlaceholder" />
</ul>
</LayoutTemplate>
<ItemTemplate>
<li>
<a href="<%#: GetRouteUrl("ProductsByCatBrandRoute", new {brandName = Item.BrandName}) %>">
<%#: Item.BrandName %>
</a>
</li>
</ItemTemplate>
</asp:ListView>
</li>
</ItemTemplate>
</asp:ListView>
代码背后:
protected void brandList_ItemDataBound(object sender, ListViewItemEventArgs e)
{
ListViewDataItem dataItem = (ListViewDataItem)e.Item;
if (e.Item.ItemType == ListViewItemType.DataItem)
{
Category mydata = (Category)dataItem.DataItem;
int CurrentCategoryId = mydata.CategoryID;
var query = _db.Products.Where(p => p.Category.CategoryID == CurrentCategoryId).Select(p => p.Brand).Distinct();
ListView brandList = (ListView)e.Item.FindControl("brandList");
brandList.DataSource = query.ToList<Brand>();
brandList.DataBind();
}
}
我在PlaceHolders中添加了LayoutTemplates,因此ListView不会为每条记录重复标记。我还移动了结束标记,因为你不应该有一个块元素(无序列表)作为粗体标记集的子元素。
我会考虑在1(或2)个SQL查询中获取所有类别和品牌,然后通过适当的CategoryID过滤品牌数据列表。您可以将Brands数据列表存储为页面级变量,但不要将其加载到Session或ViewState中,只需在页面呈现期间将其加载。