Selected row layout over customized cell background

I use conditional row styling and custom style for selected rows. This look like selected row is a transparent colored glass and is over cells. I like that.


I based my code on Syncfusion Demo - "Conditional row style".

But I need change background and font color for some columns.
I found two ways:
1) use cell data template
2) use cell style

If I use data template then I lost possibility to use a Search function [dataGrid.SearchHelper.Search(...)].

If I use cell style then I can't customize font color.

In both cases after apply template or style the selected row layout is under cell. It isn't look good.

Also, I want insert into right side of cell icon. As I understand I can do it using cell template. But I lost possibility marking seach text [dataGrid.SearchHelper.Search(...)].



Questions:
1) How to make that selected row layout always be over cells (including cells with custom template or style)?
2) How to make cell with text and image, with condition row styling (background, font weigth, font color) and possibility to use search function?


The attached example is based on Syncfusion "RowStyle Demo" example. Example illustrated my issue.

In the top of window I added text box for search function testing.
For a "Name" column I use data tamplate. I can customize font color and set background by cumdition. Also in the "Name" column is icon. Here is not working "search".

For a "Designation" column I add style where try change font weigth and font color. Font weigth is changed but font color setter didn't work.

For a "Name2" column I add style with condition background.



Attachment: CS2_dfeb8e97.7z

4 Replies 1 reply marked as answer

MA Mohanram Anbukkarasu Syncfusion Team July 18, 2020 09:20 AM UTC

Hi Dmitry, 

Thanks for contacting Syncfusion support. 

We are currently working with high priority on this query regarding the searching behavior and the selection behavior for the column with data template. We need to analyze this on our source level implementation to ensure the behavior. We will update with further details on  21st July 2020. We appreciate your patience until then. 

Regards, 
Mohanram A. 



MA Mohanram Anbukkarasu Syncfusion Team July 21, 2020 01:18 PM UTC

Hi Dmitry, 

Thanks for the patience. 

SfDataGrid doesn’t have support to search support for the templated column. However we have However, you can perform searching if the CellTemplate has the textblock by using the below work around using custom SearchHelper. 

Code example :  

public MainWindow() 
{ 
    InitializeComponent(); 
    this.SfGrid.SearchHelper = new SearchHelperExt(this.SfGrid); 
} 
 
public class SearchHelperExt : SearchHelper 
{ 
    public SearchHelperExt(SfDataGrid datagrid) 
        : base(datagrid) 
    { 
        SearchType = SearchType.Contains; 
        SearchBrush = Brushes.Yellow; 
    } 
 
    protected override bool SearchCell(DataColumnBase column, object record, bool ApplySearchHighlightBrush) 
    { 
        if (column == null) 
        { 
            return true; 
        } 
 
        if (column.GridColumn == null || DataGrid.View == null) 
        { 
            return false; 
        } 
 
        var gridTemplateColumn = column.GridColumn as GridTemplateColumn; 
        if (column.GridColumn.CellTemplate == null) 
        { 
            return base.SearchCell(column, record, ApplySearchHighlightBrush); 
        } 
 
        if (Provider == null) 
        { 
            Provider = DataGrid.View.GetPropertyAccessProvider(); 
        } 
 
        var data = Provider.GetFormattedValue(record, column.GridColumn.MappingName); 
 
        if (MatchSearchText(column.GridColumn, record)) 
        { 
            return ApplyInline(column, data, ApplySearchHighlightBrush); 
        } 
        ClearSearchCell(column, record); 
        return false; 
    } 
 
 
    protected override bool MatchSearchText(GridColumn column, object record) 
    { 
        var searchStrings = GetSearchStrings().Select(_ => _.ToUpperInvariant()); 
        var data = ((string)Provider.GetFormattedValue(record, column.MappingName)).ToUpperInvariant(); 
        return searchStrings.Any(data.Contains); 
    } 
 
    protected override void ClearSearchCell(DataColumnBase column, object record) 
    { 
        if (column.GridColumn != null && string.IsNullOrEmpty(SearchText) && column.GridColumn.CellTemplate != null) 
        { 
            var textControls = FindObjectInVisualTreeDown<TextBlock>(column.ColumnElement).ToArray(); 
            if (textControls.Any()) 
            { 
                var textBlock = textControls.First(); 
                if (textBlock != null && textBlock.Inlines.Count > 1) 
                { 
                    textBlock.ClearValue(TextBlock.TextProperty); 
                    return; 
                } 
            } 
        } 
        base.ClearSearchCell(column, record); 
    } 
 
