J'ai un répéteur à l'intérieur d'un répéteur. Où le répéteur parent est lié à une Datatble
qui contient une colonne avec une Datatable
.
Je voudrais lier le répéteur enfant à la colonne datatable du datarow du répéteur parent
Est-ce possible? Je pensais pouvoir le faire directement dans le fichier aspx
comme:
DataSource="<%# DataBinder.Eval(Container.DataItem, "Products")%>"
mais cela ne semble pas fonctionner.
Dans le répéteur parent, attachez une méthode à l'événement OnItemDataBound et dans la méthode, recherchez le répéteur imbriqué et liez-le par les données.
Exemple (.aspx):
<asp:Repeater ID="ParentRepeater" runat="server" OnItemDataBound="ItemBound">
<ItemTemplate>
<!-- Repeated data -->
<asp:Repeater ID="ChildRepeater" runat="server">
<ItemTemplate>
<!-- Nested repeated data -->
</ItemTemplate>
</asp:Repeater>
</ItemTemplate>
</asp:Repeater>
Exemple (.cs):
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
{
ParentRepeater.DataSource = ...;
ParentRepeater.DataBind();
}
}
protected void ItemBound(object sender, RepeaterItemEventArgs args)
{
if (args.Item.ItemType == ListItemType.Item || args.Item.ItemType == ListItemType.AlternatingItem)
{
Repeater childRepeater = (Repeater)args.Item.FindControl("ChildRepeater");
childRepeater.DataSource = ...;
childRepeater.DataBind();
}
}
J'ajouterais un événement DataBinding au répéteur enfant lui-même:
<asp:Repeater ID="parentRepeater" runat="server">
<asp:Repeater ID="childRepeater" runat="server"
OnDataBinding="childRepeater_DataBinding" />
</asp:Repeater>
Ensuite, implémentez-le:
protected void childRepeater_DataBinding(object sender, System.EventArgs e)
{
Repeater rep = (Repeater)(sender);
int someIdFromParentDataSource = (int)(Eval("ParentID"));
// Assuming you have a function call `GetSomeData` that will return
// the data you want to bind to your child repeater.
rep.DataSource = GetSomeData(int);
rep.DataBind();
}
Je préfère le faire au niveau du contrôle plutôt qu'au niveau ItemDataBound
afin que, si vous devez supprimer des contrôles ou des éléments dans vos modèles, vous n'avez pas à vous soucier de la recherche de code dans les contrôles parents qui l'utilisent. Tout est localisé avec le contrôle de lui-même. De plus, vous n’avez jamais à faire une FindControl
.
Si vous souhaitez remplacer un contrôle ultérieurement, vous pouvez simplement le supprimer et votre code fonctionnera toujours, car il est entièrement autonome. L'utilisation de ItemDataBound
entraînerait la compilation de votre code, mais elle planterait ou agirait de manière inattendue au moment de l'exécution, en raison de sa dépendance à l'égard des contrôles enfants.
Voici comment c'est fait:
DataSource='<%# ((System.Data.DataRowView)Container.DataItem)[3] %>'
Ainsi, si vous connaissez la colonne de la table parent qui contient la table enfant/source de données pour le répéteur imbriqué, vous pouvez l'insérer directement dans le fichier aspx.
Repeater1 OnItemDataBound, puis FindControl Repeater2. Le code-behind ne trouvera pas le Repeater2 imbriqué! Vous devez utiliser FindControl ("Repeater2").
protected void Repeater1_ItemDataBound(object sender, RepeaterItemEventArgs e)
{
if (e.Item.DataItem != null)
{
MemberView dataRow = (MemberView)e.Item.DataItem;
var cat = MemberPresenter.getMemberID(dataRow.memID);
Repeater rp2 = (Repeater)e.Item.FindControl("Repeater2");
rp2.DataSource = cat;
rp2.DataBind();
}
}
Si j'ai besoin de le faire, je le fais généralement en utilisant l'événement ItemDataBound du répéteur parent pour lier le répéteur enfant. Si e est votre paramètre EventArgs, vous aurez accès au répéteur enfant via e.Item.FindControl () et aux données via e.Item.DataItem.
Voici un exemple de procédure: Article pour le contrôle de répéteur imbriqué
protected void MainRepeater_ItemDataBound(object sender, RepeaterItemEventArgs args)
{
if (args.Item.ItemType == ListItemType.Item || args.Item.ItemType == ListItemType.AlternatingItem)
{
Repeater childRepeater = (Repeater)args.Item.FindControl("ChildRepeater");
DataTable innerTable= ((DataRowView)args.Item.DataItem)["InnerTableColumnName"] as DataTable;
childRepeater.DataSource = tasksDetails;
childRepeater.DataBind();
}
}