anchor.diff:    if not Assigned(FDataSource) then
       exit;
   
  +  SetLength(FFilter, 0);
     //LFormat.DecimalSeparator:='.';
  -  LExpressionRecord := TSearchExpressionService.Parse(FSearchEdit.Text);
  -  with LExpressionRecord do
  -  begin
  -    case Kind of
  -      ekUnknown:
  -        Exit;
  -      ekNum:
  -        case NumericComparisionKind of
  -          // nckUnknown is special case - pure number can be text and num
  -          nckUnknown: LCandidates := [vgfNumericEQ, vgfMatchTextExact];
  -          nckNumericEQ: LCandidates := [vgfNumericEQ];
  -          nckNumericLT: LCandidates := [vgfNumericLT];
  -          nckNumericLTE: LCandidates := [vgfNumericLTE];
  -          nckNumericGT: LCandidates := [vgfNumericGT];
  -          nckNumericGTE: LCandidates := [vgfNumericGTE];
  -        else
  -          Assert(false);
  +  try
  +    LExpressionRecord := TSearchExpressionService.Parse(FSearchEdit.Text);
  +    with LExpressionRecord do
  +    begin
  +      case Kind of
  +        ekUnknown:
  +          Exit;
  +        ekNum:
  +          case NumericComparisionKind of
  +            // nckUnknown is special case - pure number can be text and num
  +            nckUnknown: LCandidates := [vgfNumericEQ, vgfMatchTextExact];
  +            nckNumericEQ: LCandidates := [vgfNumericEQ];
  +            nckNumericLT: LCandidates := [vgfNumericLT];
  +            nckNumericLTE: LCandidates := [vgfNumericLTE];
  +            nckNumericGT: LCandidates := [vgfNumericGT];
  +            nckNumericGTE: LCandidates := [vgfNumericGTE];
  +          else
  +            Assert(false);
  +          end;
  +        ekText:
  +          case TextMatchKind of
  +            tmkMatchTextExact: LCandidates := [vgfMatchTextExact];
  +            tmkMatchTextBeginning: LCandidates := [vgfMatchTextBeginning];
  +            tmkMatchTextEnd: LCandidates := [vgfMatchTextEnd];
  +            tmkMatchTextAnywhere: LCandidates := [vgfMatchTextAnywhere]
  +          else
  +            Assert(false);
  +          end;
  +        ekSet:
  +          case SetKind of
  +            skNumericBetweenInclusive: LCandidates := [vgfNumericBetweenInclusive];
  +            skNumericBetweenExclusive: LCandidates := [vgfNumericBetweenExclusive];
  +          else
  +            Assert(false);
  +          end;
  +      else
  +        Assert(false);
  +      end;
  +      Assert(LCandidates<>[]);
  +    end;
  +
  +    for LSearchCapability in FSearchCapabilities do
  +    begin
  +      LAccepted := LSearchCapability.SupportedFilters * LCandidates;
  +      if LAccepted <> [] then
  +        for LFilter in LAccepted do
  +        begin
  +          LColumnFilter:=Default(TColumnFilter);
  +          LColumnFilter.ColumnName := LSearchCapability.ColumnName;
  +          LColumnFilter.Filter := LFilter;
  +
  +          if LFilter in TEXT_FILTER then
  +          begin
  +            SetLength(LColumnFilter.Values, 1);
  +            LColumnFilter.Values[0]:=LExpressionRecord.Values[0];
  +          end
  +          else if LFilter in (NUMERIC_FILTER - [vgfNumericBetweenInclusive, vgfNumericBetweenExclusive]) then
  +          begin
  +            SetLength(LColumnFilter.Values, 1);
  +            LColumnFilter.Values[0]:=StrToInt(LExpressionRecord.Values[0]);
  +          end
  +          else if LFilter in [vgfNumericBetweenInclusive, vgfNumericBetweenExclusive] then
  +          begin
  +            SetLength(LColumnFilter.Values, 2);
  +            LColumnFilter.Values[0]:=StrToInt(LExpressionRecord.Values[0]);
  +            LColumnFilter.Values[1]:=StrToInt(LExpressionRecord.Values[1]);
  +          end;
  +
  +          SetLength(FFilter, Length(FFilter)+1);
  +          FFilter[High(FFilter)] := LColumnFilter;
           end;
  -      ekText:
  -        case TextMatchKind of
  -          tmkMatchTextExact: LCandidates := [vgfMatchTextExact];
  -          tmkMatchTextBeginning: LCandidates := [vgfMatchTextBeginning];
  -          tmkMatchTextEnd: LCandidates := [vgfMatchTextEnd];
  -          tmkMatchTextAnywhere: LCandidates := [vgfMatchTextAnywhere]
  -        else
  -          Assert(false);
  -        end;
  -      ekSet:
  -        case SetKind of
  -          skNumericBetweenInclusive: LCandidates := [vgfNumericBetweenInclusive];
  -          skNumericBetweenExclusive: LCandidates := [vgfNumericBetweenExclusive];
  -        else
  -          Assert(false);
  -        end;
  -    else
  -      Assert(false);
       end;
  -    Assert(LCandidates<>[]);
  -  end;
  -
  -  SetLength(FFilter, 0);
  -  for LSearchCapability in FSearchCapabilities do
  -  begin
  -    LAccepted := LSearchCapability.SupportedFilters * LCandidates;
  -    if LAccepted <> [] then
  -      for LFilter in LAccepted do
  -      begin
  -        LColumnFilter:=Default(TColumnFilter);
  -        LColumnFilter.ColumnName := LSearchCapability.ColumnName;
  -        LColumnFilter.Filter := LFilter;
  -
  -        if LFilter in TEXT_FILTER then
  -        begin
  -          SetLength(LColumnFilter.Values, 1);
  -          LColumnFilter.Values[0]:=LExpressionRecord.Values[0];
  -        end
  -        else if LFilter in (NUMERIC_FILTER - [vgfNumericBetweenInclusive, vgfNumericBetweenExclusive]) then
  -        begin
  -          SetLength(LColumnFilter.Values, 1);
  -          LColumnFilter.Values[0]:=StrToInt(LExpressionRecord.Values[0]);
  -        end
  -        else if LFilter in [vgfNumericBetweenInclusive, vgfNumericBetweenExclusive] then
  -        begin
  -          SetLength(LColumnFilter.Values, 2);
  -          LColumnFilter.Values[0]:=StrToInt(LExpressionRecord.Values[0]);
  -          LColumnFilter.Values[1]:=StrToInt(LExpressionRecord.Values[1]);
  -        end;
  -
  -        SetLength(FFilter, Length(FFilter)+1);
  -        FFilter[High(FFilter)] := LColumnFilter;
  -      end;
  -  end;
  -  RefreshPageIndexData(false);
  +  finally
  +    LNewStrFilter := QuotedStr(FSearchEdit.Text);
  +    if FStrFilter <> LNewStrFilter then
  +    begin
  +      FStrFilter:=LNewStrFilter;
  +      RefreshPageIndexData(false);
  +    end;
  +  end;
   end;
   
   procedure TCustomVisualGrid.ControlsEnable(AEnable: boolean);
  
positive.code:     FDataTable: TDataTable;
      FCachedDataTable: PDataTable;
      FDataSource: IDataSource;
      FFilter: TFilterCriteria;
      FSearchCapabilities: TSearchCapabilities;
      FPageSize: Integer;
  
negative.code:   LExpressionRecord: TExpressionRecord;
    LSearchCapability: TSearchCapability;
    //LFormat: TFormatSettings;
    LNewStrFilter: utf8string;
    LAccepted: TVisualGridFilters;
    LCandidates: TVisualGridFilters = [];
    LFilter: TVisualGridFilter;
  