- Регистрация
- 9 Май 2015
- Сообщения
- 1,486
- Баллы
- 155
Efficient data filtering is crucial when working with large datasets. With TTMSFNCFilterDialog, you can seamlessly apply filters to various components, including TTMSFNCDataGrid. This blog explores how to integrate TTMSFNCFilterDialog with any control—using TTMSFNCDataGrid as an example—to enable dynamic filtering without manual data handling.
The Advantages of TTMSFNCFilterDialog?
The TTMSFNCFilterDialog provides a visual and intuitive way to filter data, eliminating the need for users to manually construct filter conditions. By leveraging this component, you can:
This control is a more flexible version of , allowing you to filter data beyond just database datasets. In this example, we will filter simple grid data.
Setting Up TTMSFNCFilterDialog with TTMSFNCDataGrid
Step 1: Creating Sample Grid Data
First, we populate a TTMSFNCDataGrid with different types of data. For this example, we will use sample data generated by the control.
procedure TSampleForm.FormCreate(Sender: TObject);
begin
DataGrid.LoadSampleData;
DataGrid.Columns[0].Formatting.&Type := gdftNumber;
DataGrid.Columns[1].Formatting.&Type := gdftDefault; //Text
DataGrid.Columns[2].Formatting.&Type := gdftDate;
DataGrid.Columns[3].Formatting.&Type := gdftDefault; //Text
end;
Step 2: Setting Up the Filter Dialog
Next, we create an instance of TTMSFNCFilterDialog, configure it, and retrieve the different input columns using the OnGetFilterBuilderDataColumns event.
procedure TSampleForm.FormCreate(Sender: TObject);
begin
DataGrid.LoadSampleData;
DataGrid.Columns[0].Formatting.&Type := gdftNumber;
//DataGrid.Columns[1] is Text
DataGrid.Columns[2].Formatting.&Type := gdftDate;
//DataGrid.Columns[3] is Text
fd := TTMSFNCFilterDialog.Create(Self);
fd.OnGetFilterBuilderDataColumns := DoGetFilterBuilderDataColumns;
end;
You can also use the SQL formatted filtering by setting the following property:
fd.FilterBuilder.FormatType := fftDelphiDataSet;
//Otherwise our own format type fftUniversalFilterExpressions is used.
Step 3: Mapping Filter Builder Columns
To optimize how columns are handled in the filter dialog, we map TTMSFNCDataGrid columns by assigning their names from the fixed row and their format type.
procedure TSampleForm.DoGetFilterBuilderDataColumns(Sender: TObject; AFilterBuilder: TTMSFNCFilterBuilder; ADataColumns: TTMSFNCFilterBuilderColumns);
var
I: Integer;
dt: TTMSFNCFilterBuilderDataType;
begin
ADataColumns.Clear;
for I := 0 to TMSFNCDataGrid1.Columns.Count - 1 do
begin
case DataGrid.Columns.Formatting.&Type of
gdftDateTime: dt := fdtDateTime;
gdftDate: dt := fdtDate;
gdftTime: dt := fdtTime;
gdftFloat: dt := fdtFloat;
gdftNumber: dt := fdtNumber;
gdftBoolean: dt := fdtBoolean;
gdftDefault: dt := fdtText;
else dt := fdtAutomatic;
end;
ADataColumns.AddColumn(TMSFNCDataGrid1.Strings[I,0], dt);
end;
end;
Step 4: Applying Filters to the Data Grid
When a user applies a filter, we validate and apply it to the TTMSFNCDataGrid.
procedure TSampleForm.ValidateFilter;
var
ia: TTMSFNCFilterValidateInputArray;
I, J: Integer;
begin
if DataGrid.ColumnCount = fd.FilterBuilder.DataColumns.Count then
begin
SetLength(ia, DataGrid.ColumnCount, DataGrid.RowCount - DataGrid.FixedRowCount);
for I := 0 to DataGrid.ColumnCount - 1 do
begin
for J := 0 to DataGrid.RowCount - DataGrid.FixedRowCount -1 do
begin
ia[I,J] := DataGrid.Cells[I,J + DataGrid.FixedRowCount];
end;
end;
oa := fd.FilterBuilder.ValidateFilterArray(ia);
SetFilter;
end;
TMSFNCDataGrid1.Repaint;
end;
This function ValidateFilterArray processes an array of data and returns a dynamic array of Boolean values.
Alternatively, ValidateFilterRow[FONT=Menlo, Monaco, Consolas, Courier New, monospace] [/FONT]can be used to evaluate a single row and return a Boolean indicating whether it matches the filter.
Step 5: Opening the Filter Dialog
To display the filter dialog and apply the filter:
procedure TSampleForm.FilterBtn(Sender: TObject);
begin
fd.Execute;
ValidateFilter;
end;
Step 6: Displaying the Filter Results
There are two ways to visualize the filter results: hiding non-matching rows or highlighting matching rows.
Option 1: Hiding Non-Matching Rows
procedure TSampleForm.SetFilter;
var
I: Integer;
begin
if (Length(oa) > 0) then
begin
for I := DataGrid.FixedRowCount to DataGrid.FixedRowCount + Length(oa) - 1 do
begin
if not oa[I - DataGrid.FixedRowCount] then
DataGrid.HideRow(I)
else
DataGrid.UnhideRow(I);
end;
end
else
DataGrid.UnhideAllRows;
end;
Option 2: Highlighting Matching Rows
procedure TSampleForm.DataGridBeforeDrawCell(Sender: TObject; AGraphics: TTMSFNCGraphics; ACell: TTMSFNCDataGridCell; var ACanDraw: Boolean);
begin
if (ACell.Row >= DataGrid.FixedRowCount) and (Length(oa) > ACell.Row - DataGrid.FixedRowCount) then
begin
if oa[ACell.Row - DataGrid.FixedRowCount] then
AGraphics.Fill.Color := gcDarkseagreen;
end;
end;
Future Implementation in TMSFNCDataGrid
This filtering feature is highly useful and should not require custom implementation for every grid.
Therefore, TTMSFNCDataGrid will include built-in support for TTMSFNCFilterDialog in a future release.
Conclusion
The TTMSFNCFilterDialog provides a powerful yet easy-to-use solution for dynamic filtering in Delphi applications. As demonstrated with , it offers a seamless integration that enhances user experience by eliminating the need for complex filtering logic.

