This is a migrated thread and some comments may be shown as answers.

[Solved] DistinctValuesLoading for a Custom FilterControl

3 Answers 485 Views
GridView
This is a migrated thread and some comments may be shown as answers.
This question is locked. New answers and comments are not allowed.
Sim
Top achievements
Rank 1
Sim asked on 16 Dec 2010, 05:39 PM
I have a custom FilterControl (implements IFilterControl) that I am using with a RadGridView. Can I hook into the Grid's DistinctValuesLoading event to load values when filtering? In essence, can I raise the Grid's DistinctValuesLoading in the Prepare method and get the results back? I am trying to create a generic filter control for my application and would like to avoid having to hook up a custom event to load the distinct values each time.

3 Answers, 1 is accepted

Sort by
0
Rossen Hristov
Telerik team
answered on 17 Dec 2010, 01:42 PM
Hi sim,

I can't see the logic behind this.

The DistinctValuesLoading event is for people that use the stock FilteringControl and want to change the list of distinct values it show.In other words, this is their only chance to alter the values that the stock control will display. You can't (and should not) raise this event by force from the outside.

Now, since you have your very own filtering control you are its "master and commander" and you can fill it up with anything that you want. Your control can call the public method of RadGridView called GetDistinctValues by passing in the column which you want the values for. This method will do the job of obtaining the distinct values and provide them for you. You can then choose what to do with them.

I hope this makes sense.

Regards,
Ross
the Telerik team
Browse the videos here>> to help you get started with RadControls for Silverlight
0
Sim
Top achievements
Rank 1
answered on 17 Dec 2010, 04:32 PM
Hi Ross,

Thanks for the reply. The GetDistinctValues on the RadGridView seems like what I am looking for, but it does not raise the OnLoadDistinctValues event on the grid. The issue with this is that I am doing custom paging on the server, and I want to load the distinct values from the database. This works fine for the built in FilterControl, except that the built-in control only filters data on the client-side. Which is why I have resorted to building my own FilterControl so I can both load distinct values from the database and perform filtering on the database (via a WCF service call).

I actually have the code working to retrieve the values, but I don't like how I have hooked up the code to execute. Maybe you can provide a better solution? In my project I am using the MVVM pattern and the MVVM light toolkit's EventToCommand to hook up events from the grid to my view model class. I can hook into other events on the RadGridView (such as LoadDistinctValues and Filtering), but not hooking into "Loaded" as such:

<telerik:RadGridView Name="EmailsGridView" ItemsSource="{Binding PagedEmails}" AutoGenerateColumns="False" IsReadOnly="True">
    <i:Interaction.Triggers>
        <i:EventTrigger EventName="Loaded">
            <cmd:EventToCommand Command="{Binding GridViewLoaded}" /> <!-- THIS DOESN'T WORK -->
        </i:EventTrigger>
    </i:Interaction.Triggers>
</telerik:RadGridView>

The event does not get hooked up to the GridViewLoaded command on my view model. Also, the OrigionalSource on the RoutedEventArgs is null, so I cannot access the grid object from my view model. What I want to do is for any columns that have a GenericFilterControl (my custom FilterControl class), I want to setup the DistinctValuesLoading and ApplyFilter events. Here is the code below:

private void EmailsGridView_Loaded(object sender, RoutedEventArgs args)
{
    var viewModel = DataContext as EmailLogViewModel;
    var grid = sender as RadGridView;
 
    if (grid != null && viewModel != null)
    {
        foreach (var column in grid.Columns)
        {
            var boundColumn = column as GridViewBoundColumnBase;
            if (boundColumn != null)
            {
                if (boundColumn.FilteringControl != null)
                {
                    var filterControl = boundColumn.FilteringControl as GenericFilterControl;
                    if (filterControl != null)
                    {
                        SetupGenericFilterControl(filterControl, viewModel, boundColumn);
                    }
                    // else, this is a custom filter control and we don't want to mess with it
                }
            }
        }
    }
}
 
private void SetupGenericFilterControl(GenericFilterControl filterControl, EmailLogViewModel viewModel, GridViewBoundColumnBase column)
{
    filterControl.DistinctValuesLoading += new EventHandler<MyGridViewDistinctValuesLoadingEventArgs>(
        (s, e) =>
        {
            viewModel.OnCustomLoadDistinctValues(e);  // NOTE: really don't like this line
        }
        );
 
    filterControl.ApplyFilter += (s, e) =>
    {
        viewModel.ClearFilters(column.DataMemberBinding.Path.Path);
        viewModel.AddFilters(e.Filters);
        viewModel.LoadData();
    };
}

I am currently hooking up the RadGridView's Loaded event in the code-behind of my page, which for MVVM I would rather not do. Also, I am firing the view model's LoadDistinctValues event to trigger the loading, which again I don't want to do from the page.

One final thing I have tried is to hook up the events of the custom FilteringControl directly in the XAML as such:

<telerik:GridViewDataColumn Header="From" DataMemberBinding="{Binding FromDisplayName}" Width="200" >
    <telerik:GridViewDataColumn.FilteringControl>
        <controls:GenericFilterControl>
            <i:Interaction.Triggers>
                <i:EventTrigger EventName="DistinctValuesLoading">
                    <cmd:EventToCommand Command="{Binding EmailLogViewModel.CustomLoadDistinctValues, Source={StaticResource Locator}}" PassEventArgsToCommand="True" />
                </i:EventTrigger>
            </i:Interaction.Triggers>
        </controls:GenericFilterControl>
    </telerik:GridViewDataColumn.FilteringControl>                       
</telerik:GridViewDataColumn>

Because of when the custom filtering control gets created, this hook up fails the first time the filter control is displayed. When the filter button is clicked the 2nd time for the column, the event hook up works and the values are loaded.

I know this is a bit long, but I appreciate your help on this. I have tried quite a few different ways of doing this. I know that in my custom filter control I can essentially do whatever I want, but I want a generic reusable control for my application. Essentially I want to delegate tasks to the page (and ultimately the view model). I am a bit new to MVVM and the Telerik controls, so maybe I am approaching this wrong or am missing the obvious.

Thanks.
Sim
0
Rossen Hristov
Telerik team
answered on 20 Dec 2010, 10:42 AM
Hello sim,

Here is how things currently stand:

1. You can't force the grid to fire an event. This is internal logic and you have no access to it. We do not plan to change this since it will not be correct.

2. The Custom Filtering Control feature was provided to solve a very wide array of user cases. I guess that your requirements can't be met by this feature.

I have a blog post that does server-side filtering. You can take a look at it. Maybe this blog can help you.

This week we will release a new control called RadDomainDataSource. RadGridView, RadDataPager and RadDataFilter will automatically integrate with RadDomainDataSource without any code required. In other words, when you filter with RadGridView's built-in FilteringControl the filtering will be automatically performed on the server.

This is all we can offer right now.

I hope this helps.

Regards,
Ross
the Telerik team
Browse the videos here>> to help you get started with RadControls for Silverlight
Tags
GridView
Asked by
Sim
Top achievements
Rank 1
Answers by
Rossen Hristov
Telerik team
Sim
Top achievements
Rank 1
Share this question
or