3

我在 SQL Server 中有 2 个表。一张表是所有超级英雄的列表,另一张表是能力列表。当前,在运行时,子转发器应该只获取与父表相关的项目时获取表中的所有项目。在我的 aspx 页面上,我有一个嵌套的中继器,如下所示:

<asp:Repeater id="rptHero" runat="server" DataSourceID="sdsHeros" OnItemDataBound="rptHero_ItemDataBound">
    <ItemTemplate>
        <table>
            <tr>
            <td> <%# Eval("HeroName")%> </td>                        
                <asp:Repeater id="rptAbility" runat="server" >                 
                  <ItemTemplate>                     
                    <tr>
                        <td> <%# Eval("AbilityName")%> </td>                     
                    </tr>
                  </ItemTemplate>
               </asp:Repeater>               
            </tr>
        </table>
        <p>&nbsp;</p>            
    </ItemTemplate>
</asp:Repeater>
<asp:SqlDataSource ID="sdsHero" runat="server" ConnectionString="<%$ ConnectionStrings:SiteSqlServer2 %>" 
    SelectCommand="SELECT [num], [HeroName] FROM [Super_Heros]"></asp:SqlDataSource>
<asp:SqlDataSource ID="sdsAbility" runat="server" ConnectionString="<%$ ConnectionStrings:SiteSqlServer2 %>" 
    SelectCommand="SELECT [num], [AbilityName] FROM [Super_Ability]"></asp:SqlDataSource>

在我背后的代码中,我有:

protected void rptHero_ItemDataBound(object sender, RepeaterItemEventArgs e)
{
    if (e.Item.ItemType == ListItemType.Item || e.Item.ItemType == ListItemType.AlternatingItem)
    {
        DataRowView row = (DataRowView)e.Item.DataItem;

        Repeater nestedRepeater = e.Item.FindControl("rptAbility") as Repeater;
        nestedRepeater.DataSource = sdsAbility;
        nestedRepeater.DataBind();
    }
}

按照我们的优秀顾客在 Stack Overflow 上发布的示例 1示例 2,这应该可以工作,但是,我认为我跳过的部分是[num]父中继器与[HeroID]子中继器的比较,如 SQLJoin 中的。

4

1 回答 1

2

这是我最终得到的

<asp:Repeater id="repMenu1" runat="server" OnItemDataBound="repMenu1_ItemDataBound">
    <ItemTemplate>
        <table id="gradient-style">
        <tr>
            <th> <%#DataBinder.Eval(Container.DataItem, "Hero")%> </th>
        </tr>
        <asp:Repeater id="repMenu2" runat="server">
            <ItemTemplate>
                <tr>
                <td> <a href="ScoreGraphs.aspx?id=<%#DataBinder.Eval(Container.DataItem, "num")%>"> <%#DataBinder.Eval(Container.DataItem, "Abilities")%></a> </td>
                </tr>       
            </ItemTemplate>
        </asp:Repeater>
        </table>     
    </ItemTemplate>
</asp:Repeater>

在后面的代码中

protected void Page_Load(object sender, EventArgs e)
{
    GetSQLData();
}

//my custom function to get data and create relationship between 2 tables and 
//bind the data on page load so that when menu1 is databound, it will find the matching submenu       
//items in the database and bind them to the second (nested) repeater, 
//displaying the sub-menu items below the parent

protected void GetSQLData()
{
    using (SqlConnection conn1 = new SqlConnection(ConfigurationManager.ConnectionStrings["SiteSqlServer2"].ConnectionString))
    {
        conn1.Open();
        SqlDataAdapter cmd = new SqlDataAdapter(@"SELECT * FROM [Abilities]; SELECT * FROM [Heros]", conn1);
        DataSet ds = new DataSet();
        cmd.Fill(ds);
        ds.Relations.Add(new DataRelation("nestThem", ds.Tables[0].Columns["num"], ds.Tables[1].Columns["AbilityID"]));

        repMenu1.DataSource = ds;
        repMenu1.DataBind();
    }
}

//Binding the data
protected void repMenu1_ItemDataBound(object sender, RepeaterItemEventArgs e)
{
    DataRowView dv = e.Item.DataItem as DataRowView;
    if (dv != null)
    {
        Repeater repSubMenu = e.Item.FindControl("repMenu2") as Repeater;
        if (repSubMenu != null)
        {
            repSubMenu.DataSource = dv.CreateChildView("nestThem");
            repSubMenu.DataBind();
        }
    }
}

我发现这个解决方案既简单又干净。

于 2014-11-12T14:51:52.397 回答