The Advantages of TTMSFNCFilterDialog?
The TTMSFNCFilterDialog provides a visual and intuitive way to filter data, eliminating the need for users to manually construct filter conditions. By leveraging this component, you can:
- Dynamically apply filters to any component.
- Utilize a user-friendly filter dialog instead of manually setting filter conditions.
- Integrate advanced filtering logic, including AND/OR group operations and data type-based filtering.
- Customize the UI and language settings to fit your application’s needs.
This control is a more flexible version of , allowing you to filter data beyond just database datasets. In this example, we will filter simple grid data.
Setting Up TTMSFNCFilterDialog with TTMSFNCDataGrid
Step 1: Creating Sample Grid Data
First, we populate a TTMSFNCDataGrid with different types of data. For this example, we will use sample data generated by the control.
procedure TSampleForm.FormCreate(Sender: TObject);
begin
DataGrid.LoadSampleData;
DataGrid.Columns[0].Formatting.&Type := gdftNumber;
DataGrid.Columns[1].Formatting.&Type := gdftDefault; //Text
DataGrid.Columns[2].Formatting.&Type := gdftDate;
DataGrid.Columns[3].Formatting.&Type := gdftDefault; //Text
end;
Step 2: Setting Up the Filter Dialog
Next, we create an instance of TTMSFNCFilterDialog, configure it, and retrieve the different input columns using the OnGetFilterBuilderDataColumns event.
procedure TSampleForm.FormCreate(Sender: TObject);
begin
DataGrid.LoadSampleData;
DataGrid.Columns[0].Formatting.&Type := gdftNumber;
//DataGrid.Columns[1] is Text
DataGrid.Columns[2].Formatting.&Type := gdftDate;
//DataGrid.Columns[3] is Text
fd := TTMSFNCFilterDialog.Create(Self);
fd.OnGetFilterBuilderDataColumns := DoGetFilterBuilderDataColumns;
end;
You can also use the SQL formatted filtering by setting the following property:
fd.FilterBuilder.FormatType := fftDelphiDataSet;
//Otherwise our own format type fftUniversalFilterExpressions is used.
Step 3: Mapping Filter Builder Columns
To optimize how columns are handled in the filter dialog, we map TTMSFNCDataGrid columns by assigning their names from the fixed row and their format type.
procedure TSampleForm.DoGetFilterBuilderDataColumns(Sender: TObject; AFilterBuilder: TTMSFNCFilterBuilder; ADataColumns: TTMSFNCFilterBuilderColumns);
var
I: Integer;
dt: TTMSFNCFilterBuilderDataType;
begin
ADataColumns.Clear;
for I := 0 to TMSFNCDataGrid1.Columns.Count - 1 do
begin
case DataGrid.Columns.Formatting.&Type of
gdftDateTime: dt := fdtDateTime;
gdftDate: dt := fdtDate;
gdftTime: dt := fdtTime;
gdftFloat: dt := fdtFloat;
gdftNumber: dt := fdtNumber;
gdftBoolean: dt := fdtBoolean;
gdftDefault: dt := fdtText;
else dt := fdtAutomatic;
end;
ADataColumns.AddColumn(TMSFNCDataGrid1.Strings[I,0], dt);
end;
end;
Step 4: Applying Filters to the Data Grid
When a user applies a filter, we validate and apply it to the TTMSFNCDataGrid.
procedure TSampleForm.ValidateFilter;
var
ia: TTMSFNCFilterValidateInputArray;
I, J: Integer;
begin
if DataGrid.ColumnCount = fd.FilterBuilder.DataColumns.Count then
begin
SetLength(ia, DataGrid.ColumnCount, DataGrid.RowCount - DataGrid.FixedRowCount);
for I := 0 to DataGrid.ColumnCount - 1 do
begin
for J := 0 to DataGrid.RowCount - DataGrid.FixedRowCount -1 do
begin
ia[I,J] := DataGrid.Cells[I,J + DataGrid.FixedRowCount];
end;
end;
oa := fd.FilterBuilder.ValidateFilterArray(ia);
SetFilter;
end;
TMSFNCDataGrid1.Repaint;
end;
This function ValidateFilterArray processes an array of data and returns a dynamic array of Boolean values.
Alternatively, ValidateFilterRow[FONT=Menlo, Monaco, Consolas, Courier New, monospace] [/FONT]can be used to evaluate a single row and return a Boolean indicating whether it matches the filter.
Step 5: Opening the Filter Dialog
To display the filter dialog and apply the filter:
procedure TSampleForm.FilterBtn(Sender: TObject);
begin
fd.Execute;
ValidateFilter;
end;
Step 6: Displaying the Filter Results
There are two ways to visualize the filter results: hiding non-matching rows or highlighting matching rows.
Option 1: Hiding Non-Matching Rows
procedure TSampleForm.SetFilter;
var
I: Integer;
begin
if (Length(oa) > 0) then
begin
for I := DataGrid.FixedRowCount to DataGrid.FixedRowCount + Length(oa) - 1 do
begin
if not oa[I - DataGrid.FixedRowCount] then
DataGrid.HideRow(I)
else
DataGrid.UnhideRow(I);
end;
end
else
DataGrid.UnhideAllRows;
end;

Option 2: Highlighting Matching Rows
procedure TSampleForm.DataGridBeforeDrawCell(Sender: TObject; AGraphics: TTMSFNCGraphics; ACell: TTMSFNCDataGridCell; var ACanDraw: Boolean);
begin
if (ACell.Row >= DataGrid.FixedRowCount) and (Length(oa) > ACell.Row - DataGrid.FixedRowCount) then
begin
if oa[ACell.Row - DataGrid.FixedRowCount] then
AGraphics.Fill.Color := gcDarkseagreen;
end;
end;

Future Implementation in TMSFNCDataGrid
This filtering feature is highly useful and should not require custom implementation for every grid.
Therefore, TTMSFNCDataGrid will include built-in support for TTMSFNCFilterDialog in a future release.
Conclusion
The TTMSFNCFilterDialog provides a powerful yet easy-to-use solution for dynamic filtering in Delphi applications. As demonstrated with , it offers a seamless integration that enhances user experience by eliminating the need for complex filtering logic.