Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to implement a lazy loaded Silverlight data grid without using paging

Using the Business Application template from the brand new released RIA Services, you can see lots of examples using the data grid on top of a DomainDataSource in combination with a DataPager. The properties PageSize and LoadSize can be used to adjust the amount of data to be displayed in one page and the data that is prefetched in the background.

Now I'd like to have a data grid with a scrollbar and no pager. The underlying DomainDataSource should load only the data that is diplayed in the grid. It should trigger another load, when the user scrolls down to items that are not yet in the data context. Is there any sample implementation how to do this?

like image 739
Marc Wittke Avatar asked May 25 '10 06:05

Marc Wittke


2 Answers

I've just published a couple of blog posts (Part 1, Part 2) that give my solution to this problem. I have also posted a sample to GitHub that implements my own take on the VirtualCollection concept (I don't know how this compares with Infragistics's control, because I haven't used that).

To show how easy it is to use, here are a few snippets from the sample. First, here's how you use VirtualCollection, the class that coordinates fetching the data:

public class MainViewModel : ViewModel
{
    private NetflixTitlesSource _source;

    public VirtualCollection<Title> Items { get; private set; }

    public MainViewModel()
    {
        _source = new NetflixTitlesSource();
        Items = new VirtualCollection<Title>(_source, pageSize: 20, cachedPages: 5);
    }

    protected override void OnViewLoaded()
    {
        Items.Refresh();
    }
}

In XAML you simply bind the Items property to the ItemsSource property of a ListBox or DataGrid

For each data source you must implement a VirtualCollectionSource. Here's what the two key methods of NetflixTitlesSource look like:

public class NetflixTitlesSource : VirtualCollectionSource<Title>
{
    protected override Task<int> GetCount()
    {
        return GetQueryResults(0, 1, null)
            .ContinueWith(t => (int)t.Result.TotalCount, TaskContinuationOptions.ExecuteSynchronously);
    }

    protected override Task<IList<Title>> GetPageAsyncOverride(int start, int pageSize, IList<SortDescription> sortDescriptions)
    {
        return GetQueryResults(start, pageSize, sortDescriptions)
            .ContinueWith(t => (IList<Title>)((IEnumerable<Title>)t.Result).ToList(), TaskContinuationOptions.ExecuteSynchronously);
    }

    private Task<QueryOperationResponse<Title>> GetQueryResults(int start, int pageSize, IList<SortDescription> sortDescriptions)
    {
        // code to query the Netflix OData API
    }
}
like image 127
Samuel Jack Avatar answered Oct 09 '22 12:10

Samuel Jack


Check out the work that Bea Stollnitz has done on her blog. Although not a direct answer to your question, she has written quite a bit on UI and data visualization. Here are a link from her blog that I think might help to get you started:

Data virtualization: http://bea.stollnitz.com/blog/?p=344

HTH!
Chris

like image 26
Chris Koenig Avatar answered Oct 09 '22 13:10

Chris Koenig