LINQ - Linq with DataRepeater controls - Asked By Mitch Bird on 16-Sep-11 03:09 PM

Earn up to 40 extra points for answering this tough question.

This is kind of an advanced Winforms/VB.Net question but it is also a LINQ question...

I have this datarepeater control and it has a nested datarepeater control.
I have pulled the data as a Linq to SQL query.
I have run the query and created a loop to push to the Console to validate that I am getting the correct results and that looks good.
It isn't really a parent child relation I am trying to show so much as a set of series.
The objects are coming from a pretty normalized db and so they already have about six joins per record.

Anyways, here is my problem:
When the data is loaded, I see the records in the first repeater just fine. The second repeater takes it's data from 'ShortageRecsDetail' object within each record but all it ever shows is the first 'record' of that object even though a for each loop can get to them all.


I have tried this with a pair of linq statements and even datatables but still all I see is the first value repeated out in the second datarepeater.

Here is the LINQ:

Dim ShortageRecs = (From a In context.Requirements _
    Where (a.Part.LKP_ProgramCode.ProgramCodeID = inprogramcodeid _
          And a.LineNumber.LineNumberID = inlinenumberid) _
    Select a.Part.PartNumber, a.Part.PartID, a.Part.LKP_ProgramCode.ProgramCodeID, _
    a.LineNumber.LineNumberID, a.LineNumber.LineNumber, a.Part.LKP_Position.PositionName, _
    a.Part.CatalogNumber, a.Part.Description, _
    a.Part.LKP_PartType.TypeCode, a.Part.User.LoginID, _
    Surveillance = a.Part.User.UserID, _
    BuyerCode = a.PO.BuyerID, _
    SupplierCode = a.PO.SupplierID, a.PO.PONumber, _
    a.Part.CriticalToLoad, a.Part.Ignore, a.Confirmed, _
    a.QtyRequired, a.RequiredDate, a.OrderExpectedDate, _
    a.Comment, ShortageRecDetails = _
    (From d In context.Requirements _
      Where unitnumbers.Contains(d.LineNumberID) _
      And unitnumbers.Contains(d.LineNumber.LineNumberID) _
      And d.Part.LKP_ProgramCode.ProgramCodeID = GlobalProgramID _
      And d.Part.PartID = a.Part.PartID _
      Select srdRequirementID = d.RequirementID, srdLineNumberID = d.LineNumberID, _
      srdLineNumber = d.LineNumber.LineNumber, _
      srdRequiredDate = d.RequiredDate, _
      srdOrderExpectedDate = d.OrderExpectedDate, srdPONumber = d.PO.PONumber) _
     Order By LineNumberID Ascending Order By PartNumber Ascending)
Devil Scorpio replied to Mitch Bird on 20-Sep-11 02:41 PM
Hi,
 
PLease find the example of linq with DataRepeated control

C# Code

To begin with open Visual Studio 2008 and choose File > New > Web > ASP.NET Web Application. The first thing to do is to create a class that will be the structure of our data. Add a new class to the project and name it People. Add the following code to the People class:
 
public class People
{
public int UniqueId { get; set; }
    public string GivenName { get; set; }
    public string Surname { get; set; }
    public int Height { get; set; }
    public int ShoeSize { get; set; }
    public int Age { get; set; }     
}

This code needs to be set when an item is bound to the repeater. Add the following ItemDataBound code:
 
protected void rptPeople_ItemDataBound(object sender, RepeaterItemEventArgs e)
{
if (e.Item.ItemType != ListItemType.Item && e.Item.ItemType != ListItemType.AlternatingItem)
    {
        return;
}
RadioButton rdo = e.Item.FindControl("rdoSelected") as RadioButton;
    string script = "SetUniqueRadioButton('rptPeople.*Person',this)";
    rdo.Attributes.Add("onclick", script);
}

That will ensure the user can only select one radio button at a time, which is normal functionality. To add data to the people class, add the following code to the page load event:
 
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
    {
        List<People> people = new List<People>();
        people.Add(new People()
        {
          GivenName = "Malcolm",
          Surname = "Sheridan",
          Age = 32,
          Height = 185,
          ShoeSize = 13,
          UniqueId = 1
});
        people.Add(new People()
        {
          GivenName = "Suprotim",
          Surname = "Argawal",
          Age = 28,
          Height = 175,
          ShoeSize = 10,
          UniqueId = 2
});
       rptPeople.DataSource = people;
        rptPeople.DataBind();
}     
}

Reference :- http://www.geekpedia.com/PageView2968_LINQ-and-the-ASPNET-Repeater-control.html
Mitch Bird replied to Devil Scorpio on 25-Sep-11 10:24 AM
Thanks for the reply, Devil ... and by the way, how is dad? just kidding.
I am Winforms/VB.Net on this so your answer is of limited use.
Plus it doesn't answer any of my fundie questions... but thanks anyways.

I got it figured out ... even though the documentation on the web is ridiculous; either it is a 'simple use' example or it relies on four or five OLE DB adapter manager things... didn't want that.

The answer involved setting the second 'nested repeater' to virtual mode.
Then when the first repeater's Draw_item event (which in case anyone wants to know IS the meat in the biscuit) goes off, I populate those fields and then using a tricky syntax a DirectCasts and Parent refs get to the nested repeater's DataRepeaterItem objects, loop through and populate them. One has to set the number of those items manually (which fires off the second repeater's draw_item event and which I found it better to ignore).

I never did get the horizontal scroll on the nested repeater to work (the items would get out of order and although there may have been a way to fix that I never found it) and so I just created a means of calculating how many 'fit' on the user's screen dimensions and built my own custom 'paging' functionality into the form which basically tracks how many fit, what is the first item being currently displayed, and filters my results set with a LINQ skip/take rebuilding the form when they click my 'scroll/nav' buttons. 

I am led to believe by some of the things that I have read, now, on the web that the reason there are no advanced examples out there is because the control is not reliable in any kind of advanced scenario. 
Anyone looking to create such a usage may be well served by creating a custom control.

One last thought. Much like VB6 control arrays are no longer needed because thay can be imitated using a List. Perhaps the functionailty of a datarepeater would be better imitated by using a a single column (or row) third party grid and populating it with some simple custom control. I am using the Infragistics controls and think that might not be too hard to do... 

Anyways, thanks. Consider this one answered.