- Mustangpeak Common Library - 1.7.0 - EasyListview - 1.7.0 git-svn-id: https://192.168.0.254/svn/Componentes.Terceros.Mustangpeak@2 60b41242-d4b9-2247-b156-4ccd40706241
465 lines
12 KiB
ObjectPascal
465 lines
12 KiB
ObjectPascal
unit Unit1;
|
|
|
|
interface
|
|
|
|
{$I ..\..\..\Source\Compilers.inc}
|
|
|
|
uses
|
|
Windows,
|
|
Messages,
|
|
SysUtils,
|
|
Classes,
|
|
Graphics,
|
|
Controls,
|
|
Forms,
|
|
Dialogs,
|
|
StdCtrls,
|
|
ImgList,
|
|
ExtCtrls,
|
|
ActiveX,
|
|
ComCtrls,
|
|
{$IFDEF COMPILER_6_UP}
|
|
Variants,
|
|
DateUtils,
|
|
{$ENDIF COMPILER_6_UP}
|
|
{$IFDEF COMPILER_7_UP}
|
|
XPMan,
|
|
{$ENDIF COMPILER_7_UP}
|
|
EasyListview,
|
|
MPCommonUtilities,
|
|
MPCommonObjects;
|
|
|
|
const
|
|
COLUMNSTRINGS: array[0..4] of WideString = (
|
|
'Name',
|
|
'Address',
|
|
'Phone',
|
|
'Contact',
|
|
'ID'
|
|
);
|
|
COLUMNWIDTHS: array[0..4] of Integer = (
|
|
120,
|
|
180,
|
|
90,
|
|
90,
|
|
40
|
|
);
|
|
|
|
type
|
|
//
|
|
// First some data object is defined for the task
|
|
//
|
|
TBusinessType = (
|
|
btIndividual,
|
|
btCompany
|
|
);
|
|
|
|
// We are going to use reference counting for our objects by using
|
|
// TEasyInterfacedPersistent as the ancestor. This class also implements
|
|
// IEasyExtractObj which allows us to extract the TObject out of the interface
|
|
// I know it is very un-COM like but most don't like to create a new interface
|
|
// to do it right
|
|
TBusinessObject = class(TEasyInterfacedPersistent)
|
|
private
|
|
FBusinessType: TBusinessType;
|
|
public
|
|
property BusinessType: TBusinessType read FBusinessType write FBusinessType;
|
|
end;
|
|
|
|
TCustomer = class(TBusinessObject)
|
|
private
|
|
FName: WideString;
|
|
FAddress: WideString;
|
|
FLastContact: TDateTime;
|
|
FPhone: WideString;
|
|
FRecordID: Integer;
|
|
public
|
|
constructor Create;
|
|
destructor Destroy; override;
|
|
|
|
property Address: WideString read FAddress write FAddress;
|
|
property Name: WideString read FName write FName;
|
|
property Phone: WideString read FPhone write FPhone;
|
|
property LastContact: TDateTime read FLastContact write FLastContact;
|
|
property RecordID: Integer read FRecordID write FRecordID;
|
|
end;
|
|
|
|
//
|
|
// Now we "teach" it to interact with our EasyListview through interfaces
|
|
// Currently the following interfaces are defined
|
|
// IEasyCaptions
|
|
// IEasyCaptionsEditable
|
|
// IEasyImages
|
|
// IEasyImagesEditable
|
|
// IEasyChecks
|
|
// IEasyCompareData
|
|
// IEasyNotifier
|
|
// IEasyExtractObj
|
|
//
|
|
|
|
// Our customer Data will need Editable captions but the Images are
|
|
// hard coded and known by the class so we don't need to implement
|
|
// IEasyImageEditable
|
|
//
|
|
// A little gotcha here. We must also put IEasyCaptions which is
|
|
// IEasyCaptionsEditable's ancestor. If you don't a QueryInterface to
|
|
// IEasyCaptions fails and ELV can't query for the Caption.
|
|
TCustomerData = class(TCustomer, IEasyCaptions, IEasyCaptionsEditable, IEasyImages,
|
|
IEasyNotifier, IEasyCompare, IEasyDetails, IEasyChecks)
|
|
private
|
|
FNotifier: IEasyNotificationSink;
|
|
FChecked: Boolean;
|
|
function GetDetail(Line: Integer): Integer;
|
|
function GetDetailCount: Integer;
|
|
public
|
|
destructor Destroy; override;
|
|
|
|
// IEasyNotifier
|
|
procedure OnRegisterNotify(const ANotifier: IEasyNotificationSink);
|
|
procedure OnUnRegisterNotify(const ANotifier: IEasyNotificationSink);
|
|
// IEasyCaptions, IEasyCaptionsEditable
|
|
function GetCaption(Column: Integer): Variant;
|
|
function SetCaption(Column: Integer; const Value: Variant): Boolean;
|
|
// IEasyImages
|
|
function GetImageIndex(Column: Integer; ImageKind: TEasyImageKind): Integer;
|
|
// IEasyCompareData
|
|
function Compare(const Data: IUnknown; Column: TEasyColumn): Integer;
|
|
// IEasyCaptions, IEasyCaptionsEditable
|
|
function GetChecked(Column: Integer): Boolean;
|
|
procedure SetChecked(Column: Integer; const Value: Boolean);
|
|
|
|
property Captions[Column: Integer]: Variant read GetCaption;
|
|
property Checked[Column: Integer]: Boolean read GetChecked write SetChecked;
|
|
property Images[Column: Integer; ImageKind: TEasyImageKind]: Integer read GetImageIndex;
|
|
property Detail[Line: Integer]: Integer read GetDetail;
|
|
property DetailCount: Integer read GetDetailCount;
|
|
|
|
property Notifier: IEasyNotificationSink read FNotifier write FNotifier;
|
|
end;
|
|
|
|
type
|
|
TForm1 = class(TForm)
|
|
ImageListSmall: TImageList;
|
|
Splitter1: TSplitter;
|
|
Panel1: TPanel;
|
|
Memo1: TMemo;
|
|
ComboBox1: TComboBox;
|
|
Button1: TButton;
|
|
ImageListLarge: TImageList;
|
|
ImageListExLarge: TImageList;
|
|
ButtonAddCustomers: TButton;
|
|
EditCustomerAddCount: TEdit;
|
|
StatusBar1: TStatusBar;
|
|
Button2: TButton;
|
|
ButtonChangeCaption: TButton;
|
|
ButtonLoadData: TButton;
|
|
ELV: TEasyListview;
|
|
CheckBoxAutoSort: TCheckBox;
|
|
procedure ComboBox1Change(Sender: TObject);
|
|
procedure Button1Click(Sender: TObject);
|
|
procedure FormCreate(Sender: TObject);
|
|
procedure ButtonAddCustomersClick(Sender: TObject);
|
|
procedure Button2Click(Sender: TObject);
|
|
procedure ButtonChangeCaptionClick(Sender: TObject);
|
|
procedure ButtonLoadDataClick(Sender: TObject);
|
|
procedure FormShow(Sender: TObject);
|
|
procedure CheckBoxAutoSortClick(Sender: TObject);
|
|
private
|
|
{ Private declarations }
|
|
procedure AddCustomers(Count: Integer);
|
|
public
|
|
{ Public declarations }
|
|
RecordID: Integer;
|
|
end;
|
|
|
|
var
|
|
Form1: TForm1;
|
|
|
|
implementation
|
|
|
|
{$R *.dfm}
|
|
|
|
{ TCustomer }
|
|
|
|
constructor TCustomer.Create;
|
|
begin
|
|
LastContact := Now
|
|
end;
|
|
|
|
destructor TCustomer.Destroy;
|
|
begin
|
|
inherited;
|
|
end;
|
|
|
|
{ TCustomerData }
|
|
|
|
function TCustomerData.Compare(const Data: IUnknown; Column: TEasyColumn): Integer;
|
|
var
|
|
Customer: TCustomerData;
|
|
begin
|
|
// Pull our object out of the interface
|
|
Customer := TCustomerData( (Data as ICommonExtractObj).Obj);
|
|
case Column.Index of
|
|
0: Result := WideStrIComp(PWideChar(Customer.Name), PWideChar( Name));
|
|
1: Result := WideStrIComp(PWideChar(Customer.Address), PWideChar( Address));
|
|
2: Result := WideStrIComp(PWideChar(Customer.Phone), PWideChar( Phone));
|
|
3: Result := CompareTime(Customer.LastContact, LastContact);
|
|
4: Result := Customer.RecordID - RecordID
|
|
else
|
|
Result := 0
|
|
end;
|
|
|
|
if Column.SortDirection = esdDescending then
|
|
Result := -Result
|
|
end;
|
|
|
|
destructor TCustomerData.Destroy;
|
|
begin
|
|
// Unhook from the EasyObject
|
|
if Assigned(FNotifier) then
|
|
Notifier.UnRegister;
|
|
inherited;
|
|
end;
|
|
|
|
function TCustomerData.GetCaption(Column: Integer): Variant;
|
|
begin
|
|
case Column of
|
|
0:
|
|
begin
|
|
// Flag it if it is checked
|
|
if FChecked then
|
|
Result := Name + '**'
|
|
else
|
|
Result := Name
|
|
end;
|
|
1: Result := Address;
|
|
2: Result := Phone;
|
|
3: Result := LastContact;
|
|
4: Result := RecordID;
|
|
else
|
|
// Empty the Variant
|
|
Result := ''
|
|
end;
|
|
end;
|
|
|
|
function TCustomerData.GetChecked(Column: Integer): Boolean;
|
|
begin
|
|
if Column = 0 then
|
|
Result := FChecked
|
|
else
|
|
Result := False
|
|
end;
|
|
|
|
function TCustomerData.GetDetail(Line: Integer): Integer;
|
|
begin
|
|
Result := 0;
|
|
case Line of
|
|
0: Result := 0; /// Main Column caption
|
|
1: Result := 3; /// Column 3 caption
|
|
2: Result := 2; /// Column 2 caption
|
|
end
|
|
end;
|
|
|
|
function TCustomerData.GetDetailCount: Integer;
|
|
begin
|
|
Result := 3
|
|
end;
|
|
|
|
function TCustomerData.GetImageIndex(Column: Integer; ImageKind: TEasyImageKind): Integer;
|
|
begin
|
|
Result := -1;
|
|
|
|
case ImageKind of
|
|
eikNormal:
|
|
begin
|
|
if Column < 1 then
|
|
begin
|
|
case BusinessType of
|
|
btIndividual: Result := 0;
|
|
btCompany: Result := 1;
|
|
end;
|
|
end
|
|
end;
|
|
eikOverlay:
|
|
begin
|
|
end;
|
|
eikState:
|
|
begin
|
|
end
|
|
end
|
|
end;
|
|
|
|
procedure TCustomerData.OnRegisterNotify(const ANotifier: IEasyNotificationSink);
|
|
begin
|
|
Notifier := ANotifier
|
|
end;
|
|
|
|
procedure TCustomerData.OnUnRegisterNotify(const ANotifier: IEasyNotificationSink);
|
|
begin
|
|
Notifier := nil
|
|
end;
|
|
|
|
function TCustomerData.SetCaption(Column: Integer; const Value: Variant): Boolean;
|
|
begin
|
|
Result := True;
|
|
case Column of
|
|
0: Name := Value;
|
|
1: Address := Value;
|
|
2: Phone := Value;
|
|
3: LastContact := Value;
|
|
4: RecordID := Value
|
|
end
|
|
end;
|
|
|
|
|
|
procedure TCustomerData.SetChecked(Column: Integer; const Value: Boolean);
|
|
begin
|
|
if Column = 0 then
|
|
begin
|
|
FChecked := Value;
|
|
Notifier.InvalidateItem(True);
|
|
end;
|
|
end;
|
|
|
|
{ TForm1 }
|
|
|
|
procedure TForm1.ComboBox1Change(Sender: TObject);
|
|
begin
|
|
ELV.View := TEasyListStyle(ComboBox1.ItemIndex)
|
|
end;
|
|
|
|
procedure TForm1.Button1Click(Sender: TObject);
|
|
begin
|
|
AddCustomers(1);
|
|
end;
|
|
|
|
procedure TForm1.FormCreate(Sender: TObject);
|
|
begin
|
|
ComboBox1.ItemIndex:= 0;
|
|
end;
|
|
|
|
procedure TForm1.ButtonAddCustomersClick(Sender: TObject);
|
|
begin
|
|
AddCustomers(StrToInt(EditCustomerAddCount.Text));
|
|
end;
|
|
|
|
procedure TForm1.AddCustomers(Count: Integer);
|
|
var
|
|
CustomerData: TCustomerData;
|
|
Group: TEasyGroup;
|
|
i: Integer;
|
|
TickCount: Cardinal;
|
|
begin
|
|
TickCount := GetTickCount;
|
|
ELV.BeginUpdate;
|
|
try
|
|
if ELV.Groups.Count = 0 then
|
|
begin
|
|
Group := ELV.Groups.Add;
|
|
Group.Caption := 'Group 1';
|
|
end else
|
|
Group := ELV.Groups[0];
|
|
|
|
for i := 0 to Count -1 do
|
|
begin
|
|
CustomerData := TCustomerData.Create;
|
|
CustomerData.BusinessType := TBusinessType( Random(2));
|
|
CustomerData.Name := 'New Customer ' + IntToStr(RecordID);
|
|
CustomerData.Address := '123 Elm St. Anytown USA, 99999';
|
|
CustomerData.Phone := '102-555-7890';
|
|
CustomerData.LastContact := Now;
|
|
CustomerData.RecordID := RecordID;
|
|
// Our Data object will freed automatically when the Item is freed
|
|
// because it is decended from TInterfacedObject
|
|
Group.Items.AddInterfaced(CustomerData);
|
|
Inc(RecordID)
|
|
end
|
|
finally
|
|
ELV.Sort.SortAll;
|
|
ELV.EndUpdate;
|
|
Statusbar1.Panels[0].Text := 'Elapsed Time: ' + IntToStr(GetTickCount - TickCount)
|
|
end
|
|
end;
|
|
|
|
procedure TForm1.Button2Click(Sender: TObject);
|
|
var
|
|
TickCount: Cardinal;
|
|
begin
|
|
TickCount := GetTickCount;
|
|
if ELV.Groups.Count > 0 then
|
|
ELV.Groups.Clear;
|
|
Statusbar1.Panels[0].Text := 'Elapsed Time: ' + IntToStr(GetTickCount - TickCount);
|
|
RecordID := 0;
|
|
end;
|
|
|
|
procedure TForm1.ButtonChangeCaptionClick(Sender: TObject);
|
|
begin
|
|
{ if Assigned(LocalData) then
|
|
begin
|
|
LocalData.SetCaption(0, 'John Smith');
|
|
LocalData.SetCaption(1, '4523 WayEasy Way, Coolssville USA, 45687');
|
|
LocalData.SetCaption(2, '406-555-6913');
|
|
LocalData.Notifier.InvalidateItem(True);
|
|
end }
|
|
end;
|
|
|
|
procedure TForm1.ButtonLoadDataClick(Sender: TObject);
|
|
var
|
|
CustomerData: TCustomerData;
|
|
Group: TEasyGroup;
|
|
i: Integer;
|
|
TickCount: Cardinal;
|
|
S: TStringList;
|
|
begin
|
|
S := TStringList.Create;
|
|
S.LoadFromFile('Data.txt');
|
|
TickCount := GetTickCount;
|
|
ELV.BeginUpdate;
|
|
try
|
|
ELV.Groups.Clear;
|
|
Group := ELV.Groups.Add;
|
|
for i := 0 to (S.Count div 3) - 1 do
|
|
begin
|
|
CustomerData := TCustomerData.Create;
|
|
CustomerData.BusinessType := TBusinessType( Random(2));
|
|
CustomerData.Name := S[i*3];
|
|
CustomerData.Address := S[i*3+1];
|
|
CustomerData.Phone := S[i*3+2];
|
|
CustomerData.LastContact := Now;
|
|
CustomerData.RecordID := RecordID;
|
|
// Our Data object will freed automatically when the Item is freed
|
|
// because it is decended from TInterfacedObject
|
|
Group.Items.AddInterfaced(CustomerData);
|
|
Inc(RecordID)
|
|
end
|
|
finally
|
|
ELV.EndUpdate;
|
|
Statusbar1.Panels[0].Text := 'Elapsed Time: ' + IntToStr(GetTickCount - TickCount)
|
|
end;
|
|
S.Free
|
|
end;
|
|
|
|
procedure TForm1.FormShow(Sender: TObject);
|
|
var
|
|
i: Integer;
|
|
Column: TEasyColumn;
|
|
begin
|
|
ComboBox1.ItemIndex := Integer(ELV.View);
|
|
CheckBoxAutoSort.Checked := ELV.Sort.AutoSort;
|
|
ELV.Header.Columns.Clear;
|
|
for i := 0 to High(COLUMNSTRINGS) do
|
|
begin
|
|
Column := ELV.Header.Columns.Add;
|
|
Column.Caption := COLUMNSTRINGS[i];
|
|
Column.Width := COLUMNWIDTHS[i];
|
|
Column.AutoToggleSortGlyph := True;
|
|
end;
|
|
end;
|
|
|
|
procedure TForm1.CheckBoxAutoSortClick(Sender: TObject);
|
|
begin
|
|
ELV.Sort.AutoSort := CheckBoxAutoSort.Checked
|
|
end;
|
|
|
|
end.
|