我正在使用转发器来构建自定义表。但是,如果下一行巡视与前一行不匹配,我无法弄清楚如何使表显示小计。
类似的东西。
row1 tour1
row2 tour 1
tour1 subtotal
row3 tour2
row4 tour2
subtotal
total
<asp:Repeater ID="ParentRepeater" runat="server" DataSourceID="SqlDataSource1">
<HeaderTemplate>
<table border="1">
<tr>
<th>TOUR</th>
<th>THEME</th>
<th>ROUTE</th>
<th>DEPT</th>
</tr>
</HeaderTemplate>
<ItemTemplate>
<tr>
<td><%#Container.DataItem("tour")%></td>
<td align="center"><%#Container.DataItem("theme")%></td>
<td align="right"><%#Container.DataItem("route")%></td>
<td align="right"><%#Container.DataItem("dep7")%></td>
<asp:Repeater ID="ChildRepeater" runat="server"
DataSourceID="SqlDataSource2">
<HeaderTemplate>
<table border="1">
<tr>
<th>BOOKNO</th>
<th>PARTY</th>
<th>TOUR</th>
<th>THEME</th>
<th>ROUTE</th>
<th>DEPT</th>
<th>HOME</th>
<th>USERID</th>
</tr>
</HeaderTemplate>
<ItemTemplate>
<tr>
<td align="center"><%#Container.DataItem("bookno") %></td>
<td><%#Container.DataItem("party")%></td>
<td><%#Container.DataItem("tour")%></td>
<td align="center"><%#Container.DataItem("theme")%></td>
<td align="right"><%#Container.DataItem("route")%></td>
<td align="right"><%#Container.DataItem("dep7")%></td>
<td align="right"><%#Container.DataItem("home")%></td>
<td align="right"><%#Container.DataItem("userid")%></td>
</tr>
</ItemTemplate>
<FooterTemplate>
</table>
</FooterTemplate>
</asp:Repeater>
</tr>
</ItemTemplate>
<FooterTemplate>
</table>
</FooterTemplate>
</asp:Repeater>
背后的代码
Protected Sub ItemBound(ByVal sender As Object, ByVal args As RepeaterItemEventArgs)
If args.Item.ItemType = ListItemType.Item Then
Dim childRepeater As Repeater = DirectCast(args.Item.FindControl("ChildRepeater"), Repeater)
childRepeater.DataSource = SqlDataSource2
childRepeater.DataBind()
End If
End Sub
但是这会显示嵌套转发器中的所有数据,而不是与parentrepeater字段匹配的数据 例如tour,theme,dep7应该在子中继器中匹配
答案 0 :(得分:0)
首先,添加2个类字段:
private int _subTotal; // Not sure what you're summing but you
// wrote subtotal in your pseudo-output
private int _lastTourId;
在对转发器进行数据绑定之前重置这些字段:
_subTotal = 0;
_lastTourId = -1;
TourRepeater.DataBind();
创建单级转发器:
<asp:Repeater ID="TourRepeater" ...>
<HeaderTemplate>...<>
<ItemTemplate>
<tr>
Some columns with your tour data
</tr>
<PlaceHolder ID="SubTotalRow" ... />
</ItemTemplate>
<FooterTemplate>
<PlaceHolder ID="SubTotalRow" ... />
</FooterTemplate>
</asp:Repeater>
将此Repeater直接绑定到您的巡回数据,然后在OnItemDataBound事件处理程序中执行此操作(我将不得不使用c#):
void RepeaterItemDataBound(object source, RepeaterItemEventArgs e)
{
if (
e.Item.ItemType == ListItemType.Item ||
e.Item.ItemType == ListItemType.AlternatingItem // think you forgot this
)
{
var tour = e.Item.DataItem as Tour;
if (tour != null)
{
if (_lastTourId == -1) { _lastTourId == tour.TourId; } // To avoid subtotal row before first tour
if (tour.TourId != _lastTourId) // This is a new tour so insert a subtotal row for the previous tour
{
var subTotalRow = e.Item.FindControl("SubTotalRow") as PlaceHolder;
if (subTotalRow != null)
{
RenderSummaryRow(subTotalRow, _subTotal);
}
_subTotal = tour.SomeValueYouWantToAddToSubTotal;
}
else
{
_subTotal += tour.SomValueYouWantToAddToSubTotal;
}
_lastTourId = tour.TourId;
}
}
else if (e.Item.ItemType == ListItemType.Footer)
{
var subTotalRow = e.Item.FindControl("SummaryRow") as PlaceHolder;
if (summaryTotalRow != null)
{
RenderSummaryRow(subTotalRow, _subTotal);
}
}
}
private void RenderSummaryRow(PlaceHolder placeHolder, int subTotal)
{
// create subtotal row manually by either creating TableRow + TableCells and adding them to a placeholder, or
// just add a literal and create your markup manually as innerHtml. Put your _subtotal value in where you want
}
另一种方法是将您的巡演数据检索到DataTable中,并检索WITH ROLLUP等数据,这将自动创建汇总行。网上有几个关于这方面的教程,但是在我切换到MVC之前,我找不到一个很好用的。