Skip to main content

DevExpress v24.2 Update — Your Feedback Matters

Our What's New in v24.2 webpage includes product-specific surveys. Your response to our survey questions will help us measure product satisfaction for features released in this major update and help us refine our plans for our next major release.

Take the survey Not interested

Using provider mode: Complete Code

  • 6 minutes to read
  1. Base class structure

  2. TPriceList

  3. TUserDataSource

  4. Creating columns

  5. Full code

#5. Full code

The full code used to create a custom data source is listed below.

unit Unit1;
interface
uses
  SysUtils, Types, Classes, Graphics, Controls, Forms, Dialogs,
  StdCtrls, ExtCtrls,
  cxCustomData, cxDataStorage, cxGrid, cxGridCustomTableView, cxGridTableView;
type
  TForm1 = class(TForm)
    procedure FormCreate(Sender: TObject);
  private
    FGrid: TcxGrid;
    FTableView: TcxGridTableView;
    procedure LoadValues();
  public
    property Grid: TcxGrid read FGrid;
  end;
var
  Form1: TForm1;
implementation
{$R *.dfm}
type
  { User Objects }
  PListEntry = ^TListEntry;
  TListEntry = packed record
    Description: string;
    OnHand: Integer;
    Price: Currency;
  end;
  TPriceList = class
  private
    FRecords: TList;
  public
    constructor Create;
    destructor Destroy; override;
    procedure Add(ADescription: string; AOnHand: Integer;
    APrice: Currency);
    procedure Clear;
  end;
  TUserDataSource = class(TcxCustomDataSource)
  private
    FPriceList: TPriceList;
    function GetDataBinding(AItemIndex: Integer):
    TcxGridItemDataBinding;
  protected
    function GetInfoForCompare(ARecordHandle: TcxDataRecordHandle;
    AItemHandle: TcxDataItemHandle; var PValueBuffer: PChar):
    Boolean; override;
    function GetItemHandle(AItemIndex: Integer): TcxDataItemHandle;
    override;
    function GetRecordCount: Integer; override;
    function GetValue(ARecordHandle: TcxDataRecordHandle;AItemHandle:
    TcxDataItemHandle): Variant; override;
    function IsNativeCompare: Boolean; override;
  public
    constructor Create(APriceList: TPriceList);
  end;
var
  PriceList: TPriceList;
{ TPriceList }
constructor TPriceList.Create;
begin
  FRecords := TList.Create;
end;
destructor TPriceList.Destroy;
begin
  Clear;
  FRecords.Free;
  inherited Destroy;
end;
procedure TPriceList.Add(ADescription: string; AOnHand: Integer; APrice: Currency);
var
  P: PListEntry;
begin
  New(P);
  FRecords.Add(P);
  P^.Description := ADescription;
  P^.OnHand := AOnHand;
  P^.Price := APrice;
end;
procedure TPriceList.Clear;
begin
  while FRecords.Count > 0 do
  begin
    Dispose(PListEntry(FRecords[FRecords.Count - 1]));
    FRecords.Delete(FRecords.Count - 1);
  end;
end;
{ TUserDataSource }
constructor TUserDataSource.Create(APriceList: TPriceList);
begin
  inherited Create;
  FPriceList := APriceList;
end;
function TUserDataSource.GetDataBinding(AItemIndex: Integer): TcxGridItemDataBinding;
begin
  Result := TcxCustomGridTableItem(DataController.GetItem(AItemIndex)).DataBinding;
end;
function TUserDataSource.GetInfoForCompare(ARecordHandle: TcxDataRecordHandle;
  AItemHandle: TcxDataItemHandle; var PValueBuffer: PChar): Boolean;
var
  ADataBinding: TcxGridItemDataBinding;
begin
  ADataBinding := TcxGridItemDataBinding(AItemHandle);
  PValueBuffer := PChar(Integer(FPriceList.
  FRecords[Integer(ARecordHandle)]) +
  Integer(ADataBinding.Data));
  Result := True;
end;
function TUserDataSource.GetItemHandle(AItemIndex: Integer): TcxDataItemHandle;
begin
  Result := TcxDataItemHandle(GetDataBinding(AItemIndex));
end;
function TUserDataSource.GetRecordCount: Integer;
begin
  Result := FPriceList.FRecords.Count;
end;
function TUserDataSource.GetValue(ARecordHandle: TcxDataRecordHandle; AItemHandle: TcxDataItemHandle): Variant;
var
  P: PChar;
  ADataBinding: TcxGridItemDataBinding;
begin
  ADataBinding := TcxGridItemDataBinding(AItemHandle);
  P := PChar(Integer(FPriceList.FRecords[Integer(ARecordHandle)]) +
  Integer(ADataBinding.Data));
  Result := ADataBinding.ValueTypeClass.GetValue(P);
end;
function TUserDataSource.IsNativeCompare: Boolean;
begin
  Result := True;
end;
{ routines }
procedure GenerateColumns(AGridTableView: TcxGridTableView);
var
  AListEntry: TListEntry;
begin
  with AGridTableView do
  begin
    OptionsSelection.HideFocusRect := False;
    OptionsSelection.MultiSelect := True;
    ClearItems;
    with CreateColumn as TcxGridColumn do
    begin
      Caption := 'Description';
      DataBinding.ValueTypeClass := TcxStringValueType;
      DataBinding.Data := Pointer(0);
      Width := 100;
    end;
    with CreateColumn as TcxGridColumn do
    begin
      Caption := 'OnHand';
      DataBinding.ValueTypeClass := TcxIntegerValueType;
      DataBinding.Data := Pointer(Integer(@AListEntry.OnHand) -
      Integer(@AListEntry));
      Width := 100;
    end;
    with CreateColumn as TcxGridColumn do
    begin
      Caption := 'Price';
      DataBinding.ValueTypeClass := TcxCurrencyValueType;
      DataBinding.Data := Pointer(Integer(@AListEntry.Price) -
      Integer(@AListEntry));
      Width := 100;
    end;
  end;
end;
procedure TForm1.LoadValues();
begin
  PriceList.Add('Dive kayak', 24, 3999.95);
  PriceList.Add('Underwater Diver Vehicle', 5, 1680.00);
  PriceList.Add('Regulator System', 165, 250.00);
  PriceList.Add('Personal Dive Sonar', 46, 235.00);
  PriceList.Add('Depth/Pressure Gauge', 128, 206.00);
  FTableView.DataController.CustomDataSource.DataChanged;
end;
procedure TForm1.FormCreate(Sender: TObject);
begin
  FGrid := TcxGrid.Create(Self);
  with FGrid do
  begin
    FTableView := CreateView(TcxGridTableView) as TcxGridTableView;
    Levels.Add.GridView := FTableView;
    GenerateColumns(FTableView);
    FTableView.OptionsView.Footer := True;
    with FTableView.DataController.Summary.FooterSummaryItems.Add do
    begin
      Kind := skCount;
      ItemLink := FTableView.Columns[0];
    end;
    Align := alClient;
    Parent := Self;
  end;
  FTableView.DataController.CustomDataSource :=
  TUserDataSource.Create(PriceList);
  LoadValues();
end;
initialization
  PriceList := TPriceList.Create;
finalization
  PriceList.Free;
end.
See Also