New to Telerik UI for BlazorStart a free 30-day trial

Custom Sorting Order for Groups in DropDownList

Environment

ProductDropDownList for Blazor,
AutoComplete for Blazor,
MultiSelect for Blazor,
ComboBox for Blazor,
MultiColumnComboBox for Blazor

Description

I am using the grouping feature of the DropDownList. My DropDownList model has a nested model as property. The DropDownList GroupField parameter is bound to a property of the nested model. I want the groups to appear in a non-alphabetical, custom order. I can see that there is a feature request to add a sort direction option when grouping. But in the meantime how can I customize the grouping order in the DropDownList?

Solution

To sort the groups in a DropDownList by a custom order, perform a manual sorting operation in the OnRead event handler. Follow these steps:

  1. Create a list of strings that represents the values of the group headers. This list will determine the preferred sorting order.
  2. Cast the DataSourceResult to AggregateFunctionsGroup.
  3. Sort the casted data using the Sort method with a custom comparison function.
  4. Pass the sorted data as args.Data.

Apply a custom grouping order in the DropDownList

@using Telerik.DataSource.Extensions
@using Telerik.DataSource

<TelerikDropDownList TItem="@Product"
                     TValue="@int"
                     OnRead="@ReadItems"
                     @bind-Value="@SelectedValue"
                     GroupField="ProductCategory.CategoryName"
                     TextField="@nameof(Product.Description)"
                     ValueField="@nameof(Product.ProductId)"
                     DefaultText="Select a Product">
</TelerikDropDownList>

@code {
    private int SelectedValue { get; set; }
    private List<Product> Products = new List<Product>
        {
            new Product { ProductId = 10, Description = "Juliet Jewelery Product", ProductCategory = new ProductCategory { CategoryId = 10, CategoryName = "Jewelery" } },
            new Product { ProductId = 18, Description = "Medical Care Product", ProductCategory = new ProductCategory { CategoryId = 8, CategoryName = "Healthcare" } },
            new Product { ProductId = 19, Description = "QQ Tech Product", ProductCategory = new ProductCategory { CategoryId = 9, CategoryName = "Information Technology" } },
            new Product { ProductId = 10, Description = "Z Jewelery Product", ProductCategory = new ProductCategory { CategoryId = 10, CategoryName = "Jewelery" } },
            new Product { ProductId = 4, Description = "Delta Bond Product", ProductCategory = new ProductCategory { CategoryId = 4, CategoryName = "Defense" } },
            new Product { ProductId = 8, Description = "Health Care Product", ProductCategory = new ProductCategory { CategoryId = 8, CategoryName = "Healthcare" } },
            new Product { ProductId = 9, Description = "Tech Product", ProductCategory = new ProductCategory { CategoryId = 9, CategoryName = "Information Technology" } }
        };

    protected async Task ReadItems(DropDownListReadEventArgs args)
    {
        await Task.Delay(200);

        var preferredOrder = new List<string> { "Healthcare", "Information Technology", "Defense", "Jewelery" };

        var datasourceResult = Products.ToDataSourceResult(args.Request);

        var sortedData = datasourceResult.Data.Cast<AggregateFunctionsGroup>().ToList();
        sortedData.Sort((a, b) =>
        {
            int indexA = preferredOrder.IndexOf(a.Key.ToString());
            int indexB = preferredOrder.IndexOf(b.Key.ToString());

            if (indexA >= 0 && indexB >= 0)
            {
                return indexA.CompareTo(indexB);
            }

            if (indexA >= 0) return -1;
            if (indexB >= 0) return 1;
            return a.Key.ToString().CompareTo(b.Key.ToString());
        });

        args.Data = sortedData;
    }

    public class Product
    {
        public int ProductId { get; set; }
        public string Description { get; set; }
        public ProductCategory ProductCategory { get; set; }
    }

    public class ProductCategory
    {
        public int CategoryId { get; set; }
        public string CategoryName { get; set; }
    }
}

See Also