    protected override bool ApplyInline(DataColumnBase column, object data, bool ApplySearchHighlightBrush) 
    { 
        var searchTexts = GetSearchStrings().Select(Regex.Escape); 
        var success = false; 
 
        var regex = new Regex("(" + String.Join("|", searchTexts) + ")", RegexOptions.IgnoreCase); 
 
        var textControls = FindObjectInVisualTreeDown<TextBlock>(column.ColumnElement).ToArray(); 
        if (!textControls.Any()) 
        { 
            return base.ApplyInline(column, data, ApplySearchHighlightBrush); 
        } 
        var textBlock = textControls.First(); 
        var binding = BindingOperations.GetBinding(textBlock, TextBlock.TextProperty); 
 
        var substrings = regex.Split(data.ToString()); 
        textBlock.Inlines.Clear(); 
 
        var binding1 = BindingOperations.GetBinding(textBlock, TextBlock.TextProperty); 
        foreach (var item in substrings) 
        { 
            if (regex.Match(item).Success) 
            { 
                var run = new Run(item); 
                run.Background = this.SearchBrush; 
                textBlock.Inlines.Add(run); 
                success = true; 
            } 
            else 
            { 
                textBlock.Inlines.Add(item); 
            } 
        } 
 
        return success; 
    } 
 
    private IEnumerable<T> FindObjectInVisualTreeDown<T>(DependencyObject parent) where T : DependencyObject 
    { 
        if (parent == null) 
        { 
            return null; 
        } 
 
        var foundChildren = new List<T>(); 
 
        var childrenCount = VisualTreeHelper.GetChildrenCount(parent); 
        for (var i = 0; i < childrenCount; i++) 
        { 
            var child = VisualTreeHelper.GetChild(parent, i); 
            var childType = child as T; 
            if (childType == null) 
           { 
                foundChildren.AddRange(FindObjectInVisualTreeDown<T>(child)); 
            } 
            else 
            { 
                foundChildren.Add(childType); 
            } 
        } 
 
        return foundChildren; 
    } 
 
    private IEnumerable<string> GetSearchStrings() 
    { 
        return GetAllStringVariants(SearchText); 
    } 
 
    private static IEnumerable<string> GetAllStringVariants(string text) 
    { 
        var strings = new List<string> { text }; 
        if ((text.StartsWith(Quote, StringComparison.Ordinal) && text.EndsWith(Quote, StringComparison.Ordinal))) 
        { 
            strings[0] = strings.First().Replace(Quote, string.Empty); 
        } 
        else if (text.StartsWith(Quote, StringComparison.Ordinal)) 
        { 
            strings[0] = strings.First().Replace(Quote, string.Empty); 
            text = text.Replace(Quote, string.Empty); 
            strings.AddRange(text.Split(new[] { " " }, StringSplitOptions.RemoveEmptyEntries).ToList()); 
            strings.Remove(text); 
        } 
        else 
        { 
            //Split text filter into seperated filter texts  
            var splittedStrings = text.Split(new[] { " " }, StringSplitOptions.RemoveEmptyEntries). 
                ToList().Where(_ => !strings.Contains(_)); 
            strings.AddRange(splittedStrings); 
        } 
        return strings; 
    } 
    private const string Quote = "\""; 
 
} 

We have also resolved the selection visibility by setting opacity for the BackgrounBrush to 0.5.  

The Foreground color can be applied as per the need by avoiding the MetroMode for the layout control.  

We have prepared a sample using above solutions and it is available in the following link for your reference. 


Please let us know if you require further assistance from us.  

Regards, 
Mohanram A. 


Marked as answer

DM Dmitry July 23, 2020 11:23 AM UTC

It's almost the things I need.
Thanks!


MA Mohanram Anbukkarasu Syncfusion Team July 24, 2020 05:00 AM UTC

Hi Dmitry, 

Thanks for the update. 

We are glad to know that the provided solution worked at your end. Please let us know if you have any further queries on this. We are happy to help you. 

Regards, 
Mohanram A. 


Loader.
Up arrow icon