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 = "\"";
} |