Search code examples
delphidevexpressvcl

DevExpress cxDBFilterControl value enumeration


I am trying to enumerate the criteria in cxDBFilterControl, including any groups. The field name, operator, value fields.

cxDBFilterControl1.ApplyFilter;
Memo1.Lines.Add(cxDBFilterControl1.FilterCaption);
Memo1.Lines.Add('');
for ci := 0 to cxDBFilterControl1.Criteria.Root.Count - 1 do begin
  if not cxDBFilterControl1.Criteria.Root.Items[ci].IsItemList then begin
    Memo1.Lines.Add(
//    ((cxDBFilterControl1.Criteria.Root.Items[ci] as TcxFilterCriteriaItem).ItemLink as TcxFilterItem).FieldName +' : '+ // typecast issue
      (cxDBFilterControl1.Criteria.Root.Items[ci] as TcxFilterCriteriaItem).Operator.DisplayText +' : '+
      (cxDBFilterControl1.Criteria.Root.Items[ci] as TcxFilterCriteriaItem).DisplayValue
);
  end
  else begin
  end;
end;

The above code will list the root level criteria without the field names, how can I get the field names also along with any added groups and their operators?

cxDBFilterControl1.FilterCaption output:
(id = 1) and (ttype > 4) and ((tdate < 2/2/2014) or (outcome = test))

The enumerated output should be something like:

id equals 1
AND
ttype equals 4
AND
  tdate lessthan 2/2/2014
  OR
  outcome equals test

Solution

  • enter image description here

    procedure Form1.Test
    begin
      PrintFilter(Memo1, cxDBFilterControl1.Criteria.Root);
    end;
    
    procedure PrintFilter(Memo: TMemo; ARoot: TcxFilterCriteriaItemList; Level: integer = 0);
    var
      I: Integer;
      Op: string;
      Line: string;
      LItemLink: TObject;
      LItem: TcxFilterCriteriaItem;
    begin
      for I := 0 to ARoot.Count - 1 do
      begin
        //extract into a function?
        case ARoot.BoolOperatorKind of
          fboAnd: Op := 'AND';
          fboOr: Op := 'OR';
          fboNotAnd: Op := 'NOT AND';
          fboNotOr: Op := 'NOT OR';
        end;
        //
        if not ARoot.Items[I].IsItemList then
        begin
          if I <> 0 then
            Memo.Lines.Add(StringOfChar(' ', Level * 2) + Op);
          LItem := (ARoot.Items[I] as TcxFilterCriteriaItem);
          LItemLink := LItem.ItemLink;
          if (LItemLink <> nil) and (LItemLink is TField) then
            Line := TField(LItemLink).DisplayName;
          Line := Line + ' ' + LItem.Operator.DisplayText +' '+ LItem.DisplayValue;
          Memo.Lines.Add(StringOfChar(' ', Level * 2) + Line)
        end else
        begin
          if TcxFilterCriteriaItemList(ARoot.Items[I]).Count > 0 then
            Memo.Lines.Add(StringOfChar(' ', Level * 2) + Op);
          PrintFilter(Memo, TcxFilterCriteriaItemList(ARoot.Items[I]), Level + 1);
        end;
      end;
    end;