Skip to content

DevExpress-Examples/blazor-grid-runtime-conditional-formatting

Repository files navigation

Blazor Grid – Apply Conditional Formatting at Runtime

This example allows users to specify and apply conditional formatting rules at runtime. The format editor appears on-screen when a user right-clicks a column header. Once the user specifies required rules and styles, the CustomizeElement event applies desired styles to data cells.

Blazor Grid - Cells Formatted Based on a Condition

Implementation Details

Define Custom Styles

In the wwwroot/css folder, create a stylesheet to store CSS rules users can apply to Grid regions. We recommend the use of public design tokens when constructing styles. Review the following help topic for additional information in this regard: CSS Variables in Fluent Themes.

To review design token usage in this example, see the following file: conditional.format.css.

Implement a Format Object

  1. Create a SimpleFormat class to store the following information:

    This example allows users to specify the following condition types:

    • Build your own condition. This example uses a standalone Filter Builder component for the condition builder UI and then evaluates the resulting rule using the Filter Criteria API.
    • Cell value is greater than or less than the total summary (average).
    public enum ConditionType {
        Filter,
        GreaterThanTotalSummary,
        LessThanTotalSummary
    }
    
    public class SimpleFormat {
        public SimpleFormat(string columnFieldName, ConditionInfo condition, FormatStyleInfo? style) {
            FormatId = Guid.NewGuid().ToString();
            ColumnFieldName = columnFieldName;
            Condition = condition;
            Style = style;
        }
        public string FormatId { get; }
        public ConditionInfo Condition { get; set; }
        public FormatStyleInfo? Style { get; set; }
        public string ColumnFieldName { get; set; }
    }
  2. Evaluate whether the style should be applied to the current element based on the specified condition.

    public static bool Evaluate(SimpleFormat format, GridCustomizeElementEventArgs args) {
        switch(format.Condition.ConditionType) {
            case ConditionType.Filter:
                return EvaluateFilterCriteria(format, args);
            case ConditionType.GreaterThanTotalSummary:
                return EvaluateGreaterThanTotalSummary(format, args);
            case ConditionType.LessThanTotalSummary:
                return EvaluateLessThanTotalSummary(format, args);
            default:
                return false;
        }
    }

    Review the following file for implementation details: ConditionalFormatHelper.cs.

  3. In the SimpleFormat class, implement a method that calls the evaluation method and applies CSS rules.

    public class SimpleFormat {
        public void ApplyStyle(GridCustomizeElementEventArgs args) {
            bool isTargetDataCell = args.ElementType == GridElementType.DataCell && args.Column is IGridDataColumn column && column.FieldName == ColumnFieldName;
            if(isTargetDataCell) {
                bool shouldApply = ConditionalFormatHelper.Evaluate(this, args);
                if(shouldApply) {
                    if(!string.IsNullOrEmpty(args.CssClass))
                        args.CssClass += " ";
                    if(Style != null)
                        args.CssClass += Style.CssClassName;
                }
            }
        }
    }

Create a Format Selector Component

  1. Create a Razor component (the UI designed to configure conditions and styles).

  2. Check if specified conditions are valid.

  3. Process "Apply", "Cancel", and "Remove" operations. After each operation, invoke the FormatsChanged callback.

  4. Add the newly created component to the Index.razor page. In the FormatsChanged handler, call the StateHasChanged method to re-render the page after new styles are applied.

    <ConditionalFormatSelector @ref="formatSelectorRef"
                            TModel="GridItem"
                            Formats="@formats"
                            FormatsChanged="OnFormatsChanged"
                            FormatStyles="formatStyles" />
    
    @code {
        private void OnFormatsChanged() {
            StateHasChanged();
        }
    }

Review the following file for implementation details: ConditionalFormatSelector.razor.

Set Up a Grid

  1. Add a DxGrid to the Index.razor page and populate it with data.
  2. Add a TotalSummary that will be used as a reference value in summary-based conditions.
  3. Enable the Grid's context menu using the ContextMenus property.
  4. Handle the CustomizeContextMenu event to add custom items to the context menu (Conditional Formatting, Apply New Format, and Clear Formatting).
  5. Process context menu item clicks.
  6. Handle the CustomizeElement event to apply user-specified styles.
<DxGrid Data="@data"
        ContextMenus="GridContextMenus.All"
        CustomizeContextMenu="CustomizeContextMenu"
        CustomizeElement="OnCustomizeElement">
    <Columns>
        @* ... *@
    </Columns>
    <TotalSummary>
        <DxGridSummaryItem SummaryType="GridSummaryItemType.Avg" 
                           FieldName="Progress" 
                           Name="AverageProgress" />
    </TotalSummary>
</DxGrid>

@code {
    List<SimpleFormat> formats = SimpleFormat.GenerateTestFormats("Progress", 20, "Red Background", 80, "Green Background");
    
    private void CustomizeContextMenu(GridCustomizeContextMenuEventArgs args) {
        args.Items.Clear();

        if (args.Context is GridHeaderCommandContext headerContext && headerContext.Column is IGridDataColumn column) {
            var formatItem = args.Items.AddCustomItem("Conditional Formatting");
            formatItem.Items.AddCustomItem("Apply New Format", () => { formatSelectorRef?.AddNewFormat(column.FieldName); });
            foreach (SimpleFormat format in formats.Where(f => f.ColumnFieldName == column.FieldName)) {
                formatItem.Items.AddCustomItem(format.ToString(), () => { formatSelectorRef?.EditFormat(format.FormatId); });
            }
            formatItem.Items.AddCustomItem("Clear Formatting", () => { formatSelectorRef?.ClearAllColumnFormats(column.FieldName); });
        }
    }

    private void OnCustomizeElement(GridCustomizeElementEventArgs args) {
        foreach (var format in formats) {
            format.ApplyStyle(args);
        }
    }
}

Files to Review

Documentation

More Examples

Does This Example Address Your Development Requirements/Objectives?

(you will be redirected to DevExpress.com to submit your response)

Releases

Packages

Contributors

Languages