home *** CD-ROM | disk | FTP | other *** search
-
- {*******************************************************}
- { }
- { Delphi Visual Component Library }
- { }
- { Copyright (c) 1996 Borland International }
- { }
- {*******************************************************}
-
- unit ComCtrls;
-
- {$R-}
-
- interface
-
- uses Messages, Windows, SysUtils, CommCtrl, Classes, Controls, Forms,
- Menus, Graphics, StdCtrls, RichEdit;
-
- type
- TTabChangingEvent = procedure(Sender: TObject;
- var AllowChange: Boolean) of object;
-
- TCustomTabControl = class(TWinControl)
- private
- FTabs: TStrings;
- FSaveTabs: TStringList;
- FSaveTabIndex: Integer;
- FTabSize: TSmallPoint;
- FMultiLine: Boolean;
- FUpdating: Boolean;
- FOnChange: TNotifyEvent;
- FOnChanging: TTabChangingEvent;
- function GetDisplayRect: TRect;
- function GetTabIndex: Integer;
- procedure SetMultiLine(Value: Boolean);
- procedure SetTabHeight(Value: Smallint);
- procedure SetTabIndex(Value: Integer);
- procedure SetTabs(Value: TStrings);
- procedure SetTabWidth(Value: Smallint);
- procedure TabsChanged;
- procedure UpdateTabSize;
- procedure WMDestroy(var Message: TWMDestroy); message WM_DESTROY;
- procedure CMTabStopChanged(var Message: TMessage); message CM_TABSTOPCHANGED;
- procedure CNNotify(var Message: TWMNotify); message CN_NOTIFY;
- protected
- procedure AlignControls(AControl: TControl; var Rect: TRect); override;
- function CanChange: Boolean; dynamic;
- procedure Change; dynamic;
- procedure CreateParams(var Params: TCreateParams); override;
- procedure CreateWnd; override;
- procedure DestroyWnd; override;
- property DisplayRect: TRect read GetDisplayRect;
- property MultiLine: Boolean read FMultiLine write SetMultiLine default False;
- property TabHeight: Smallint read FTabSize.Y write SetTabHeight default 0;
- property TabIndex: Integer read GetTabIndex write SetTabIndex default -1;
- property Tabs: TStrings read FTabs write SetTabs;
- property TabWidth: Smallint read FTabSize.X write SetTabWidth default 0;
- property OnChange: TNotifyEvent read FOnChange write FOnChange;
- property OnChanging: TTabChangingEvent read FOnChanging write FOnChanging;
- public
- constructor Create(AOwner: TComponent); override;
- destructor Destroy; override;
- property TabStop default True;
- end;
-
- TTabControl = class(TCustomTabControl)
- public
- property DisplayRect;
- published
- property Align;
- property DragCursor;
- property DragMode;
- property Enabled;
- property Font;
- property MultiLine;
- property ParentFont;
- property ParentShowHint;
- property PopupMenu;
- property ShowHint;
- property TabHeight;
- property TabIndex;
- property TabOrder;
- property Tabs;
- property TabStop;
- property TabWidth;
- property Visible;
- property OnChange;
- property OnChanging;
- property OnDragDrop;
- property OnDragOver;
- property OnEndDrag;
- property OnEnter;
- property OnExit;
- property OnMouseDown;
- property OnMouseMove;
- property OnMouseUp;
- property OnStartDrag;
- end;
-
- TPageControl = class;
-
- TTabSheet = class(TWinControl)
- private
- FPageControl: TPageControl;
- FTabVisible: Boolean;
- FTabShowing: Boolean;
- function GetPageIndex: Integer;
- function GetTabIndex: Integer;
- procedure SetPageControl(APageControl: TPageControl);
- procedure SetPageIndex(Value: Integer);
- procedure SetTabShowing(Value: Boolean);
- procedure SetTabVisible(Value: Boolean);
- procedure UpdateTabShowing;
- procedure CMTextChanged(var Message: TMessage); message CM_TEXTCHANGED;
- protected
- procedure ReadState(Reader: TReader); override;
- public
- constructor Create(AOwner: TComponent); override;
- destructor Destroy; override;
- property PageControl: TPageControl read FPageControl write SetPageControl;
- property TabIndex: Integer read GetTabIndex;
- published
- property Caption;
- property Enabled;
- property Font;
- property Height stored False;
- property Left stored False;
- property PageIndex: Integer read GetPageIndex write SetPageIndex stored False;
- property ParentFont;
- property ParentShowHint;
- property PopupMenu;
- property ShowHint;
- property TabVisible: Boolean read FTabVisible write SetTabVisible default True;
- property Top stored False;
- property Visible stored False;
- property Width stored False;
- property OnDragDrop;
- property OnDragOver;
- property OnEnter;
- property OnExit;
- property OnMouseDown;
- property OnMouseMove;
- property OnMouseUp;
- end;
-
- TPageControl = class(TCustomTabControl)
- private
- FPages: TList;
- FActivePage: TTabSheet;
- procedure ChangeActivePage(Page: TTabSheet);
- procedure DeleteTab(Page: TTabSheet);
- function GetPage(Index: Integer): TTabSheet;
- function GetPageCount: Integer;
- procedure InsertPage(Page: TTabSheet);
- procedure InsertTab(Page: TTabSheet);
- procedure MoveTab(CurIndex, NewIndex: Integer);
- procedure RemovePage(Page: TTabSheet);
- procedure SetActivePage(Page: TTabSheet);
- procedure UpdateTab(Page: TTabSheet);
- procedure UpdateActivePage;
- procedure CMDesignHitTest(var Message: TCMDesignHitTest); message CM_DESIGNHITTEST;
- procedure CMDialogKey(var Message: TCMDialogKey); message CM_DIALOGKEY;
- protected
- procedure Change; override;
- procedure GetChildren(Proc: TGetChildProc); override;
- procedure SetChildOrder(Child: TComponent; Order: Integer); override;
- procedure ShowControl(AControl: TControl); override;
- public
- constructor Create(AOwner: TComponent); override;
- destructor Destroy; override;
- function FindNextPage(CurPage: TTabSheet;
- GoForward, CheckTabVisible: Boolean): TTabSheet;
- procedure SelectNextPage(GoForward: Boolean);
- property PageCount: Integer read GetPageCount;
- property Pages[Index: Integer]: TTabSheet read GetPage;
- published
- property ActivePage: TTabSheet read FActivePage write SetActivePage;
- property Align;
- property DragCursor;
- property DragMode;
- property Enabled;
- property Font;
- property MultiLine;
- property ParentFont;
- property ParentShowHint;
- property PopupMenu;
- property ShowHint;
- property TabHeight;
- property TabOrder;
- property TabStop;
- property TabWidth;
- property Visible;
- property OnChange;
- property OnChanging;
- property OnDragDrop;
- property OnDragOver;
- property OnEndDrag;
- property OnEnter;
- property OnExit;
- property OnMouseDown;
- property OnMouseMove;
- property OnMouseUp;
- property OnStartDrag;
- end;
-
- TStatusBar = class;
-
- TStatusPanelStyle = (psText, psOwnerDraw);
- TStatusPanelBevel = (pbNone, pbLowered, pbRaised);
-
- TStatusPanel = class(TCollectionItem)
- private
- FText: string;
- FWidth: Integer;
- FAlignment: TAlignment;
- FBevel: TStatusPanelBevel;
- FStyle: TStatusPanelStyle;
- procedure SetAlignment(Value: TAlignment);
- procedure SetBevel(Value: TStatusPanelBevel);
- procedure SetStyle(Value: TStatusPanelStyle);
- procedure SetText(const Value: string);
- procedure SetWidth(Value: Integer);
- public
- constructor Create(Collection: TCollection); override;
- procedure Assign(Source: TPersistent); override;
- published
- property Alignment: TAlignment read FAlignment write SetAlignment default taLeftJustify;
- property Bevel: TStatusPanelBevel read FBevel write SetBevel default pbLowered;
- property Style: TStatusPanelStyle read FStyle write SetStyle default psText;
- property Text: string read FText write SetText;
- property Width: Integer read FWidth write SetWidth;
- end;
-
- TStatusPanels = class(TCollection)
- private
- FStatusBar: TStatusBar;
- function GetItem(Index: Integer): TStatusPanel;
- procedure SetItem(Index: Integer; Value: TStatusPanel);
- protected
- procedure Update(Item: TCollectionItem); override;
- public
- constructor Create(StatusBar: TStatusBar);
- function Add: TStatusPanel;
- property Items[Index: Integer]: TStatusPanel read GetItem write SetItem; default;
- end;
-
- TDrawPanelEvent = procedure(StatusBar: TStatusBar; Panel: TStatusPanel;
- const Rect: TRect) of object;
-
- TStatusBar = class(TWinControl)
- private
- FPanels: TStatusPanels;
- FCanvas: TCanvas;
- FSimpleText: string;
- FSimplePanel: Boolean;
- FSizeGrip: Boolean;
- FOnDrawPanel: TDrawPanelEvent;
- FOnResize: TNotifyEvent;
- procedure SetPanels(Value: TStatusPanels);
- procedure SetSimplePanel(Value: Boolean);
- procedure SetSimpleText(const Value: string);
- procedure SetSizeGrip(Value: Boolean);
- procedure UpdatePanel(Index: Integer);
- procedure UpdatePanels;
- procedure CNDrawItem(var Message: TWMDrawItem); message CN_DRAWITEM;
- procedure WMSize(var Message: TWMSize); message WM_SIZE;
- protected
- procedure CreateParams(var Params: TCreateParams); override;
- procedure CreateWnd; override;
- procedure DrawPanel(Panel: TStatusPanel; const Rect: TRect); dynamic;
- procedure Resize; dynamic;
- public
- constructor Create(AOwner: TComponent); override;
- destructor Destroy; override;
- property Canvas: TCanvas read FCanvas;
- published
- property Align default alBottom;
- property DragCursor;
- property DragMode;
- property Enabled;
- property Font;
- property Panels: TStatusPanels read FPanels write SetPanels;
- property ParentFont;
- property ParentShowHint;
- property PopupMenu;
- property ShowHint;
- property SimplePanel: Boolean read FSimplePanel write SetSimplePanel;
- property SimpleText: string read FSimpleText write SetSimpleText;
- property SizeGrip: Boolean read FSizeGrip write SetSizeGrip default True;
- property Visible;
- property OnClick;
- property OnDblClick;
- property OnDragDrop;
- property OnDragOver;
- property OnEndDrag;
- property OnMouseDown;
- property OnMouseMove;
- property OnMouseUp;
- property OnDrawPanel: TDrawPanelEvent read FOnDrawPanel write FOnDrawPanel;
- property OnResize: TNotifyEvent read FOnResize write FOnResize;
- property OnStartDrag;
- end;
-
- THeaderControl = class;
-
- THeaderSectionStyle = (hsText, hsOwnerDraw);
-
- THeaderSection = class(TCollectionItem)
- private
- FText: string;
- FWidth: Integer;
- FMinWidth: Integer;
- FMaxWidth: Integer;
- FAlignment: TAlignment;
- FStyle: THeaderSectionStyle;
- FAllowClick: Boolean;
- function GetLeft: Integer;
- function GetRight: Integer;
- procedure SetAlignment(Value: TAlignment);
- procedure SetMaxWidth(Value: Integer);
- procedure SetMinWidth(Value: Integer);
- procedure SetStyle(Value: THeaderSectionStyle);
- procedure SetText(const Value: string);
- procedure SetWidth(Value: Integer);
- public
- constructor Create(Collection: TCollection); override;
- procedure Assign(Source: TPersistent); override;
- property Left: Integer read GetLeft;
- property Right: Integer read GetRight;
- published
- property Alignment: TAlignment read FAlignment write SetAlignment default taLeftJustify;
- property AllowClick: Boolean read FAllowClick write FAllowClick default True;
- property MaxWidth: Integer read FMaxWidth write SetMaxWidth default 10000;
- property MinWidth: Integer read FMinWidth write SetMinWidth default 0;
- property Style: THeaderSectionStyle read FStyle write SetStyle default hsText;
- property Text: string read FText write SetText;
- property Width: Integer read FWidth write SetWidth;
- end;
-
- THeaderSections = class(TCollection)
- private
- FHeaderControl: THeaderControl;
- function GetItem(Index: Integer): THeaderSection;
- procedure SetItem(Index: Integer; Value: THeaderSection);
- protected
- procedure Update(Item: TCollectionItem); override;
- public
- constructor Create(HeaderControl: THeaderControl);
- function Add: THeaderSection;
- property Items[Index: Integer]: THeaderSection read GetItem write SetItem; default;
- end;
-
- TSectionTrackState = (tsTrackBegin, tsTrackMove, tsTrackEnd);
-
- TDrawSectionEvent = procedure(HeaderControl: THeaderControl;
- Section: THeaderSection; const Rect: TRect; Pressed: Boolean) of object;
- TSectionNotifyEvent = procedure(HeaderControl: THeaderControl;
- Section: THeaderSection) of object;
- TSectionTrackEvent = procedure(HeaderControl: THeaderControl;
- Section: THeaderSection; Width: Integer;
- State: TSectionTrackState) of object;
-
- THeaderControl = class(TWinControl)
- private
- FSections: THeaderSections;
- FCanvas: TCanvas;
- FOnDrawSection: TDrawSectionEvent;
- FOnResize: TNotifyEvent;
- FOnSectionClick: TSectionNotifyEvent;
- FOnSectionResize: TSectionNotifyEvent;
- FOnSectionTrack: TSectionTrackEvent;
- procedure SetSections(Value: THeaderSections);
- procedure UpdateItem(Message, Index: Integer);
- procedure UpdateSection(Index: Integer);
- procedure UpdateSections;
- procedure CNDrawItem(var Message: TWMDrawItem); message CN_DRAWITEM;
- procedure CNNotify(var Message: TWMNotify); message CN_NOTIFY;
- procedure WMLButtonDown(var Message: TWMLButtonDown); message WM_LBUTTONDOWN;
- procedure WMSize(var Message: TWMSize); message WM_SIZE;
- protected
- procedure CreateParams(var Params: TCreateParams); override;
- procedure CreateWnd; override;
- procedure DrawSection(Section: THeaderSection; const Rect: TRect;
- Pressed: Boolean); dynamic;
- procedure Resize; dynamic;
- procedure SectionClick(Section: THeaderSection); dynamic;
- procedure SectionResize(Section: THeaderSection); dynamic;
- procedure SectionTrack(Section: THeaderSection; Width: Integer;
- State: TSectionTrackState); dynamic;
- public
- constructor Create(AOwner: TComponent); override;
- destructor Destroy; override;
- property Canvas: TCanvas read FCanvas;
- published
- property Align default alTop;
- property DragCursor;
- property DragMode;
- property Enabled;
- property Font;
- property Sections: THeaderSections read FSections write SetSections;
- property ShowHint;
- property ParentFont;
- property ParentShowHint;
- property PopupMenu;
- property Visible;
- property OnDragDrop;
- property OnDragOver;
- property OnEndDrag;
- property OnMouseDown;
- property OnMouseMove;
- property OnMouseUp;
- property OnDrawSection: TDrawSectionEvent read FOnDrawSection write FOnDrawSection;
- property OnResize: TNotifyEvent read FOnResize write FOnResize;
- property OnSectionClick: TSectionNotifyEvent read FOnSectionClick write FOnSectionClick;
- property OnSectionResize: TSectionNotifyEvent read FOnSectionResize write FOnSectionResize;
- property OnSectionTrack: TSectionTrackEvent read FOnSectionTrack write FOnSectionTrack;
- property OnStartDrag;
- end;
-
- { TTreeNode }
-
- TCustomTreeView = class;
- TTreeNodes = class;
-
- TNodeState = (nsCut, nsDropHilited, nsFocused, nsSelected, nsExpanded);
- TNodeAttachMode = (naAdd, naAddFirst, naAddChild, naAddChildFirst, naInsert);
- TAddMode = (taAddFirst, taAdd, taInsert);
-
- PNodeInfo = ^TNodeInfo;
- TNodeInfo = packed record
- ImageIndex: Integer;
- SelectedIndex: Integer;
- StateIndex: Integer;
- OverlayIndex: Integer;
- Data: Pointer;
- Count: Integer;
- Text: string[255];
- end;
-
- TTreeNode = class(TPersistent)
- private
- FOwner: TTreeNodes;
- FText: string;
- FData: Pointer;
- FItemId: HTreeItem;
- FImageIndex: Integer;
- FSelectedIndex: Integer;
- FOverlayIndex: Integer;
- FStateIndex: Integer;
- FDeleting: Boolean;
- procedure ExpandItem(Expand: Boolean; Recurse: Boolean);
- function GetAbsoluteIndex: Integer;
- function GetExpanded: Boolean;
- function GetLevel: Integer;
- function GetParent: TTreeNode;
- function GetChildren: Boolean;
- function GetCut: Boolean;
- function GetDropTarget: Boolean;
- function GetFocused: Boolean;
- function GetIndex: Integer;
- function GetItem(Index: Integer): TTreeNode;
- function GetSelected: Boolean;
- function GetState(NodeState: TNodeState): Boolean;
- function GetCount: Integer;
- function GetTreeView: TCustomTreeView;
- function HasVisibleParent: Boolean;
- procedure InternalMove(ParentNode, Node: TTreeNode; HItem: HTreeItem;
- AddMode: TAddMode);
- function IsEqual(Node: TTreeNode): Boolean;
- function IsNodeVisible: Boolean;
- procedure ReadData(Stream: TStream; Info: PNodeInfo);
- procedure SetChildren(Value: Boolean);
- procedure SetCut(Value: Boolean);
- procedure SetData(Value: Pointer);
- procedure SetDropTarget(Value: Boolean);
- procedure SetItem(Index: Integer; Value: TTreeNode);
- procedure SetExpanded(Value: Boolean);
- procedure SetFocused(Value: Boolean);
- procedure SetImageIndex(Value: Integer);
- procedure SetOverlayIndex(Value: Integer);
- procedure SetSelectedIndex(Value: Integer);
- procedure SetSelected(Value: Boolean);
- procedure SetStateIndex(Value: Integer);
- procedure SetText(const S: string);
- procedure WriteData(Stream: TStream; Info: PNodeInfo);
- public
- constructor Create(AOwner: TTreeNodes);
- destructor Destroy; override;
- function AlphaSort: Boolean;
- procedure Assign(Source: TPersistent); override;
- procedure Collapse(Recurse: Boolean);
- function CustomSort(SortProc: TTVCompare; Data: Longint): Boolean;
- procedure Delete;
- procedure DeleteChildren;
- function DisplayRect(TextOnly: Boolean): TRect;
- function EditText: Boolean;
- procedure EndEdit(Cancel: Boolean);
- procedure Expand(Recurse: Boolean);
- function GetFirstChild: TTreeNode;
- function GetHandle: HWND;
- function GetLastChild: TTreeNode;
- function GetNext: TTreeNode;
- function GetNextChild(Value: TTreeNode): TTreeNode;
- function GetNextSibling: TTreeNode;
- function GetNextVisible: TTreeNode;
- function GetPrev: TTreeNode;
- function GetPrevChild(Value: TTreeNode): TTreeNode;
- function GetPrevSibling: TTreeNode;
- function GetPrevVisible: TTreeNode;
- function HasAsParent(Value: TTreeNode): Boolean;
- function IndexOf(Value: TTreeNode): Integer;
- procedure MakeVisible;
- procedure MoveTo(Destination: TTreeNode; Mode: TNodeAttachMode);
- property AbsoluteIndex: Integer read GetAbsoluteIndex;
- property Count: Integer read GetCount;
- property Cut: Boolean read GetCut write SetCut;
- property Data: Pointer read FData write SetData;
- property Deleting: Boolean read FDeleting;
- property Focused: Boolean read GetFocused write SetFocused;
- property DropTarget: Boolean read GetDropTarget write SetDropTarget;
- property Selected: Boolean read GetSelected write SetSelected;
- property Expanded: Boolean read GetExpanded write SetExpanded;
- property Handle: HWND read GetHandle;
- property HasChildren: Boolean read GetChildren write SetChildren;
- property ImageIndex: Integer read FImageIndex write SetImageIndex;
- property Index: Integer read GetIndex;
- property IsVisible: Boolean read IsNodeVisible;
- property Item[Index: Integer]: TTreeNode read GetItem write SetItem; default;
- property ItemId: HTreeItem read FItemId;
- property Level: Integer read GetLevel;
- property OverlayIndex: Integer read FOverlayIndex write SetOverlayIndex;
- property Owner: TTreeNodes read FOwner;
- property Parent: TTreeNode read GetParent;
- property SelectedIndex: Integer read FSelectedIndex write SetSelectedIndex;
- property StateIndex: Integer read FStateIndex write SetStateIndex;
- property Text: string read FText write SetText;
- property TreeView: TCustomTreeView read GetTreeView;
- end;
-
- { TTreeNodes }
-
- TTreeNodes = class(TPersistent)
- private
- FOwner: TCustomTreeView;
- FUpdateCount: Integer;
- procedure AddedNode(Value: TTreeNode);
- function GetHandle: HWND;
- function GetNodeFromIndex(Index: Integer): TTreeNode;
- procedure ReadData(Stream: TStream);
- procedure Repaint(Node: TTreeNode);
- procedure WriteData(Stream: TStream);
- protected
- function AddItem(Parent, Target: HTreeItem; const Item: TTVItem;
- AddMode: TAddMode): HTreeItem;
- function InternalAddObject(Node: TTreeNode; const S: string;
- Ptr: Pointer; AddMode: TAddMode): TTreeNode;
- procedure DefineProperties(Filer: TFiler); override;
- function CreateItem(Node: TTreeNode): TTVItem;
- function GetCount: Integer;
- procedure SetItem(Index: Integer; Value: TTreeNode);
- procedure SetUpdateState(Updating: Boolean);
- public
- constructor Create(AOwner: TCustomTreeView);
- destructor Destroy; override;
- function AddChildFirst(Node: TTreeNode; const S: string): TTreeNode;
- function AddChild(Node: TTreeNode; const S: string): TTreeNode;
- function AddChildObjectFirst(Node: TTreeNode; const S: string;
- Ptr: Pointer): TTreeNode;
- function AddChildObject(Node: TTreeNode; const S: string;
- Ptr: Pointer): TTreeNode;
- function AddFirst(Node: TTreeNode; const S: string): TTreeNode;
- function Add(Node: TTreeNode; const S: string): TTreeNode;
- function AddObjectFirst(Node: TTreeNode; const S: string;
- Ptr: Pointer): TTreeNode;
- function AddObject(Node: TTreeNode; const S: string;
- Ptr: Pointer): TTreeNode;
- procedure Assign(Source: TPersistent); override;
- procedure BeginUpdate;
- procedure Clear;
- procedure Delete(Node: TTreeNode);
- procedure EndUpdate;
- function GetFirstNode: TTreeNode;
- function GetNode(ItemId: HTreeItem): TTreeNode;
- function Insert(Node: TTreeNode; const S: string): TTreeNode;
- function InsertObject(Node: TTreeNode; const S: string;
- Ptr: Pointer): TTreeNode;
- property Count: Integer read GetCount;
- property Handle: HWND read GetHandle;
- property Item[Index: Integer]: TTreeNode read GetNodeFromIndex; default;
- property Owner: TCustomTreeView read FOwner;
- end;
-
- { TCustomTreeView }
-
- THitTest = (htAbove, htBelow, htNowhere, htOnItem, htOnButton,
- htOnIcon, htOnIndent, htOnLabel, htOnRight,
- htOnStateIcon, htToLeft, htToRight);
- THitTests = set of THitTest;
- ETreeViewError = class(Exception);
-
- TTVChangingEvent = procedure(Sender: TObject; Node: TTreeNode;
- var AllowChange: Boolean) of object;
- TTVChangedEvent = procedure(Sender: TObject; Node: TTreeNode) of object;
- TTVEditingEvent = procedure(Sender: TObject; Node: TTreeNode;
- var AllowEdit: Boolean) of object;
- TTVEditedEvent = procedure(Sender: TObject; Node: TTreeNode; var S: string) of object;
- TTVExpandingEvent = procedure(Sender: TObject; Node: TTreeNode;
- var AllowExpansion: Boolean) of object;
- TTVCollapsingEvent = procedure(Sender: TObject; Node: TTreeNode;
- var AllowCollapse: Boolean) of object;
- TTVExpandedEvent = procedure(Sender: TObject; Node: TTreeNode) of object;
- TTVCompareEvent = procedure(Sender: TObject; Node1, Node2: TTreeNode;
- Data: Integer; var Compare: Integer) of object;
-
- TSortType = (stNone, stData, stText, stBoth);
-
- TCustomTreeView = class(TWinControl)
- private
- FShowLines: Boolean;
- FShowRoot: Boolean;
- FShowButtons: Boolean;
- FBorderStyle: TBorderStyle;
- FReadOnly: Boolean;
- FImages: TImageList;
- FStateImages: TImageList;
- FImageChangeLink: TChangeLink;
- FStateChangeLink: TChangeLink;
- FDragImage: TImageList;
- FTreeNodes: TTreeNodes;
- FSortType: TSortType;
- FSaveItems: TStringList;
- FSaveTopIndex: Integer;
- FSaveIndex: Integer;
- FSaveIndent: Integer;
- FHideSelection: Boolean;
- FMemStream: TMemoryStream;
- FEditInstance: Pointer;
- FDefEditProc: Pointer;
- FEditHandle: HWND;
- FDragged: Boolean;
- FRClicked: Boolean;
- FLastDropTarget: TTreeNode;
- FDragNode: TTreeNode;
- FOnEditing: TTVEditingEvent;
- FOnEdited: TTVEditedEvent;
- FOnExpanded: TTVExpandedEvent;
- FOnExpanding: TTVExpandingEvent;
- FOnCollapsed: TTVExpandedEvent;
- FOnCollapsing: TTVCollapsingEvent;
- FOnChanging: TTVChangingEvent;
- FOnChange: TTVChangedEvent;
- FOnCompare: TTVCompareEvent;
- FOnDeletion: TTVExpandedEvent;
- FOnGetImageIndex: TTVExpandedEvent;
- FOnGetSelectedIndex: TTVExpandedEvent;
- procedure CMColorChanged(var Message: TMessage); message CM_COLORCHANGED;
- procedure CMCtl3DChanged(var Message: TMessage); message CM_CTL3DCHANGED;
- procedure CMDrag(var Message: TCMDrag); message CM_DRAG;
- procedure CNNotify(var Message: TWMNotify); message CN_NOTIFY;
- procedure EditWndProc(var Message: TMessage);
- procedure DoDragOver(Source: TDragObject; X, Y: Integer);
- procedure GetImageIndex(Node: TTreeNode);
- procedure GetSelectedIndex(Node: TTreeNode);
- function GetDropTarget: TTreeNode;
- function GetIndent: Integer;
- function GetNodeFromItem(const Item: TTVItem): TTreeNode;
- function GetSelection: TTreeNode;
- function GetTopItem: TTreeNode;
- procedure ImageListChange(Sender: TObject);
- procedure SetBorderStyle(Value: TBorderStyle);
- procedure SetButtonStyle(Value: Boolean);
- procedure SetDropTarget(Value: TTreeNode);
- procedure SetHideSelection(Value: Boolean);
- procedure SetImageList(Value: HImageList; Flags: Integer);
- procedure SetIndent(Value: Integer);
- procedure SetImages(Value: TImageList);
- procedure SetLineStyle(Value: Boolean);
- procedure SetReadOnly(Value: Boolean);
- procedure SetRootStyle(Value: Boolean);
- procedure SetSelection(Value: TTreeNode);
- procedure SetSortType(Value: TSortType);
- procedure SetStateImages(Value: TImageList);
- procedure SetStyle(Value: Integer; UseStyle: Boolean);
- procedure SetTreeNodes(Value: TTreeNodes);
- procedure SetTopItem(Value: TTreeNode);
- procedure WMLButtonDown(var Message: TWMLButtonDown); message WM_LBUTTONDOWN;
- procedure WMRButtonDown(var Message: TWMRButtonDown); message WM_RBUTTONDOWN;
- protected
- function CanEdit(Node: TTreeNode): Boolean; dynamic;
- function CanChange(Node: TTreeNode): Boolean; dynamic;
- function CanCollapse(Node: TTreeNode): Boolean; dynamic;
- function CanExpand(Node: TTreeNode): Boolean; dynamic;
- procedure Change(Node: TTreeNode); dynamic;
- procedure Collapse(Node: TTreeNode); dynamic;
- function CreateNode: TTreeNode; virtual;
- procedure CreateParams(var Params: TCreateParams); override;
- procedure CreateWnd; override;
- procedure DestroyWnd; override;
- procedure DoEndDrag(Target: TObject; X, Y: Integer); dynamic;
- procedure DoStartDrag(var DragObject: TDragObject); override;
- procedure Edit(const Item: TTVItem); dynamic;
- procedure Expand(Node: TTreeNode); dynamic;
- function GetDragImages: TCustomImageList; override;
- procedure Loaded; override;
- procedure Notification(AComponent: TComponent;
- Operation: TOperation); override;
- procedure SetDragMode(Value: TDragMode); override;
- procedure WndProc(var Message: TMessage); override;
- property OnEditing: TTVEditingEvent read FOnEditing write FOnEditing;
- property OnEdited: TTVEditedEvent read FOnEdited write FOnEdited;
- property OnExpanding: TTVExpandingEvent read FOnExpanding write FOnExpanding;
- property OnExpanded: TTVExpandedEvent read FOnExpanded write FOnExpanded;
- property OnCollapsing: TTVCollapsingEvent read FOnCollapsing write FOnCollapsing;
- property OnCollapsed: TTVExpandedEvent read FOnCollapsed write FOnCollapsed;
- property OnChanging: TTVChangingEvent read FOnChanging write FOnChanging;
- property OnChange: TTVChangedEvent read FOnChange write FOnChange;
- property OnCompare: TTVCompareEvent read FOnCompare write FOnCompare;
- property OnDeletion: TTVExpandedEvent read FOnDeletion write FOnDeletion;
- property OnGetImageIndex: TTVExpandedEvent read FOnGetImageIndex write FOnGetImageIndex;
- property OnGetSelectedIndex: TTVExpandedEvent read FOnGetSelectedIndex write FOnGetSelectedIndex;
- property ShowButtons: Boolean read FShowButtons write SetButtonStyle default True;
- property BorderStyle: TBorderStyle read FBorderStyle write SetBorderStyle default bsSingle;
- property ShowLines: Boolean read FShowLines write SetLineStyle default True;
- property ShowRoot: Boolean read FShowRoot write SetRootStyle default True;
- property ReadOnly: Boolean read FReadOnly write SetReadOnly default False;
- property Indent: Integer read GetIndent write SetIndent;
- property Items: TTreeNodes read FTreeNodes write SetTreeNodes;
- property SortType: TSortType read FSortType write SetSortType default stNone;
- property HideSelection: Boolean read FHideSelection write SetHideSelection default True;
- property Images: TImageList read FImages write SetImages;
- property StateImages: TImageList read FStateImages write SetStateImages;
- public
- constructor Create(AOwner: TComponent); override;
- destructor Destroy; override;
- function AlphaSort: Boolean;
- function CustomSort(SortProc: TTVCompare; Data: Longint): Boolean;
- procedure FullCollapse;
- procedure FullExpand;
- function GetHitTestInfoAt(X, Y: Integer): THitTests;
- function GetNodeAt(X, Y: Integer): TTreeNode;
- function IsEditing: Boolean;
- procedure LoadFromFile(const FileName: string);
- procedure LoadFromStream(Stream: TStream);
- procedure SaveToFile(const FileName: string);
- procedure SaveToStream(Stream: TStream);
- property DropTarget: TTreeNode read GetDropTarget write SetDropTarget;
- property Selected: TTreeNode read GetSelection write SetSelection;
- property TopItem: TTreeNode read GetTopItem write SetTopItem;
- end;
-
- TTreeView = class(TCustomTreeView)
- published
- property ShowButtons;
- property BorderStyle;
- property DragCursor;
- property ShowLines;
- property ShowRoot;
- property ReadOnly;
- property DragMode;
- property HideSelection;
- property Indent;
- property Items;
- property OnEditing;
- property OnEdited;
- property OnExpanding;
- property OnExpanded;
- property OnCollapsing;
- property OnCompare;
- property OnCollapsed;
- property OnChanging;
- property OnChange;
- property OnDeletion;
- property OnGetImageIndex;
- property OnGetSelectedIndex;
- property Align;
- property Enabled;
- property Font;
- property Color;
- property ParentColor;
- property ParentCtl3D;
- property Ctl3D;
- property SortType;
- property TabOrder;
- property TabStop default True;
- property Visible;
- property OnClick;
- property OnEnter;
- property OnExit;
- property OnDragDrop;
- property OnDragOver;
- property OnStartDrag;
- property OnEndDrag;
- property OnMouseDown;
- property OnMouseMove;
- property OnMouseUp;
- property OnDblClick;
- property OnKeyDown;
- property OnKeyPress;
- property OnKeyUp;
- property PopupMenu;
- property ParentFont;
- property ParentShowHint;
- property ShowHint;
- property Images;
- property StateImages;
- end;
-
- { TTrackBar }
-
- TTrackBarOrientation = (trHorizontal, trVertical);
- TTickMark = (tmBottomRight, tmTopLeft, tmBoth);
- TTickStyle = (tsNone, tsAuto, tsManual);
-
- TTrackBar = class(TWinControl)
- private
- FOrientation: TTrackBarOrientation;
- FTickMarks: TTickMark;
- FTickStyle: TTickStyle;
- FLineSize: Integer;
- FPageSize: Integer;
- FMin: Integer;
- FMax: Integer;
- FFrequency: Integer;
- FPosition: Integer;
- FSelStart: Integer;
- FSelEnd: Integer;
- FOnChange: TNotifyEvent;
-
- procedure SetOrientation(Value: TTrackBarOrientation);
- procedure SetParams(APosition, AMin, AMax: Integer);
- procedure SetPosition(Value: Integer);
- procedure SetMin(Value: Integer);
- procedure SetMax(Value: Integer);
- procedure SetFrequency(Value: Integer);
- procedure SetTickStyle(Value: TTickStyle);
- procedure SetTickMarks(Value: TTickMark);
- procedure SetLineSize(Value: Integer);
- procedure SetPageSize(Value: Integer);
- procedure SetSelStart(Value: Integer);
- procedure SetSelEnd(Value: Integer);
- procedure UpdateSelection;
-
- procedure CNHScroll(var Message: TWMHScroll); message CN_HSCROLL;
- procedure CNVScroll(var Message: TWMVScroll); message CN_VSCROLL;
- protected
- procedure CreateParams(var Params: TCreateParams); override;
- procedure CreateWnd; override;
- procedure DestroyWnd; override;
- public
- constructor Create(AOwner: TComponent); override;
- procedure SetTick(Value: Integer);
- published
- property Ctl3D;
- property DragCursor;
- property DragMode;
- property Enabled;
- property LineSize: Integer read FLineSize write SetLineSize default 1;
- property Max: Integer read FMax write SetMax default 10;
- property Min: Integer read FMin write SetMin default 0;
- property Orientation: TTrackBarOrientation read FOrientation write SetOrientation;
- property ParentCtl3D;
- property ParentShowHint;
- property PageSize: Integer read FPageSize write SetPageSize default 2;
- property PopupMenu;
- property Frequency: Integer read FFrequency write SetFrequency;
- property Position: Integer read FPosition write SetPosition;
- property SelEnd: Integer read FSelEnd write SetSelEnd;
- property SelStart: Integer read FSelStart write SetSelStart;
- property ShowHint;
- property TabOrder;
- property TabStop default True;
- property TickMarks: TTickMark read FTickMarks write SetTickMarks;
- property TickStyle: TTickStyle read FTickStyle write SetTickStyle;
- property Visible;
- property OnChange: TNotifyEvent read FOnChange write FOnChange;
- property OnDragDrop;
- property OnDragOver;
- property OnEndDrag;
- property OnEnter;
- property OnExit;
- property OnKeyDown;
- property OnKeyPress;
- property OnKeyUp;
- property OnStartDrag;
- end;
-
- { TProgressBar }
-
- TProgressRange = 0..65535; // max & position limitation of Progess Bar
- TProgressBar = class(TWinControl)
- private
- FMin: TProgressRange;
- FMax: TProgressRange;
- FStep: TProgressRange;
- FPosition: TProgressRange;
- function GetPosition: TProgressRange;
- procedure SetParams(AMin, AMax: TProgressRange);
- procedure SetMin(Value: TProgressRange);
- procedure SetMax(Value: TProgressRange);
- procedure SetPosition(Value: TProgressRange);
- procedure SetStep(Value: TProgressRange);
- protected
- procedure CreateParams(var Params: TCreateParams); override;
- procedure CreateWnd; override;
- public
- constructor Create(AOwner: TComponent); override;
- procedure StepIt;
- procedure StepBy(Delta: TProgressRange);
- published
- property Align;
- property Enabled;
- property Hint;
- property Min: TProgressRange read FMin write SetMin;
- property Max: TProgressRange read FMax write SetMax;
- property ParentShowHint;
- property PopupMenu;
- property Position: TProgressRange read GetPosition write SetPosition default 0;
- property Step: TProgressRange read FStep write SetStep default 10;
- property ShowHint;
- property TabOrder;
- property TabStop;
- property Visible;
- property OnDragDrop;
- property OnDragOver;
- property OnEndDrag;
- property OnEnter;
- property OnExit;
- property OnMouseDown;
- property OnMouseMove;
- property OnMouseUp;
- property OnStartDrag;
- end;
-
- { TTextAttributes }
-
- TCustomRichEdit = class;
-
- TAttributeType = (atSelected, atDefaultText);
- TConsistentAttribute = (caBold, caColor, caFace, caItalic,
- caSize, caStrikeOut, caUnderline, caProtected);
- TConsistentAttributes = set of TConsistentAttribute;
-
- TTextAttributes = class(TPersistent)
- private
- RichEdit: TCustomRichEdit;
- FType: TAttributeType;
- procedure GetAttributes(var Format: TCharFormat);
- function GetColor: TColor;
- function GetConsistentAttributes: TConsistentAttributes;
- function GetHeight: Integer;
- function GetName: TFontName;
- function GetPitch: TFontPitch;
- function GetProtected: Boolean;
- function GetSize: Integer;
- function GetStyle: TFontStyles;
- procedure SetAttributes(var Format: TCharFormat);
- procedure SetColor(Value: TColor);
- procedure SetHeight(Value: Integer);
- procedure SetName(Value: TFontName);
- procedure SetPitch(Value: TFontPitch);
- procedure SetProtected(Value: Boolean);
- procedure SetSize(Value: Integer);
- procedure SetStyle(Value: TFontStyles);
- protected
- procedure InitFormat(var Format: TCharFormat);
- procedure AssignTo(Dest: TPersistent); override;
- public
- constructor Create(AOwner: TCustomRichEdit; AttributeType: TAttributeType);
- procedure Assign(Source: TPersistent); override;
- property Color: TColor read GetColor write SetColor;
- property ConsistentAttributes: TConsistentAttributes read GetConsistentAttributes;
- property Name: TFontName read GetName write SetName;
- property Pitch: TFontPitch read GetPitch write SetPitch;
- property Protected: Boolean read GetProtected write SetProtected;
- property Size: Integer read GetSize write SetSize;
- property Style: TFontStyles read GetStyle write SetStyle;
- property Height: Integer read GetHeight write SetHeight;
- end;
-
- { TParaAttributes }
-
- TNumberingStyle = (nsNone, nsBullet);
-
- TParaAttributes = class(TPersistent)
- private
- RichEdit: TCustomRichEdit;
- procedure GetAttributes(var Paragraph: TParaFormat);
- function GetAlignment: TAlignment;
- function GetFirstIndent: Longint;
- function GetLeftIndent: Longint;
- function GetRightIndent: Longint;
- function GetNumbering: TNumberingStyle;
- function GetTab(Index: Byte): Longint;
- function GetTabCount: Integer;
- procedure InitPara(var Paragraph: TParaFormat);
- procedure SetAlignment(Value: TAlignment);
- procedure SetAttributes(var Paragraph: TParaFormat);
- procedure SetFirstIndent(Value: Longint);
- procedure SetLeftIndent(Value: Longint);
- procedure SetRightIndent(Value: Longint);
- procedure SetNumbering(Value: TNumberingStyle);
- procedure SetTab(Index: Byte; Value: Longint);
- procedure SetTabCount(Value: Integer);
- public
- constructor Create(AOwner: TCustomRichEdit);
- procedure Assign(Source: TPersistent); override;
- property Alignment: TAlignment read GetAlignment write SetAlignment;
- property FirstIndent: Longint read GetFirstIndent write SetFirstIndent;
- property LeftIndent: Longint read GetLeftIndent write SetLeftIndent;
- property Numbering: TNumberingStyle read GetNumbering write SetNumbering;
- property RightIndent: Longint read GetRightIndent write SetRightIndent;
- property Tab[Index: Byte]: Longint read GetTab write SetTab;
- property TabCount: Integer read GetTabCount write SetTabCount;
- end;
-
- { TCustomRichEdit }
-
- TRichEditResizeEvent = procedure(Sender: TObject; Rect: TRect) of object;
- TRichEditProtectChange = procedure(Sender: TObject;
- StartPos, EndPos: Integer; var AllowChange: Boolean) of object;
- TRichEditSaveClipboard = procedure(Sender: TObject;
- NumObjects, NumChars: Integer; var SaveClipboard: Boolean) of object;
- TSearchType = (stWholeWord, stMatchCase);
- TSearchTypes = set of TSearchType;
-
- TConversion = class(TObject)
- public
- function ConvertReadStream(Stream: TStream; Buffer: PChar; BufSize: Integer): Integer; virtual;
- function ConvertWriteStream(Stream: TStream; Buffer: PChar; BufSize: Integer): Integer; virtual;
- end;
-
- TConversionClass = class of TConversion;
-
- PConversionFormat = ^TConversionFormat;
- TConversionFormat = record
- ConversionClass: TConversionClass;
- Extension: string;
- Next: PConversionFormat;
- end;
-
- PRichEditStreamInfo = ^TRichEditStreamInfo;
- TRichEditStreamInfo = record
- Converter: TConversion;
- Stream: TStream;
- end;
-
- TCustomRichEdit = class(TCustomMemo)
- private
- FLibHandle: THandle;
- FHideScrollBars: Boolean;
- FSelAttributes: TTextAttributes;
- FDefAttributes: TTextAttributes;
- FParagraph: TParaAttributes;
- FScreenLogPixels: Integer;
- FRichEditStrings: TStrings;
- FMemStream: TMemoryStream;
- FOnSelChange: TNotifyEvent;
- FHideSelection: Boolean;
- FModified: Boolean;
- FDefaultConverter: TConversionClass;
- FOnResizeRequest: TRichEditResizeEvent;
- FOnProtectChange: TRichEditProtectChange;
- FOnSaveClipboard: TRichEditSaveClipboard;
- FPageRect: TRect;
- procedure CMColorChanged(var Message: TMessage); message CM_COLORCHANGED;
- procedure CMFontChanged(var Message: TMessage); message CM_FONTCHANGED;
- procedure CNNotify(var Message: TWMNotify); message CN_NOTIFY;
- function GetPlainText: Boolean;
- function ProtectChange(StartPos, EndPos: Integer): Boolean;
- function SaveClipboard(NumObj, NumChars: Integer): Boolean;
- procedure SetHideScrollBars(Value: Boolean);
- procedure SetHideSelection(Value: Boolean);
- procedure SetPlainText(Value: Boolean);
- procedure SetRichEditStrings(Value: TStrings);
- procedure SetDefAttributes(Value: TTextAttributes);
- procedure SetSelAttributes(Value: TTextAttributes);
- procedure WMNCDestroy(var Message: TWMNCDestroy); message WM_NCDESTROY;
- procedure WMSetCursor(var Message: TWMSetCursor); message WM_SETCURSOR;
- procedure WMPaint(var Message: TWMPaint); message WM_PAINT;
- procedure WMSetFont(var Message: TWMSetFont); message WM_SETFONT;
- protected
- procedure CreateParams(var Params: TCreateParams); override;
- procedure CreateWnd; override;
- procedure DestroyWnd; override;
- procedure RequestSize(const Rect: TRect); virtual;
- procedure SelectionChange; dynamic;
- property HideSelection: Boolean read FHideSelection write SetHideSelection default True;
- property HideScrollBars: Boolean read FHideScrollBars
- write SetHideScrollBars default True;
- property Lines: TStrings read FRichEditStrings write SetRichEditStrings;
- property OnSaveClipboard: TRichEditSaveClipboard read FOnSaveClipboard
- write FOnSaveClipboard;
- property OnSelectionChange: TNotifyEvent read FOnSelChange write FOnSelChange;
- property OnProtectChange: TRichEditProtectChange read FOnProtectChange
- write FOnProtectChange;
- property OnResizeRequest: TRichEditResizeEvent read FOnResizeRequest
- write FOnResizeRequest;
- property PlainText: Boolean read GetPlainText write SetPlainText default False;
- public
- constructor Create(AOwner: TComponent); override;
- destructor Destroy; override;
- function FindText(const SearchStr: string;
- StartPos, Length: Integer; Options: TSearchTypes): Integer;
- procedure Print(const Caption: string);
- class procedure RegisterConversionFormat(const AExtension: string;
- AConversionClass: TConversionClass);
- property DefaultConverter: TConversionClass
- read FDefaultConverter write FDefaultConverter;
- property DefAttributes: TTextAttributes read FDefAttributes write SetDefAttributes;
- property SelAttributes: TTextAttributes read FSelAttributes write SetSelAttributes;
- property PageRect: TRect read FPageRect write FPageRect;
- property Paragraph: TParaAttributes read FParagraph;
- end;
-
- TRichEdit = class(TCustomRichEdit)
- published
- property Align;
- property Alignment;
- property BorderStyle;
- property Color;
- property Ctl3D;
- property DragMode;
- property Enabled;
- property Font;
- property HideSelection;
- property HideScrollBars;
- property Lines;
- property MaxLength;
- property ParentColor;
- property ParentCtl3D;
- property ParentFont;
- property PlainText;
- property PopupMenu;
- property ReadOnly;
- property ScrollBars;
- property ShowHint;
- property TabOrder;
- property TabStop default True;
- property Visible;
- property WantTabs;
- property WantReturns;
- property WordWrap;
- property OnChange;
- property OnDragDrop;
- property OnDragOver;
- property OnEndDrag;
- property OnEnter;
- property OnExit;
- property OnKeyDown;
- property OnKeyPress;
- property OnKeyUp;
- property OnMouseDown;
- property OnMouseMove;
- property OnMouseUp;
- property OnResizeRequest;
- property OnSelectionChange;
- property OnStartDrag;
- property OnProtectChange;
- property OnSaveClipboard;
- end;
-
- { TUpDown }
-
- TUDAlignButton = (udLeft, udRight);
- TUDOrientation = (udHorizontal, udVertical);
- TUDBtnType = (btNext, btPrev);
- TUDClickEvent = procedure (Sender: TObject; Button: TUDBtnType) of object;
- TUDChangingEvent = procedure (Sender: TObject; var AllowChange: Boolean) of object;
-
- TCustomUpDown = class(TWinControl)
- private
- FArrowKeys: Boolean;
- FAssociate: TWinControl;
- FMin: SmallInt;
- FMax: SmallInt;
- FIncrement: Integer;
- FPosition: SmallInt;
- FThousands: Boolean;
- FWrap: Boolean;
- FOnClick: TUDClickEvent;
- FAlignButton: TUDAlignButton;
- FOrientation: TUDOrientation;
- FOnChanging: TUDChangingEvent;
- procedure UndoAutoResizing(Value: TWinControl);
- procedure SetAssociate(Value: TWinControl);
- function GetPosition: SmallInt;
- procedure SetMin(Value: SmallInt);
- procedure SetMax(Value: SmallInt);
- procedure SetIncrement(Value: Integer);
- procedure SetPosition(Value: SmallInt);
- procedure SetAlignButton(Value: TUDAlignButton);
- procedure SetOrientation(Value: TUDOrientation);
- procedure SetArrowKeys(Value: Boolean);
- procedure SetThousands(Value: Boolean);
- procedure SetWrap(Value: Boolean);
- procedure CNNotify(var Message: TWMNotify); message CN_NOTIFY;
- procedure WMHScroll(var Message: TWMHScroll); message CN_HSCROLL;
- procedure WMVScroll(var Message: TWMVScroll); message CN_VSCROLL;
- protected
- function CanChange: Boolean;
- procedure CreateParams(var Params: TCreateParams); override;
- procedure CreateWnd; override;
- procedure Notification(AComponent: TComponent; Operation: TOperation); override;
- procedure Click(Button: TUDBtnType); dynamic;
- property AlignButton: TUDAlignButton read FAlignButton write SetAlignButton default udRight;
- property ArrowKeys: Boolean read FArrowKeys write SetArrowKeys default True;
- property Associate: TWinControl read FAssociate write SetAssociate;
- property Min: SmallInt read FMin write SetMin;
- property Max: SmallInt read FMax write SetMax default 100;
- property Increment: Integer read FIncrement write SetIncrement default 1;
- property Orientation: TUDOrientation read FOrientation write SetOrientation default udVertical;
- property Position: SmallInt read GetPosition write SetPosition;
- property Thousands: Boolean read FThousands write SetThousands default True;
- property Wrap: Boolean read FWrap write SetWrap;
- property OnChanging: TUDChangingEvent read FOnChanging write FOnChanging;
- property OnClick: TUDClickEvent read FOnClick write FOnClick;
- public
- constructor Create(AOwner: TComponent); override;
- end;
-
- TUpDown = class(TCustomUpDown)
- published
- property AlignButton;
- property Associate;
- property ArrowKeys;
- property Enabled;
- property Hint;
- property Min;
- property Max;
- property Increment;
- property Orientation;
- property ParentShowHint;
- property PopupMenu;
- property Position;
- property ShowHint;
- property TabOrder;
- property TabStop;
- property Thousands;
- property Visible;
- property Wrap;
- property OnChanging;
- property OnClick;
- property OnEnter;
- property OnExit;
- property OnMouseDown;
- property OnMouseMove;
- property OnMouseUp;
- end;
-
- { THotKey }
-
- THKModifier = (hkShift, hkCtrl, hkAlt, hkExt);
- THKModifiers = set of THKModifier;
- THKInvalidKey = (hcNone, hcShift, hcCtrl, hcAlt, hcShiftCtrl,
- hcShiftAlt, hcCtrlAlt, hcShiftCtrlAlt);
- THKInvalidKeys = set of THKInvalidKey;
-
- TCustomHotKey = class(TWinControl)
- private
- FAutoSize: Boolean;
- FModifiers: THKModifiers;
- FInvalidKeys: THKInvalidKeys;
- FHotKey: Word;
- FShiftState: TShiftState;
- procedure AdjustHeight;
- procedure SetAutoSize(Value: Boolean);
- procedure SetInvalidKeys(Value: THKInvalidKeys);
- procedure SetModifiers(Value: THKModifiers);
- procedure UpdateHeight;
- function GetHotKey: TShortCut;
- procedure SetHotKey(Value: TShortCut);
- procedure ShortCutToHotKey(Value: TShortCut);
- function HotKeyToShortCut(Value: Longint): TShortCut;
- protected
- procedure CreateParams(var Params: TCreateParams); override;
- procedure CreateWnd; override;
- property AutoSize: Boolean read FAutoSize write SetAutoSize default True;
- property InvalidKeys: THKInvalidKeys read FInvalidKeys write SetInvalidKeys;
- property Modifiers: THKModifiers read FModifiers write SetModifiers;
- property HotKey: TShortCut read GetHotKey write SetHotKey;
- property TabStop default True;
- public
- constructor Create(AOwner: TComponent); override;
- end;
-
- THotKey = class(TCustomHotKey)
- published
- property AutoSize;
- property Enabled;
- property Hint;
- property HotKey;
- property InvalidKeys;
- property Modifiers;
- property ParentShowHint;
- property PopupMenu;
- property ShowHint;
- property TabOrder;
- property TabStop;
- property Visible;
- property OnEnter;
- property OnExit;
- property OnMouseDown;
- property OnMouseMove;
- property OnMouseUp;
- end;
-
- const
- ColumnHeaderWidth = LVSCW_AUTOSIZE_USEHEADER;
- ColumnTextWidth = LVSCW_AUTOSIZE;
-
- type
- TListColumns = class;
- TListItems = class;
- TCustomListView = class;
- TWidth = ColumnHeaderWidth..MaxInt;
-
- TListColumn = class(TCollectionItem)
- private
- FCaption: string;
- FAlignment: TAlignment;
- FWidth: TWidth;
- procedure DoChange;
- function GetWidth: TWidth;
- procedure ReadData(Reader: TReader);
- procedure SetAlignment(Value: TAlignment);
- procedure SetCaption(const Value: string);
- procedure SetWidth(Value: TWidth);
- procedure WriteData(Writer: TWriter);
- protected
- procedure DefineProperties(Filer: TFiler); override;
- public
- constructor Create(Collection: TCollection); override;
- destructor Destroy; override;
- procedure Assign(Source: TPersistent); override;
- property WidthType: TWidth read FWidth;
- published
- property Alignment: TAlignment read FAlignment write SetAlignment default taLeftJustify;
- property Caption: string read FCaption write SetCaption;
- property Width: TWidth read GetWidth write SetWidth default 50;
- end;
-
- TListColumns = class(TCollection)
- private
- FOwner: TCustomListView;
- function GetItem(Index: Integer): TListColumn;
- procedure SetItem(Index: Integer; Value: TListColumn);
- protected
- procedure Update(Item: TCollectionItem); override;
- public
- constructor Create(AOwner: TCustomListView);
- function Add: TListColumn;
- property Owner: TCustomListView read FOwner;
- property Items[Index: Integer]: TListColumn read GetItem write SetItem; default;
- end;
-
- TDisplayCode = (drBounds, drIcon, drLabel, drSelectBounds);
-
- { TListItem }
-
- TListItem = class(TPersistent)
- private
- FOwner: TListItems;
- FSubItems: TStrings;
- FData: Pointer;
- FImageIndex: Integer;
- FOverlayIndex: Integer;
- FStateIndex: Integer;
- FCaption: string;
- FDeleting: Boolean;
- FProcessedDeleting: Boolean;
- function GetHandle: HWND;
- function GetIndex: Integer;
- function GetListView: TCustomListView;
- function GetLeft: Integer;
- function GetState(Index: Integer): Boolean;
- function GetTop: Integer;
- function IsEqual(Item: TListItem): Boolean;
- procedure SetCaption(const Value: string);
- procedure SetData(Value: Pointer);
- procedure SetImage(Index: Integer; Value: Integer);
- procedure SetLeft(Value: Integer);
- procedure SetState(Index: Integer; State: Boolean);
- procedure SetSubItems(Value: TStrings);
- procedure SetTop(Value: Integer);
- protected
- procedure Assign(Source: TPersistent); override;
- public
- constructor Create(AOwner: TListItems);
- destructor Destroy; override;
- procedure CancelEdit;
- procedure Delete;
- function DisplayRect(Code: TDisplayCode): TRect;
- function EditCaption: Boolean;
- function GetPosition: TPoint;
- procedure MakeVisible(PartialOK: Boolean);
- procedure Update;
- procedure SetPosition(const Value: TPoint);
- property Caption: string read FCaption write SetCaption;
- property Cut: Boolean index 0 read GetState write SetState;
- property Data: Pointer read FData write SetData;
- property DropTarget: Boolean index 1 read GetState write SetState;
- property Focused: Boolean index 2 read GetState write SetState;
- property Handle: HWND read GetHandle;
- property ImageIndex: Integer index 0 read FImageIndex write SetImage;
- property Index: Integer read GetIndex;
- property Left: Integer read GetLeft write SetLeft;
- property ListView: TCustomListView read GetListView;
- property Owner: TListItems read FOwner;
- property OverlayIndex: Integer index 1 read FOverlayIndex write SetImage;
- property Selected: Boolean index 3 read GetState write SetState;
- property StateIndex: Integer index 2 read FStateIndex write SetImage;
- property SubItems: TStrings read FSubItems write SetSubItems;
- property Top: Integer read GetTop write SetTop;
- end;
-
- { TListItems }
-
- TListItems = class(TPersistent)
- private
- FOwner: TCustomListView;
- FUpdateCount: Integer;
- FNoRedraw: Boolean;
- procedure ReadData(Stream: TStream);
- procedure WriteData(Stream: TStream);
- protected
- procedure DefineProperties(Filer: TFiler); override;
- function CreateItem(Index: Integer; ListItem: TListItem): TLVItem;
- function GetCount: Integer;
- function GetHandle: HWND;
- function GetItem(Index: Integer): TListItem;
- procedure SetItem(Index: Integer; Value: TListItem);
- procedure SetUpdateState(Updating: Boolean);
- public
- constructor Create(AOwner: TCustomListView);
- destructor Destroy; override;
- function Add: TListItem;
- procedure Assign(Source: TPersistent); override;
- procedure BeginUpdate;
- procedure Clear;
- procedure Delete(Index: Integer);
- procedure EndUpdate;
- function IndexOf(Value: TListItem): Integer;
- function Insert(Index: Integer): TListItem;
- property Count: Integer read GetCount;
- property Handle: HWND read GetHandle;
- property Item[Index: Integer]: TListItem read GetItem write SetItem; default;
- property Owner: TCustomListView read FOwner;
- end;
-
- { TIconOptions }
- TIconArrangement = (iaTop, iaLeft);
-
- TIconOptions = class(TPersistent)
- private
- FListView: TCustomListView;
- FArrangement: TIconArrangement;
- FAutoArrange: Boolean;
- FWrapText: Boolean;
- procedure SetArrangement(Value: TIconArrangement);
- procedure SetAutoArrange(Value: Boolean);
- procedure SetWrapText(Value: Boolean);
- public
- constructor Create(AOwner: TCustomListView);
- published
- property Arrangement: TIconArrangement read FArrangement write SetArrangement default iaTop;
- property AutoArrange: Boolean read FAutoArrange write SetAutoArrange default False;
- property WrapText: Boolean read FWrapText write SetWrapText default True;
- end;
-
- TListArrangement = (arAlignBottom, arAlignLeft, arAlignRight,
- arAlignTop, arDefault, arSnapToGrid);
- TViewStyle = (vsIcon, vsSmallIcon, vsList, vsReport);
- TItemState = (isNone, isCut, isDropHilited, isFocused, isSelected);
- TItemStates = set of TItemState;
- TItemChange = (ctText, ctImage, ctState);
- TLVDeletedEvent = procedure(Sender: TObject; Item: TListItem) of object;
- TLVEditingEvent = procedure(Sender: TObject; Item: TListItem;
- var AllowEdit: Boolean) of object;
- TLVEditedEvent = procedure(Sender: TObject; Item: TListItem; var S: string) of object;
- TLVChangeEvent = procedure(Sender: TObject; Item: TListItem;
- Change: TItemChange) of object;
- TLVChangingEvent = procedure(Sender: TObject; Item: TListItem;
- Change: TItemChange; var AllowChange: Boolean) of object;
- TLVColumnClickEvent = procedure(Sender: TObject; Column: TListColumn) of object;
- TLVCompareEvent = procedure(Sender: TObject; Item1, Item2: TListItem;
- Data: Integer; var Compare: Integer) of object;
- TSearchDirection = (sdLeft, sdRight, sdAbove, sdBelow, sdAll);
-
- { TCustomListView }
- TCustomListView = class(TWinControl)
- private
- FBorderStyle: TBorderStyle;
- FViewStyle: TViewStyle;
- FReadOnly: Boolean;
- FLargeImages: TImageList;
- FSmallImages: TImageList;
- FStateImages: TImageList;
- FDragImage: TImageList;
- FShareImages: Boolean;
- FMultiSelect: Boolean;
- FSortType: TSortType;
- FColumnClick: Boolean;
- FShowColumnHeaders: Boolean;
- FListItems: TListItems;
- FClicked: Boolean;
- FRClicked: Boolean;
- FIconOptions: TIconOptions;
- FHideSelection: Boolean;
- FListColumns: TListColumns;
- FMemStream: TMemoryStream;
- FEditInstance: Pointer;
- FDefEditProc: Pointer;
- FEditHandle: HWND;
- FHeaderInstance: Pointer;
- FDefHeaderProc: Pointer;
- FHeaderHandle: HWND;
- FAllocBy: Integer;
- FDragIndex: Integer;
- FLastDropTarget: TListItem;
- FLargeChangeLink: TChangeLink;
- FSmallChangeLink: TChangeLink;
- FStateChangeLink: TChangeLink;
- FOnChange: TLVChangeEvent;
- FOnChanging: TLVChangingEvent;
- FOnColumnClick: TLVColumnClickEvent;
- FOnDeletion: TLVDeletedEvent;
- FOnEditing: TLVEditingEvent;
- FOnEdited: TLVEditedEvent;
- FOnInsert: TLVDeletedEvent;
- FOnCompare: TLVCompareEvent;
- procedure CMColorChanged(var Message: TMessage); message CM_COLORCHANGED;
- procedure CMCtl3DChanged(var Message: TMessage); message CM_CTL3DCHANGED;
- procedure CMDrag(var Message: TCMDrag); message CM_DRAG;
- procedure CMFontChanged(var Message: TMessage); message CM_FONTCHANGED;
- procedure CNNotify(var Message: TWMNotify); message CN_NOTIFY;
- procedure DoDragOver(Source: TDragObject; X, Y: Integer);
- procedure EditWndProc(var Message: TMessage);
- function GetBoundingRect: TRect;
- function GetColumnFromIndex(Index: Integer): TListColumn;
- function GetDropTarget: TListItem;
- function GetFocused: TListItem;
- function GetItem(Value: TLVItem): TListItem;
- function GetSelCount: Integer;
- function GetSelection: TListItem;
- function GetTopItem: TListItem;
- function GetViewOrigin: TPoint;
- function GetVisibleRowCount: Integer;
- procedure HeaderWndProc(var Message: TMessage);
- procedure ImageListChange(Sender: TObject);
- procedure InsertItem(Item: TListItem); dynamic;
- procedure SetBorderStyle(Value: TBorderStyle);
- procedure SetColumnClick(Value: Boolean);
- procedure SetColumnHeaders(Value: Boolean);
- procedure SetDropTarget(Value: TListItem);
- procedure SetFocused(Value: TListItem);
- procedure SetHideSelection(Value: Boolean);
- procedure SetIconArrangement(Value: TIconArrangement);
- procedure SetIconOptions(Value: TIconOptions);
- procedure SetImageList(Value: HImageList; Flags: Integer);
- procedure SetLargeImages(Value: TImageList);
- procedure SetAllocBy(Value: Integer);
- procedure SetItems(Value: TListItems);
- procedure SetListColumns(Value: TListColumns);
- procedure SetMultiSelect(Value: Boolean);
- procedure SetReadOnly(Value: Boolean);
- procedure SetSmallImages(Value: TImageList);
- procedure SetSortType(Value: TSortType);
- procedure SetSelection(Value: TListItem);
- procedure SetStateImages(Value: TImageList);
- procedure SetTextBkColor(Value: TColor);
- procedure SetTextColor(Value: TColor);
- procedure SetViewStyle(Value: TViewStyle);
- function ValidHeaderHandle: Boolean;
- procedure WMLButtonDown(var Message: TWMLButtonDown); message WM_LBUTTONDOWN;
- procedure WMNotify(var Message: TWMNotify); message WM_NOTIFY;
- procedure WMParentNotify(var Message: TWMParentNotify); message WM_PARENTNOTIFY;
- procedure WMRButtonDown(var Message: TWMRButtonDown); message WM_RBUTTONDOWN;
- protected
- function CanChange(Item: TListItem; Change: Integer): Boolean; dynamic;
- function CanEdit(Item: TListItem): Boolean; dynamic;
- procedure Change(Item: TListItem; Change: Integer); dynamic;
- procedure ColClick(Column: TListColumn); dynamic;
- function ColumnsShowing: Boolean;
- function CreateListItem: TListItem; virtual;
- procedure CreateParams(var Params: TCreateParams); override;
- procedure CreateWnd; override;
- procedure Delete(Item: TListItem); dynamic;
- procedure DestroyWnd; override;
- procedure DoEndDrag(Target: TObject; X, Y: Integer); dynamic;
- procedure DoStartDrag(var DragObject: TDragObject); override;
- procedure Edit(const Item: TLVItem); dynamic;
- function GetDragImages: TCustomImageList; override;
- function GetItemIndex(Value: TListItem): Integer;
- procedure Notification(AComponent: TComponent; Operation: TOperation); override;
- procedure UpdateColumn(Index: Integer);
- procedure UpdateColumns;
- procedure WndProc(var Message: TMessage); override;
- property BorderStyle: TBorderStyle read FBorderStyle write SetBorderStyle default bsSingle;
- property Columns: TListColumns read FListColumns write SetListColumns;
- property ColumnClick: Boolean read FColumnClick write SetColumnClick default True;
- property ReadOnly: Boolean read FReadOnly write SetReadOnly;
- property HideSelection: Boolean read FHideSelection write SetHideSelection default True;
- property IconOptions: TIconOptions read FIconOptions write SetIconOptions;
- property Items: TListItems read FListItems write SetItems;
- property AllocBy: Integer read FAllocBy write SetAllocBy default 0;
- property LargeImages: TImageList read FLargeImages write SetLargeImages;
- property MultiSelect: Boolean read FMultiSelect write SetMultiSelect default False;
- property OnChange: TLVChangeEvent read FOnChange write FOnChange;
- property OnChanging: TLVChangingEvent read FOnChanging write FOnChanging;
- property OnColumnClick: TLVColumnClickEvent read FOnColumnClick
- write FOnColumnClick;
- property OnCompare: TLVCompareEvent read FOnCompare write FOnCompare;
- property OnDeletion: TLVDeletedEvent read FOnDeletion write FOnDeletion;
- property OnEdited: TLVEditedEvent read FOnEdited write FOnEdited;
- property OnEditing: TLVEditingEvent read FOnEditing write FOnEditing;
- property OnInsert: TLVDeletedEvent read FOnInsert write FOnInsert;
- property ShowColumnHeaders: Boolean read FShowColumnHeaders write
- SetColumnHeaders default True;
- property SmallImages: TImageList read FSmallImages write SetSmallImages;
- property SortType: TSortType read FSortType write SetSortType default stNone;
- property StateImages: TImageList read FStateImages write SetStateImages;
- property ViewStyle: TViewStyle read FViewStyle write SetViewStyle default vsIcon;
- public
- constructor Create(AOwner: TComponent); override;
- destructor Destroy; override;
- function AlphaSort: Boolean;
- procedure Arrange(Code: TListArrangement);
- function FindCaption(StartIndex: Integer; Value: string;
- Partial, Inclusive, Wrap: Boolean): TListItem;
- function FindData(StartIndex: Integer; Value: Pointer;
- Inclusive, Wrap: Boolean): TListItem;
- function GetItemAt(X, Y: Integer): TListItem;
- function GetNearestItem(Point: TPoint;
- Direction: TSearchDirection): TListItem;
- function GetNextItem(StartItem: TListItem;
- Direction: TSearchDirection; States: TItemStates): TListItem;
- function GetSearchString: string;
- function IsEditing: Boolean;
- procedure Scroll(DX, DY: Integer);
- property Column[Index: Integer]: TListColumn read GetColumnFromIndex;
- property DropTarget: TListItem read GetDropTarget write SetDropTarget;
- property ItemFocused: TListItem read GetFocused write SetFocused;
- property SelCount: Integer read GetSelCount;
- property Selected: TListItem read GetSelection write SetSelection;
- function CustomSort(SortProc: TLVCompare; lParam: Longint): Boolean;
- function StringWidth(S: string): Integer;
- procedure UpdateItems(FirstIndex, LastIndex: Integer);
- property TopItem: TListItem read GetTopItem;
- property ViewOrigin: TPoint read GetViewOrigin;
- property VisibleRowCount: Integer read GetVisibleRowCount;
- property BoundingRect: TRect read GetBoundingRect;
- end;
-
- { TListView }
- TListView = class(TCustomListView)
- published
- property Align;
- property BorderStyle;
- property Color;
- property ColumnClick;
- property OnClick;
- property OnDblClick;
- property Columns;
- property Ctl3D;
- property DragMode;
- property ReadOnly;
- property Font;
- property HideSelection;
- property IconOptions;
- property Items;
- property AllocBy;
- property MultiSelect;
- property OnChange;
- property OnChanging;
- property OnColumnClick;
- property OnCompare;
- property OnDeletion;
- property OnEdited;
- property OnEditing;
- property OnEnter;
- property OnExit;
- property OnInsert;
- property OnDragDrop;
- property OnDragOver;
- property DragCursor;
- property OnStartDrag;
- property OnEndDrag;
- property OnMouseDown;
- property OnMouseMove;
- property OnMouseUp;
- property ParentShowHint;
- property ShowHint;
- property PopupMenu;
- property ShowColumnHeaders;
- property SortType;
- property TabOrder;
- property TabStop default True;
- property ViewStyle;
- property Visible;
- property OnKeyDown;
- property OnKeyPress;
- property OnKeyUp;
- property LargeImages;
- property SmallImages;
- property StateImages;
- end;
-
- implementation
-
- uses Printers, Consts, ComStrs;
-
- const
- SectionSizeArea = 8;
- RTFConversionFormat: TConversionFormat = (
- ConversionClass: TConversion;
- Extension: 'rtf';
- Next: nil);
- TextConversionFormat: TConversionFormat = (
- ConversionClass: TConversion;
- Extension: 'txt';
- Next: @RTFConversionFormat);
-
- var
- ConversionFormatList: PConversionFormat = @TextConversionFormat;
-
- { TTabStrings }
-
- type
- TTabStrings = class(TStrings)
- private
- FTabControl: TCustomTabControl;
- protected
- function Get(Index: Integer): string; override;
- function GetCount: Integer; override;
- function GetObject(Index: Integer): TObject; override;
- procedure Put(Index: Integer; const S: string); override;
- procedure PutObject(Index: Integer; AObject: TObject); override;
- procedure SetUpdateState(Updating: Boolean); override;
- public
- procedure Clear; override;
- procedure Delete(Index: Integer); override;
- procedure Insert(Index: Integer; const S: string); override;
- end;
-
- procedure TabControlError;
- begin
- raise EListError.CreateRes(sTabAccessError);
- end;
-
- procedure TTabStrings.Clear;
- begin
- if SendMessage(FTabControl.Handle, TCM_DELETEALLITEMS, 0, 0) = 0 then
- TabControlError;
- FTabControl.TabsChanged;
- end;
-
- procedure TTabStrings.Delete(Index: Integer);
- begin
- if SendMessage(FTabControl.Handle, TCM_DELETEITEM, Index, 0) = 0 then
- TabControlError;
- FTabControl.TabsChanged;
- end;
-
- function TTabStrings.Get(Index: Integer): string;
- var
- TCItem: TTCItem;
- Buffer: array[0..4095] of Char;
- begin
- TCItem.mask := TCIF_TEXT;
- TCItem.pszText := Buffer;
- TCItem.cchTextMax := SizeOf(Buffer);
- if SendMessage(FTabControl.Handle, TCM_GETITEM, Index,
- Longint(@TCItem)) = 0 then TabControlError;
- Result := Buffer;
- end;
-
- function TTabStrings.GetCount: Integer;
- begin
- Result := SendMessage(FTabControl.Handle, TCM_GETITEMCOUNT, 0, 0);
- end;
-
- function TTabStrings.GetObject(Index: Integer): TObject;
- var
- TCItem: TTCItem;
- begin
- TCItem.mask := TCIF_PARAM;
- if SendMessage(FTabControl.Handle, TCM_GETITEM, Index,
- Longint(@TCItem)) = 0 then TabControlError;
- Result := TObject(TCItem.lParam);
- end;
-
- procedure TTabStrings.Put(Index: Integer; const S: string);
- var
- TCItem: TTCItem;
- begin
- TCItem.mask := TCIF_TEXT;
- TCItem.pszText := PChar(S);
- if SendMessage(FTabControl.Handle, TCM_SETITEM, Index,
- Longint(@TCItem)) = 0 then TabControlError;
- FTabControl.TabsChanged;
- end;
-
- procedure TTabStrings.PutObject(Index: Integer; AObject: TObject);
- var
- TCItem: TTCItem;
- begin
- TCItem.mask := TCIF_PARAM;
- TCItem.lParam := Longint(AObject);
- if SendMessage(FTabControl.Handle, TCM_SETITEM, Index,
- Longint(@TCItem)) = 0 then TabControlError;
- end;
-
- procedure TTabStrings.Insert(Index: Integer; const S: string);
- var
- TCItem: TTCItem;
- begin
- TCItem.mask := TCIF_TEXT;
- TCItem.pszText := PChar(S);
- if SendMessage(FTabControl.Handle, TCM_INSERTITEM, Index,
- Longint(@TCItem)) < 0 then TabControlError;
- FTabControl.TabsChanged;
- end;
-
- procedure TTabStrings.SetUpdateState(Updating: Boolean);
- begin
- FTabControl.FUpdating := Updating;
- SendMessage(FTabControl.Handle, WM_SETREDRAW, Ord(not Updating), 0);
- if not Updating then
- begin
- FTabControl.Invalidate;
- FTabControl.TabsChanged;
- end;
- end;
-
- { TCustomTabControl }
-
- constructor TCustomTabControl.Create(AOwner: TComponent);
- begin
- inherited Create(AOwner);
- Width := 289;
- Height := 193;
- TabStop := True;
- ControlStyle := [csAcceptsControls, csDoubleClicks];
- FTabs := TTabStrings.Create;
- TTabStrings(FTabs).FTabControl := Self;
- end;
-
- destructor TCustomTabControl.Destroy;
- begin
- FTabs.Free;
- FSaveTabs.Free;
- inherited Destroy;
- end;
-
- function TCustomTabControl.CanChange: Boolean;
- begin
- Result := True;
- if Assigned(FOnChanging) then FOnChanging(Self, Result);
- end;
-
- procedure TCustomTabControl.Change;
- begin
- if Assigned(FOnChange) then FOnChange(Self);
- end;
-
- procedure TCustomTabControl.CreateParams(var Params: TCreateParams);
- begin
- InitCommonControls;
- inherited CreateParams(Params);
- CreateSubClass(Params, WC_TABCONTROL);
- with Params do
- begin
- Style := Style or WS_CLIPCHILDREN;
- if not TabStop then Style := Style or TCS_FOCUSNEVER;
- if FMultiLine then Style := Style or TCS_MULTILINE;
- if FTabSize.X <> 0 then Style := Style or TCS_FIXEDWIDTH;
- WindowClass.style := WindowClass.style or CS_DBLCLKS;
- end;
- end;
-
- procedure TCustomTabControl.CreateWnd;
- begin
- inherited CreateWnd;
- if Integer(FTabSize) <> 0 then UpdateTabSize;
- if FSaveTabs <> nil then
- begin
- FTabs.Assign(FSaveTabs);
- SetTabIndex(FSaveTabIndex);
- FSaveTabs.Free;
- FSaveTabs := nil;
- end;
- end;
-
- procedure TCustomTabControl.DestroyWnd;
- begin
- if FTabs.Count > 0 then
- begin
- FSaveTabs := TStringList.Create;
- FSaveTabs.Assign(FTabs);
- FSaveTabIndex := GetTabIndex;
- end;
- inherited DestroyWnd;
- end;
-
- procedure TCustomTabControl.AlignControls(AControl: TControl;
- var Rect: TRect);
- begin
- Rect := DisplayRect;
- inherited AlignControls(AControl, Rect);
- end;
-
- function TCustomTabControl.GetDisplayRect: TRect;
- begin
- Result := ClientRect;
- SendMessage(Handle, TCM_ADJUSTRECT, 0, Integer(@Result));
- Inc(Result.Top, 2);
- end;
-
- function TCustomTabControl.GetTabIndex: Integer;
- begin
- Result := SendMessage(Handle, TCM_GETCURSEL, 0, 0);
- end;
-
- procedure TCustomTabControl.SetMultiLine(Value: Boolean);
- begin
- if FMultiLine <> Value then
- begin
- FMultiLine := Value;
- RecreateWnd;
- end;
- end;
-
- procedure TCustomTabControl.SetTabHeight(Value: Smallint);
- begin
- if FTabSize.Y <> Value then
- begin
- if Value < 0 then
- raise EInvalidOperation.CreateResFmt(SPropertyOutOfRange, [Self.Classname]);
- FTabSize.Y := Value;
- UpdateTabSize;
- end;
- end;
-
- procedure TCustomTabControl.SetTabIndex(Value: Integer);
- begin
- SendMessage(Handle, TCM_SETCURSEL, Value, 0);
- end;
-
- procedure TCustomTabControl.SetTabs(Value: TStrings);
- begin
- FTabs.Assign(Value);
- end;
-
- procedure TCustomTabControl.SetTabWidth(Value: Smallint);
- var
- OldValue: Smallint;
- begin
- if FTabSize.X <> Value then
- begin
- if Value < 0 then
- raise EInvalidOperation.CreateResFmt(SPropertyOutOfRange, [Self.Classname]);
- OldValue := FTabSize.X;
- FTabSize.X := Value;
- if (OldValue = 0) or (Value = 0) then
- RecreateWnd else
- UpdateTabSize;
- end;
- end;
-
- procedure TCustomTabControl.TabsChanged;
- begin
- if not FUpdating then
- begin
- if HandleAllocated then
- SendMessage(Handle, WM_SIZE, SIZE_RESTORED,
- Word(Width) or Word(Height) shl 16);
- Realign;
- end;
- end;
-
- procedure TCustomTabControl.UpdateTabSize;
- begin
- SendMessage(Handle, TCM_SETITEMSIZE, 0, Integer(FTabSize));
- TabsChanged;
- end;
-
- procedure TCustomTabControl.WMDestroy(var Message: TWMDestroy);
- var
- FocusHandle: HWnd;
- begin
- FocusHandle := GetFocus;
- if (FocusHandle <> 0) and ((FocusHandle = Handle) or
- IsChild(Handle, FocusHandle)) then
- Windows.SetFocus(0);
- inherited;
- end;
-
- procedure TCustomTabControl.CMTabStopChanged(var Message: TMessage);
- begin
- if not (csDesigning in ComponentState) then RecreateWnd;
- end;
-
- procedure TCustomTabControl.CNNotify(var Message: TWMNotify);
- begin
- with Message.NMHdr^ do
- case code of
- TCN_SELCHANGE:
- Change;
- TCN_SELCHANGING:
- begin
- Message.Result := 1;
- if CanChange then Message.Result := 0;
- end;
- end;
- end;
-
- { TTabSheet }
-
- constructor TTabSheet.Create(AOwner: TComponent);
- begin
- inherited Create(AOwner);
- Align := alClient;
- ControlStyle := ControlStyle + [csAcceptsControls, csNoDesignVisible];
- Visible := False;
- FTabVisible := True;
- end;
-
- destructor TTabSheet.Destroy;
- begin
- if FPageControl <> nil then FPageControl.RemovePage(Self);
- inherited Destroy;
- end;
-
- function TTabSheet.GetPageIndex: Integer;
- begin
- if FPageControl <> nil then
- Result := FPageControl.FPages.IndexOf(Self) else
- Result := -1;
- end;
-
- function TTabSheet.GetTabIndex: Integer;
- var
- I: Integer;
- begin
- Result := 0;
- if not FTabShowing then Dec(Result) else
- for I := 0 to PageIndex - 1 do
- if TTabSheet(FPageControl.FPages[I]).FTabShowing then
- Inc(Result);
- end;
-
- procedure TTabSheet.ReadState(Reader: TReader);
- begin
- inherited ReadState(Reader);
- if Reader.Parent is TPageControl then
- PageControl := TPageControl(Reader.Parent);
- end;
-
- procedure TTabSheet.SetPageControl(APageControl: TPageControl);
- begin
- if FPageControl <> APageControl then
- begin
- if FPageControl <> nil then FPageControl.RemovePage(Self);
- Parent := APageControl;
- if APageControl <> nil then APageControl.InsertPage(Self);
- end;
- end;
-
- procedure TTabSheet.SetPageIndex(Value: Integer);
- var
- I: Integer;
- begin
- if FPageControl <> nil then
- begin
- I := TabIndex;
- FPageControl.FPages.Move(PageIndex, Value);
- if I >= 0 then FPageControl.MoveTab(I, TabIndex);
- end;
- end;
-
- procedure TTabSheet.SetTabShowing(Value: Boolean);
- begin
- if FTabShowing <> Value then
- if Value then
- begin
- FTabShowing := True;
- FPageControl.InsertTab(Self);
- end else
- begin
- FPageControl.DeleteTab(Self);
- FTabShowing := False;
- end;
- end;
-
- procedure TTabSheet.SetTabVisible(Value: Boolean);
- begin
- if FTabVisible <> Value then
- begin
- FTabVisible := Value;
- UpdateTabShowing;
- end;
- end;
-
- procedure TTabSheet.UpdateTabShowing;
- begin
- SetTabShowing((FPageControl <> nil) and FTabVisible);
- end;
-
- procedure TTabSheet.CMTextChanged(var Message: TMessage);
- begin
- if FTabShowing then FPageControl.UpdateTab(Self);
- end;
-
- { TPageControl }
-
- constructor TPageControl.Create(AOwner: TComponent);
- begin
- inherited Create(AOwner);
- ControlStyle := [csDoubleClicks];
- FPages := TList.Create;
- end;
-
- destructor TPageControl.Destroy;
- var
- I: Integer;
- begin
- for I := 0 to FPages.Count - 1 do TTabSheet(FPages[I]).FPageControl := nil;
- FPages.Free;
- inherited Destroy;
- end;
-
- procedure TPageControl.Change;
- var
- Form: TForm;
- begin
- UpdateActivePage;
- if csDesigning in ComponentState then
- begin
- Form := GetParentForm(Self);
- if (Form <> nil) and (Form.Designer <> nil) then Form.Designer.Modified;
- end;
- inherited Change;
- end;
-
- procedure TPageControl.ChangeActivePage(Page: TTabSheet);
- var
- ParentForm: TForm;
- begin
- if FActivePage <> Page then
- begin
- ParentForm := GetParentForm(Self);
- if (ParentForm <> nil) and (FActivePage <> nil) and
- FActivePage.ContainsControl(ParentForm.ActiveControl) then
- ParentForm.ActiveControl := FActivePage;
- if Page <> nil then
- begin
- Page.BringToFront;
- Page.Visible := True;
- if (ParentForm <> nil) and (FActivePage <> nil) and
- (ParentForm.ActiveControl = FActivePage) then
- if Page.CanFocus then
- ParentForm.ActiveControl := Page else
- ParentForm.ActiveControl := Self;
- end;
- if FActivePage <> nil then FActivePage.Visible := False;
- FActivePage := Page;
- if (ParentForm <> nil) and (FActivePage <> nil) and
- (ParentForm.ActiveControl = FActivePage) then
- FActivePage.SelectFirst;
- end;
- end;
-
- procedure TPageControl.DeleteTab(Page: TTabSheet);
- begin
- Tabs.Delete(Page.TabIndex);
- UpdateActivePage;
- end;
-
- function TPageControl.FindNextPage(CurPage: TTabSheet;
- GoForward, CheckTabVisible: Boolean): TTabSheet;
- var
- I, StartIndex: Integer;
- begin
- if FPages.Count <> 0 then
- begin
- StartIndex := FPages.IndexOf(CurPage);
- if StartIndex = -1 then
- if GoForward then StartIndex := FPages.Count - 1 else StartIndex := 0;
- I := StartIndex;
- repeat
- if GoForward then
- begin
- Inc(I);
- if I = FPages.Count then I := 0;
- end else
- begin
- if I = 0 then I := FPages.Count;
- Dec(I);
- end;
- Result := FPages[I];
- if not CheckTabVisible or Result.TabVisible then Exit;
- until I = StartIndex;
- end;
- Result := nil;
- end;
-
- procedure TPageControl.GetChildren(Proc: TGetChildProc);
- var
- I: Integer;
- begin
- for I := 0 to FPages.Count - 1 do Proc(TComponent(FPages[I]));
- end;
-
- function TPageControl.GetPage(Index: Integer): TTabSheet;
- begin
- Result := FPages[Index];
- end;
-
- function TPageControl.GetPageCount: Integer;
- begin
- Result := FPages.Count;
- end;
-
- procedure TPageControl.InsertPage(Page: TTabSheet);
- begin
- FPages.Add(Page);
- Page.FPageControl := Self;
- Page.UpdateTabShowing;
- end;
-
- procedure TPageControl.InsertTab(Page: TTabSheet);
- begin
- Tabs.InsertObject(Page.TabIndex, Page.Caption, Page);
- UpdateActivePage;
- end;
-
- procedure TPageControl.MoveTab(CurIndex, NewIndex: Integer);
- begin
- Tabs.Move(CurIndex, NewIndex);
- end;
-
- procedure TPageControl.RemovePage(Page: TTabSheet);
- begin
- if FActivePage = Page then SetActivePage(nil);
- Page.SetTabShowing(False);
- Page.FPageControl := nil;
- FPages.Remove(Page);
- end;
-
- procedure TPageControl.SelectNextPage(GoForward: Boolean);
- var
- Page: TTabSheet;
- begin
- Page := FindNextPage(ActivePage, GoForward, True);
- if (Page <> nil) and (Page <> ActivePage) and CanChange then
- begin
- TabIndex := Page.TabIndex;
- Change;
- end;
- end;
-
- procedure TPageControl.SetActivePage(Page: TTabSheet);
- begin
- if (Page <> nil) and (Page.PageControl <> Self) then Exit;
- ChangeActivePage(Page);
- if Page <> nil then TabIndex := Page.TabIndex else TabIndex := -1;
- end;
-
- procedure TPageControl.SetChildOrder(Child: TComponent; Order: Integer);
- begin
- TTabSheet(Child).PageIndex := Order;
- end;
-
- procedure TPageControl.ShowControl(AControl: TControl);
- begin
- if (AControl is TTabSheet) and (TTabSheet(AControl).PageControl = Self) then
- SetActivePage(TTabSheet(AControl));
- inherited ShowControl(AControl);
- end;
-
- procedure TPageControl.UpdateTab(Page: TTabSheet);
- begin
- Tabs[Page.TabIndex] := Page.Caption;
- end;
-
- procedure TPageControl.UpdateActivePage;
- begin
- if TabIndex >= 0 then SetActivePage(TTabSheet(Tabs.Objects[TabIndex]));
- end;
-
- procedure TPageControl.CMDesignHitTest(var Message: TCMDesignHitTest);
- var
- HitIndex: Integer;
- HitTestInfo: TTCHitTestInfo;
- begin
- HitTestInfo.pt := SmallPointToPoint(Message.Pos);
- HitIndex := SendMessage(Handle, TCM_HITTEST, 0, Longint(@HitTestInfo));
- if (HitIndex >= 0) and (HitIndex <> TabIndex) then Message.Result := 1;
- end;
-
- procedure TPageControl.CMDialogKey(var Message: TCMDialogKey);
- begin
- if (Message.CharCode = VK_TAB) and (GetKeyState(VK_CONTROL) < 0) then
- begin
- SelectNextPage(GetKeyState(VK_SHIFT) >= 0);
- Message.Result := 1;
- end else
- inherited;
- end;
-
- { TStatusPanel }
-
- constructor TStatusPanel.Create(Collection: TCollection);
- begin
- FWidth := 50;
- FBevel := pbLowered;
- inherited Create(Collection);
- end;
-
- procedure TStatusPanel.Assign(Source: TPersistent);
- begin
- if Source is TStatusPanel then
- begin
- Text := TStatusPanel(Source).Text;
- Width := TStatusPanel(Source).Width;
- Alignment := TStatusPanel(Source).Alignment;
- Bevel := TStatusPanel(Source).Bevel;
- Style := TStatusPanel(Source).Style;
- Exit;
- end;
- inherited Assign(Source);
- end;
-
- procedure TStatusPanel.SetAlignment(Value: TAlignment);
- begin
- if FAlignment <> Value then
- begin
- FAlignment := Value;
- Changed(False);
- end;
- end;
-
- procedure TStatusPanel.SetBevel(Value: TStatusPanelBevel);
- begin
- if FBevel <> Value then
- begin
- FBevel := Value;
- Changed(True);
- end;
- end;
-
- procedure TStatusPanel.SetStyle(Value: TStatusPanelStyle);
- begin
- if FStyle <> Value then
- begin
- FStyle := Value;
- Changed(False);
- end;
- end;
-
- procedure TStatusPanel.SetText(const Value: string);
- begin
- if FText <> Value then
- begin
- FText := Value;
- Changed(False);
- end;
- end;
-
- procedure TStatusPanel.SetWidth(Value: Integer);
- begin
- if FWidth <> Value then
- begin
- FWidth := Value;
- Changed(True);
- end;
- end;
-
- { TStatusPanels }
-
- constructor TStatusPanels.Create(StatusBar: TStatusBar);
- begin
- inherited Create(TStatusPanel);
- FStatusBar := StatusBar;
- end;
-
- function TStatusPanels.Add: TStatusPanel;
- begin
- Result := TStatusPanel(inherited Add);
- end;
-
- function TStatusPanels.GetItem(Index: Integer): TStatusPanel;
- begin
- Result := TStatusPanel(inherited GetItem(Index));
- end;
-
- procedure TStatusPanels.SetItem(Index: Integer; Value: TStatusPanel);
- begin
- inherited SetItem(Index, Value);
- end;
-
- procedure TStatusPanels.Update(Item: TCollectionItem);
- begin
- if Item <> nil then
- FStatusBar.UpdatePanel(Item.Index) else
- FStatusBar.UpdatePanels;
- end;
-
- { TStatusBar }
-
- constructor TStatusBar.Create(AOwner: TComponent);
- begin
- inherited Create(AOwner);
- ControlStyle := [csCaptureMouse, csClickEvents, csDoubleClicks];
- Color := clBtnFace;
- Height := 19;
- Align := alBottom;
- FPanels := TStatusPanels.Create(Self);
- FCanvas := TControlCanvas.Create;
- TControlCanvas(FCanvas).Control := Self;
- FSizeGrip := True;
- end;
-
- destructor TStatusBar.Destroy;
- begin
- FCanvas.Free;
- FPanels.Free;
- inherited Destroy;
- end;
-
- procedure TStatusBar.CreateParams(var Params: TCreateParams);
- begin
- InitCommonControls;
- inherited CreateParams(Params);
- CreateSubClass(Params, STATUSCLASSNAME);
- if FSizeGrip then
- Params.Style := Params.Style or SBARS_SIZEGRIP else
- Params.Style := Params.Style or CCS_TOP;
- end;
-
- procedure TStatusBar.CreateWnd;
- begin
- inherited CreateWnd;
- UpdatePanels;
- if FSimpleText <> '' then
- SendMessage(Handle, SB_SETTEXT, 255, Integer(PChar(FSimpleText)));
- if FSimplePanel then
- SendMessage(Handle, SB_SIMPLE, 1, 0);
- end;
-
- procedure TStatusBar.DrawPanel(Panel: TStatusPanel; const Rect: TRect);
- begin
- if Assigned(FOnDrawPanel) then
- FOnDrawPanel(Self, Panel, Rect) else
- FCanvas.FillRect(Rect);
- end;
-
- procedure TStatusBar.Resize;
- begin
- if Assigned(FOnResize) then FOnResize(Self);
- end;
-
- procedure TStatusBar.SetPanels(Value: TStatusPanels);
- begin
- FPanels.Assign(Value);
- end;
-
- procedure TStatusBar.SetSimplePanel(Value: Boolean);
- begin
- if FSimplePanel <> Value then
- begin
- FSimplePanel := Value;
- if HandleAllocated then
- SendMessage(Handle, SB_SIMPLE, Ord(FSimplePanel), 0);
- end;
- end;
-
- procedure TStatusBar.SetSimpleText(const Value: string);
- begin
- if FSimpleText <> Value then
- begin
- FSimpleText := Value;
- if HandleAllocated then
- SendMessage(Handle, SB_SETTEXT, 255, Integer(PChar(FSimpleText)));
- end;
- end;
-
- procedure TStatusBar.SetSizeGrip(Value: Boolean);
- begin
- if FSizeGrip <> Value then
- begin
- FSizeGrip := Value;
- RecreateWnd;
- end;
- end;
-
- procedure TStatusBar.UpdatePanel(Index: Integer);
- var
- Flags: Integer;
- S: string;
- begin
- if HandleAllocated then
- with Panels[Index] do
- begin
- Flags := 0;
- case Bevel of
- pbNone: Flags := SBT_NOBORDERS;
- pbRaised: Flags := SBT_POPOUT;
- end;
- if Style = psOwnerDraw then Flags := Flags or SBT_OWNERDRAW;
- S := Text;
- case Alignment of
- taCenter: S := #9 + S;
- taRightJustify: S := #9#9 + S;
- end;
- SendMessage(Handle, SB_SETTEXT, Index or Flags, Integer(PChar(S)));
- end;
- end;
-
- procedure TStatusBar.UpdatePanels;
- const
- MaxPanelCount = 128;
- var
- I, Count, PanelPos: Integer;
- PanelEdges: array[0..MaxPanelCount - 1] of Integer;
- begin
- if HandleAllocated then
- begin
- Count := Panels.Count;
- if Count > MaxPanelCount then Count := MaxPanelCount;
- if Count = 0 then
- begin
- PanelEdges[0] := -1;
- SendMessage(Handle, SB_SETPARTS, 1, Integer(@PanelEdges));
- SendMessage(Handle, SB_SETTEXT, 0, Integer(PChar('')));
- end else
- begin
- PanelPos := 0;
- for I := 0 to Count - 2 do
- begin
- Inc(PanelPos, Panels[I].Width);
- PanelEdges[I] := PanelPos;
- end;
- PanelEdges[Count - 1] := -1;
- SendMessage(Handle, SB_SETPARTS, Count, Integer(@PanelEdges));
- for I := 0 to Count - 1 do UpdatePanel(I);
- end;
- end;
- end;
-
- procedure TStatusBar.CNDrawItem(var Message: TWMDrawItem);
- var
- SaveIndex: Integer;
- begin
- with Message.DrawItemStruct^ do
- begin
- SaveIndex := SaveDC(hDC);
- FCanvas.Handle := hDC;
- FCanvas.Font := Font;
- FCanvas.Brush.Color := clBtnFace;
- FCanvas.Brush.Style := bsSolid;
- DrawPanel(Panels[itemID], rcItem);
- FCanvas.Handle := 0;
- RestoreDC(hDC, SaveIndex);
- end;
- Message.Result := 1;
- end;
-
- procedure TStatusBar.WMSize(var Message: TWMSize);
- begin
- { Eat WM_SIZE message to prevent control from doing alignment }
- if not (csLoading in ComponentState) then Resize;
- end;
-
- { THeaderSection }
-
- constructor THeaderSection.Create(Collection: TCollection);
- begin
- FWidth := 50;
- FMaxWidth := 10000;
- FAllowClick := True;
- inherited Create(Collection);
- end;
-
- procedure THeaderSection.Assign(Source: TPersistent);
- begin
- if Source is THeaderSection then
- begin
- Text := THeaderSection(Source).Text;
- Width := THeaderSection(Source).Width;
- MinWidth := THeaderSection(Source).MinWidth;
- MaxWidth := THeaderSection(Source).MaxWidth;
- Alignment := THeaderSection(Source).Alignment;
- Style := THeaderSection(Source).Style;
- AllowClick := THeaderSection(Source).AllowClick;
- Exit;
- end;
- inherited Assign(Source);
- end;
-
- function THeaderSection.GetLeft: Integer;
- var
- I: Integer;
- begin
- Result := 0;
- for I := 0 to Index - 1 do
- Inc(Result, THeaderSections(Collection)[I].Width);
- end;
-
- function THeaderSection.GetRight: Integer;
- begin
- Result := Left + Width;
- end;
-
- procedure THeaderSection.SetAlignment(Value: TAlignment);
- begin
- if FAlignment <> Value then
- begin
- FAlignment := Value;
- Changed(False);
- end;
- end;
-
- procedure THeaderSection.SetMaxWidth(Value: Integer);
- begin
- if Value < FMinWidth then Value := FMinWidth;
- if Value > 10000 then Value := 10000;
- FMaxWidth := Value;
- SetWidth(FWidth);
- end;
-
- procedure THeaderSection.SetMinWidth(Value: Integer);
- begin
- if Value < 0 then Value := 0;
- if Value > FMaxWidth then Value := FMaxWidth;
- FMinWidth := Value;
- SetWidth(FWidth);
- end;
-
- procedure THeaderSection.SetStyle(Value: THeaderSectionStyle);
- begin
- if FStyle <> Value then
- begin
- FStyle := Value;
- Changed(False);
- end;
- end;
-
- procedure THeaderSection.SetText(const Value: string);
- begin
- if FText <> Value then
- begin
- FText := Value;
- Changed(False);
- end;
- end;
-
- procedure THeaderSection.SetWidth(Value: Integer);
- begin
- if Value < FMinWidth then Value := FMinWidth;
- if Value > FMaxWidth then Value := FMaxWidth;
- if FWidth <> Value then
- begin
- FWidth := Value;
- Changed(True);
- end;
- end;
-
- { THeaderSections }
-
- constructor THeaderSections.Create(HeaderControl: THeaderControl);
- begin
- inherited Create(THeaderSection);
- FHeaderControl := HeaderControl;
- end;
-
- function THeaderSections.Add: THeaderSection;
- begin
- Result := THeaderSection(inherited Add);
- end;
-
- function THeaderSections.GetItem(Index: Integer): THeaderSection;
- begin
- Result := THeaderSection(inherited GetItem(Index));
- end;
-
- procedure THeaderSections.SetItem(Index: Integer; Value: THeaderSection);
- begin
- inherited SetItem(Index, Value);
- end;
-
- procedure THeaderSections.Update(Item: TCollectionItem);
- begin
- if Item <> nil then
- FHeaderControl.UpdateSection(Item.Index) else
- FHeaderControl.UpdateSections;
- end;
-
- { THeaderControl }
-
- constructor THeaderControl.Create(AOwner: TComponent);
- begin
- inherited Create(AOwner);
- ControlStyle := [];
- Align := alTop;
- Height := 17;
- FSections := THeaderSections.Create(Self);
- FCanvas := TControlCanvas.Create;
- TControlCanvas(FCanvas).Control := Self;
- end;
-
- destructor THeaderControl.Destroy;
- begin
- FCanvas.Free;
- FSections.Free;
- inherited Destroy;
- end;
-
- procedure THeaderControl.CreateParams(var Params: TCreateParams);
- begin
- InitCommonControls;
- inherited CreateParams(Params);
- CreateSubClass(Params, 'SysHeader32');
- Params.Style := Params.Style or HDS_BUTTONS;
- end;
-
- procedure THeaderControl.CreateWnd;
- begin
- inherited CreateWnd;
- UpdateSections;
- end;
-
- procedure THeaderControl.DrawSection(Section: THeaderSection;
- const Rect: TRect; Pressed: Boolean);
- begin
- if Assigned(FOnDrawSection) then
- FOnDrawSection(Self, Section, Rect, Pressed) else
- FCanvas.FillRect(Rect);
- end;
-
- procedure THeaderControl.Resize;
- begin
- if Assigned(FOnResize) then FOnResize(Self);
- end;
-
- procedure THeaderControl.SectionClick(Section: THeaderSection);
- begin
- if Assigned(FOnSectionClick) then FOnSectionClick(Self, Section);
- end;
-
- procedure THeaderControl.SectionResize(Section: THeaderSection);
- begin
- if Assigned(FOnSectionResize) then FOnSectionResize(Self, Section);
- end;
-
- procedure THeaderControl.SectionTrack(Section: THeaderSection;
- Width: Integer; State: TSectionTrackState);
- begin
- if Assigned(FOnSectionTrack) then FOnSectionTrack(Self, Section, Width, State);
- end;
-
- procedure THeaderControl.SetSections(Value: THeaderSections);
- begin
- FSections.Assign(Value);
- end;
-
- procedure THeaderControl.UpdateItem(Message, Index: Integer);
- var
- Item: THDItem;
- begin
- with Sections[Index] do
- begin
- FillChar(Item, SizeOf(Item), 0);
- Item.mask := HDI_WIDTH or HDI_TEXT or HDI_FORMAT;
- Item.cxy := Width;
- Item.pszText := PChar(Text);
- Item.cchTextMax := Length(Text);
- case Alignment of
- taLeftJustify: Item.fmt := HDF_LEFT;
- taRightJustify: Item.fmt := HDF_RIGHT;
- else
- Item.fmt := HDF_CENTER;
- end;
- if Style = hsOwnerDraw then
- Item.fmt := Item.fmt or HDF_OWNERDRAW else
- Item.fmt := Item.fmt or HDF_STRING;
- SendMessage(Handle, Message, Index, Integer(@Item));
- end;
- end;
-
- procedure THeaderControl.UpdateSection(Index: Integer);
- begin
- if HandleAllocated then UpdateItem(HDM_SETITEM, Index);
- end;
-
- procedure THeaderControl.UpdateSections;
- var
- I: Integer;
- begin
- if HandleAllocated then
- begin
- for I := 0 to SendMessage(Handle, HDM_GETITEMCOUNT, 0, 0) - 1 do
- SendMessage(Handle, HDM_DELETEITEM, 0, 0);
- for I := 0 to Sections.Count - 1 do UpdateItem(HDM_INSERTITEM, I);
- end;
- end;
-
- procedure THeaderControl.CNDrawItem(var Message: TWMDrawItem);
- var
- SaveIndex: Integer;
- begin
- with Message.DrawItemStruct^ do
- begin
- SaveIndex := SaveDC(hDC);
- FCanvas.Handle := hDC;
- FCanvas.Font := Font;
- FCanvas.Brush.Color := clBtnFace;
- FCanvas.Brush.Style := bsSolid;
- DrawSection(Sections[itemID], rcItem, itemState and ODS_SELECTED <> 0);
- FCanvas.Handle := 0;
- RestoreDC(hDC, SaveIndex);
- end;
- Message.Result := 1;
- end;
-
- procedure THeaderControl.CNNotify(var Message: TWMNotify);
- var
- Section: THeaderSection;
- TrackState: TSectionTrackState;
- begin
- with PHDNotify(Message.NMHdr)^ do
- case Hdr.code of
- HDN_ITEMCLICK:
- SectionClick(Sections[Item]);
- HDN_ITEMCHANGED:
- if PItem^.mask and HDI_WIDTH <> 0 then
- begin
- Section := Sections[Item];
- if Section.FWidth <> PItem^.cxy then
- begin
- Section.FWidth := PItem^.cxy;
- SectionResize(Section);
- end;
- end;
- HDN_BEGINTRACK, HDN_TRACK, HDN_ENDTRACK:
- begin
- Section := Sections[Item];
- case Hdr.code of
- HDN_BEGINTRACK: TrackState := tsTrackBegin;
- HDN_ENDTRACK: TrackState := tsTrackEnd;
- else
- TrackState := tsTrackMove;
- end;
- with PItem^ do
- begin
- if cxy < Section.FMinWidth then cxy := Section.FMinWidth;
- if cxy > Section.FMaxWidth then cxy := Section.FMaxWidth;
- SectionTrack(Sections[Item], cxy, TrackState);
- end;
- end;
- end;
- end;
-
- procedure THeaderControl.WMLButtonDown(var Message: TWMLButtonDown);
- var
- Index: Integer;
- Info: THDHitTestInfo;
- begin
- Info.Point.X := Message.Pos.X;
- Info.Point.Y := Message.Pos.Y;
- Index := SendMessage(Handle, HDM_HITTEST, 0, Integer(@Info));
- if (Index < 0) or (Info.Flags and HHT_ONHEADER = 0) or
- Sections[Index].AllowClick then inherited;
- end;
-
- procedure THeaderControl.WMSize(var Message: TWMSize);
- begin
- inherited;
- if not (csLoading in ComponentState) then Resize;
- end;
-
- { TTreeNode }
-
- function DefaultTreeViewSort(Node1, Node2: TTreeNode; lParam: Integer): Integer; stdcall;
- begin
- with Node1 do
- if Assigned(TreeView.OnCompare) then
- TreeView.OnCompare(TreeView, Node1, Node2, lParam, Result)
- else Result := lstrcmp(PChar(Node1.Text), PChar(Node2.Text));
- end;
-
- procedure TreeViewError(MsgID: Integer);
- begin
- raise ETreeViewError.CreateRes(MsgID);
- end;
-
- constructor TTreeNode.Create(AOwner: TTreeNodes);
- begin
- inherited Create;
- FOverlayIndex := -1;
- FStateIndex := -1;
- FOwner := AOwner;
- end;
-
- destructor TTreeNode.Destroy;
- var
- Node: TTreeNode;
- CheckValue: Integer;
- begin
- FDeleting := True;
- Node := Parent;
- if (Node <> nil) and (not Node.Deleting) then
- begin
- if Node.IndexOf(Self) <> -1 then CheckValue := 1
- else CheckValue := 0;
- if Node.Count = CheckValue then
- begin
- Node.Expanded := False;
- Node.HasChildren := False;
- end;
- end;
- if ItemId <> nil then TreeView_DeleteItem(Handle, ItemId);
- Data := nil;
- inherited Destroy;
- end;
-
- function TTreeNode.GetHandle: HWND;
- begin
- Result := TreeView.Handle;
- end;
-
- function TTreeNode.GetTreeView: TCustomTreeView;
- begin
- Result := Owner.Owner;
- end;
-
- function TTreeNode.HasAsParent(Value: TTreeNode): Boolean;
- begin
- if Self = Value then Result := True
- else if Parent <> nil then Result := Parent.HasAsParent(Value)
- else Result := False;
- end;
-
- procedure TTreeNode.SetText(const S: string);
- var
- Item: TTVItem;
- begin
- FText := S;
- with Item do
- begin
- mask := TVIF_TEXT;
- hItem := ItemId;
- pszText := LPSTR_TEXTCALLBACK;
- end;
- TreeView_SetItem(Handle, Item);
- if TreeView.SortType in [stText, stBoth] then
- begin
- if Parent <> nil then Parent.AlphaSort
- else TreeView.AlphaSort;
- end;
- end;
-
- procedure TTreeNode.SetData(Value: Pointer);
- begin
- FData := Value;
- if (TreeView.SortType in [stData, stBoth]) and Assigned(TreeView.OnCompare) then
- begin
- if Parent <> nil then Parent.AlphaSort
- else TreeView.AlphaSort;
- end;
- end;
-
- function TTreeNode.GetState(NodeState: TNodeState): Boolean;
- var
- Item: TTVItem;
- begin
- Result := False;
- with Item do
- begin
- mask := TVIF_STATE;
- hItem := ItemId;
- if TreeView_GetItem(Handle, Item) then
- case NodeState of
- nsCut: Result := (state and TVIS_CUT) <> 0;
- nsFocused: Result := (state and TVIS_FOCUSED) <> 0;
- nsSelected: Result := (state and TVIS_SELECTED) <> 0;
- nsExpanded: Result := (state and TVIS_EXPANDED) <> 0;
- nsDropHilited: Result := (state and TVIS_DROPHILITED) <> 0;
- end;
- end;
- end;
-
- procedure TTreeNode.SetImageIndex(Value: Integer);
- var
- Item: TTVItem;
- begin
- FImageIndex := Value;
- with Item do
- begin
- mask := TVIF_IMAGE;
- hItem := ItemId;
- iImage := I_IMAGECALLBACK;
- end;
- TreeView_SetItem(Handle, Item);
- end;
-
- procedure TTreeNode.SetSelectedIndex(Value: Integer);
- var
- Item: TTVItem;
- begin
- FSelectedIndex := Value;
- with Item do
- begin
- mask := TVIF_SELECTEDIMAGE;
- hItem := ItemId;
- iSelectedImage := I_IMAGECALLBACK;
- end;
- TreeView_SetItem(Handle, Item);
- end;
-
- procedure TTreeNode.SetOverlayIndex(Value: Integer);
- var
- Item: TTVItem;
- begin
- FOverlayIndex := Value;
- with Item do
- begin
- mask := TVIF_STATE;
- stateMask := TVIS_OVERLAYMASK;
- hItem := ItemId;
- state := IndexToOverlayMask(OverlayIndex + 1);
- end;
- TreeView_SetItem(Handle, Item);
- end;
-
- procedure TTreeNode.SetStateIndex(Value: Integer);
- var
- Item: TTVItem;
- begin
- FStateIndex := Value;
- if Value >= 0 then Dec(Value);
- with Item do
- begin
- mask := TVIF_STATE;
- stateMask := TVIS_STATEIMAGEMASK;
- hItem := ItemId;
- state := IndexToStateImageMask(Value + 1);
- end;
- TreeView_SetItem(Handle, Item);
- end;
-
- procedure TTreeNode.ExpandItem(Expand: Boolean; Recurse: Boolean);
- var
- Flag: Integer;
- Node: TTreeNode;
- begin
- if Recurse then
- begin
- Node := Self;
- repeat
- Node.ExpandItem(Expand, False);
- Node := Node.GetNext;
- until (Node = nil) or not Node.HasAsParent(Self);
- end
- else begin
- if Expand then Flag := TVE_EXPAND
- else Flag := TVE_COLLAPSE;
- TreeView_Expand(Handle, ItemId, Flag);
- end;
- end;
-
- procedure TTreeNode.Expand(Recurse: Boolean);
- begin
- ExpandItem(True, Recurse);
- end;
-
- procedure TTreeNode.Collapse(Recurse: Boolean);
- begin
- ExpandItem(False, Recurse);
- end;
-
- function TTreeNode.GetExpanded: Boolean;
- begin
- Result := GetState(nsExpanded);
- end;
-
- procedure TTreeNode.SetExpanded(Value: Boolean);
- begin
- if Value then Expand(False)
- else Collapse(False);
- end;
-
- function TTreeNode.GetSelected: Boolean;
- begin
- Result := GetState(nsSelected);
- end;
-
- procedure TTreeNode.SetSelected(Value: Boolean);
- begin
- if Value then TreeView_SelectItem(Handle, ItemId)
- else if Selected then TreeView_SelectItem(Handle, nil);
- end;
-
- function TTreeNode.GetCut: Boolean;
- begin
- Result := GetState(nsCut);
- end;
-
- procedure TTreeNode.SetCut(Value: Boolean);
- var
- Item: TTVItem;
- Template: Integer;
- begin
- if Value then Template := -1
- else Template := 0;
- with Item do
- begin
- mask := TVIF_STATE;
- hItem := ItemId;
- stateMask := TVIS_CUT;
- state := stateMask and Template;
- end;
- TreeView_SetItem(Handle, Item);
- end;
-
- function TTreeNode.GetDropTarget: Boolean;
- begin
- Result := GetState(nsDropHilited);
- end;
-
- procedure TTreeNode.SetDropTarget(Value: Boolean);
- begin
- if Value then TreeView_SelectDropTarget(Handle, ItemId)
- else if DropTarget then TreeView_SelectDropTarget(Handle, nil);
- end;
-
- function TTreeNode.GetChildren: Boolean;
- var
- Item: TTVItem;
- begin
- Item.mask := TVIF_CHILDREN;
- Item.hItem := ItemId;
- if TreeView_GetItem(Handle, Item) then Result := Item.cChildren > 0
- else Result := False;
- end;
-
- procedure TTreeNode.SetFocused(Value: Boolean);
- var
- Item: TTVItem;
- Template: Integer;
- begin
- if Value then Template := -1
- else Template := 0;
- with Item do
- begin
- mask := TVIF_STATE;
- hItem := ItemId;
- stateMask := TVIS_FOCUSED;
- state := stateMask and Template;
- end;
- TreeView_SetItem(Handle, Item);
- end;
-
- function TTreeNode.GetFocused: Boolean;
- begin
- Result := GetState(nsFocused);
- end;
-
- procedure TTreeNode.SetChildren(Value: Boolean);
- var
- Item: TTVItem;
- begin
- with Item do
- begin
- mask := TVIF_CHILDREN;
- hItem := ItemId;
- cChildren := Ord(Value);
- end;
- TreeView_SetItem(Handle, Item);
- end;
-
- function TTreeNode.GetParent: TTreeNode;
- begin
- with FOwner do
- Result := GetNode(TreeView_GetParent(Handle, ItemId));
- end;
-
- function TTreeNode.GetNextSibling: TTreeNode;
- begin
- with FOwner do
- Result := GetNode(TreeView_GetNextSibling(Handle, ItemId));
- end;
-
- function TTreeNode.GetPrevSibling: TTreeNode;
- begin
- with FOwner do
- Result := GetNode(TreeView_GetPrevSibling(Handle, ItemId));
- end;
-
- function TTreeNode.GetNextVisible: TTreeNode;
- begin
- if IsVisible then
- with FOwner do
- Result := GetNode(TreeView_GetNextVisible(Handle, ItemId))
- else Result := nil;
- end;
-
- function TTreeNode.GetPrevVisible: TTreeNode;
- begin
- with FOwner do
- Result := GetNode(TreeView_GetPrevVisible(Handle, ItemId));
- end;
-
- function TTreeNode.GetNextChild(Value: TTreeNode): TTreeNode;
- begin
- if Value <> nil then Result := Value.GetNextSibling
- else Result := nil;
- end;
-
- function TTreeNode.GetPrevChild(Value: TTreeNode): TTreeNode;
- begin
- if Value <> nil then Result := Value.GetPrevSibling
- else Result := nil;
- end;
-
- function TTreeNode.GetFirstChild: TTreeNode;
- begin
- with FOwner do
- Result := GetNode(TreeView_GetChild(Handle, ItemId));
- end;
-
- function TTreeNode.GetLastChild: TTreeNode;
- var
- Node: TTreeNode;
- begin
- Result := GetFirstChild;
- if Result <> nil then
- begin
- Node := Result;
- repeat
- Result := Node;
- Node := Result.GetNextSibling;
- until Node = nil;
- end;
- end;
-
- function TTreeNode.GetNext: TTreeNode;
- var
- NodeID, ParentID: HTreeItem;
- Handle: HWND;
- begin
- Handle := FOwner.Handle;
- NodeID := TreeView_GetChild(Handle, ItemId);
- if NodeID = nil then NodeID := TreeView_GetNextSibling(Handle, ItemId);
- ParentID := ItemId;
- while (NodeID = nil) and (ParentID <> nil) do
- begin
- ParentID := TreeView_GetParent(Handle, ParentID);
- NodeID := TreeView_GetNextSibling(Handle, ParentID);
- end;
- Result := FOwner.GetNode(NodeID);
- end;
-
- function TTreeNode.GetPrev: TTreeNode;
- var
- Node: TTreeNode;
- begin
- Result := GetPrevSibling;
- if Result <> nil then
- begin
- Node := Result;
- repeat
- Result := Node;
- Node := Result.GetLastChild;
- until Node = nil;
- end else
- Result := Parent;
- end;
-
- function TTreeNode.GetAbsoluteIndex: Integer;
- var
- Node: TTreeNode;
- begin
- Result := -1;
- Node := Self;
- while Node <> nil do
- begin
- Inc(Result);
- Node := Node.GetPrev;
- end;
- end;
-
- function TTreeNode.GetIndex: Integer;
- var
- Node: TTreeNode;
- begin
- Result := -1;
- Node := Self;
- while Node <> nil do
- begin
- Inc(Result);
- Node := Node.GetPrevSibling;
- end;
- end;
-
- function TTreeNode.GetItem(Index: Integer): TTreeNode;
- begin
- Result := GetFirstChild;
- while (Result <> nil) and (Index > 0) do
- begin
- Result := GetNextChild(Result);
- Dec(Index);
- end;
- if Result = nil then TreeViewError(SListIndexError);
- end;
-
- procedure TTreeNode.SetItem(Index: Integer; Value: TTreeNode);
- begin
- item[Index].Assign(Value);
- end;
-
- function TTreeNode.IndexOf(Value: TTreeNode): Integer;
- var
- Node: TTreeNode;
- begin
- Result := -1;
- Node := GetFirstChild;
- while (Node <> nil) do
- begin
- Inc(Result);
- if Node = Value then Break;
- Node := GetNextChild(Node);
- end;
- if Node = nil then Result := -1;
- end;
-
- function TTreeNode.GetCount: Integer;
- var
- Node: TTreeNode;
- begin
- Result := 0;
- Node := GetFirstChild;
- while Node <> nil do
- begin
- Inc(Result);
- Node := Node.GetNextChild(Node);
- end;
- end;
-
- procedure TTreeNode.EndEdit(Cancel: Boolean);
- begin
- TreeView_EndEditLabelNow(Handle, Cancel);
- end;
-
- procedure TTreeNode.InternalMove(ParentNode, Node: TTreeNode;
- HItem: HTreeItem; AddMode: TAddMode);
- var
- I: Integer;
- NodeId: HTreeItem;
- TreeViewItem: TTVItem;
- Children: Boolean;
- IsSelected: Boolean;
- begin
- if (AddMode = taInsert) and (Node <> nil) then
- NodeId := Node.ItemId else
- NodeId := nil;
- Children := HasChildren;
- IsSelected := Selected;
- if (Parent <> nil) and (Parent.Count = 1) then
- begin
- Parent.Expanded := False;
- Parent.HasChildren := False;
- end;
- with TreeViewItem do
- begin
- mask := TVIF_PARAM;
- hItem := ItemId;
- lParam := 0;
- end;
- TreeView_SetItem(Handle, TreeViewItem);
- with Owner do
- HItem := AddItem(HItem, NodeId, CreateItem(Self), AddMode);
- if HItem = nil then
- raise EOutOfResources.CreateRes(sInsertError);
- for I := Count - 1 downto 0 do
- Item[I].InternalMove(Self, nil, HItem, taAddFirst);
- TreeView_DeleteItem(Handle, ItemId);
- FItemId := HItem;
- Assign(Self);
- HasChildren := Children;
- Selected := IsSelected;
- end;
-
- procedure TTreeNode.MoveTo(Destination: TTreeNode; Mode: TNodeAttachMode);
- var
- AddMode: TAddMode;
- Node: TTreeNode;
- HItem: HTreeItem;
- OldOnChanging: TTVChangingEvent;
- OldOnChange: TTVChangedEvent;
- begin
- OldOnChanging := TreeView.OnChanging;
- OldOnChange := TreeView.OnChange;
- TreeView.OnChanging := nil;
- TreeView.OnChange := nil;
- try
- if (Destination = nil) or not Destination.HasAsParent(Self) then
- begin
- AddMode := taAdd;
- if (Destination <> nil) and not (Mode in [naAddChild, naAddChildFirst]) then
- Node := Destination.Parent else
- Node := Destination;
- case Mode of
- naAdd,
- naAddChild: AddMode := taAdd;
- naAddFirst,
- naAddChildFirst: AddMode := taAddFirst;
- naInsert:
- begin
- Destination := Destination.GetPrevSibling;
- if Destination = nil then AddMode := taAddFirst
- else AddMode := taInsert;
- end;
- end;
- if Node <> nil then
- HItem := Node.ItemId else
- HItem := nil;
- InternalMove(Node, Destination, HItem, AddMode);
- Node := Parent;
- if Node <> nil then
- begin
- Node.HasChildren := True;
- Node.Expanded := True;
- end;
- end;
- finally
- TreeView.OnChanging := OldOnChanging;
- TreeView.OnChange := OldOnChange;
- end;
- end;
-
- procedure TTreeNode.MakeVisible;
- begin
- TreeView_EnsureVisible(Handle, ItemId);
- end;
-
- function TTreeNode.GetLevel: Integer;
- var
- Node: TTreeNode;
- begin
- Result := 0;
- Node := Parent;
- while Node <> nil do
- begin
- Inc(Result);
- Node := Node.Parent;
- end;
- end;
-
- function TTreeNode.IsNodeVisible: Boolean;
- var
- Rect: TRect;
- begin
- Result := TreeView_GetItemRect(Handle, ItemId, Rect, True);
- end;
-
- function TTreeNode.HasVisibleParent: Boolean;
- begin
- Result := (Parent <> nil) and (Parent.Expanded);
- end;
-
- function TTreeNode.EditText: Boolean;
- begin
- Result := TreeView_EditLabel(Handle, ItemId) <> 0;
- end;
-
- function TTreeNode.DisplayRect(TextOnly: Boolean): TRect;
- begin
- FillChar(Result, SizeOf(Result), 0);
- TreeView_GetItemRect(Handle, ItemId, Result, TextOnly);
- end;
-
- function TTreeNode.AlphaSort: Boolean;
- begin
- Result := CustomSort(nil, 0);
- end;
-
- function TTreeNode.CustomSort(SortProc: TTVCompare; Data: Longint): Boolean;
- var
- SortCB: TTVSortCB;
- begin
- with SortCB do
- begin
- if not Assigned(SortProc) then lpfnCompare := @DefaultTreeViewSort
- else lpfnCompare := SortProc;
- hParent := ItemId;
- lParam := Data;
- end;
- Result := TreeView_SortChildrenCB(Handle, SortCB, 0);
- end;
-
- procedure TTreeNode.Delete;
- begin
- if not Deleting then Free;
- end;
-
- procedure TTreeNode.DeleteChildren;
- var
- Node: TTreeNode;
- begin
- repeat
- Node := GetFirstChild;
- if Node <> nil then Node.Delete;
- until Node = nil;
- end;
-
- procedure TTreeNode.Assign(Source: TPersistent);
- var
- Node: TTreeNode;
- begin
- if Source is TTreeNode then
- begin
- Node := TTreeNode(Source);
- Text := Node.Text;
- Data := Node.Data;
- ImageIndex := Node.ImageIndex;
- SelectedIndex := Node.SelectedIndex;
- StateIndex := Node.StateIndex;
- OverlayIndex := Node.OverlayIndex;
- Focused := Node.Focused;
- DropTarget := Node.DropTarget;
- Cut := Node.Cut;
- HasChildren := Node.HasChildren;
- end
- else inherited Assign(Source);
- end;
-
- function TTreeNode.IsEqual(Node: TTreeNode): Boolean;
- begin
- Result := (Text = Node.Text) and (Data = Node.Data);
- end;
-
- procedure TTreeNode.ReadData(Stream: TStream; Info: PNodeInfo);
- var
- I, Size, ItemCount: Integer;
- begin
- Stream.ReadBuffer(Size, SizeOf(Size));
- Stream.ReadBuffer(Info^, Size);
- Text := Info^.Text;
- ImageIndex := Info^.ImageIndex;
- SelectedIndex := Info^.SelectedIndex;
- StateIndex := Info^.StateIndex;
- OverlayIndex := Info^.OverlayIndex;
- Data := Info^.Data;
- ItemCount := Info^.Count;
- for I := 0 to ItemCount - 1 do
- with Owner.AddChild(Self, '') do ReadData(Stream, Info);
- end;
-
- procedure TTreeNode.WriteData(Stream: TStream; Info: PNodeInfo);
- var
- I, Size, L, ItemCount: Integer;
- begin
- L := Length(Text);
- if L > 255 then L := 255;
- Size := SizeOf(TNodeInfo) + L - 255;
- Info^.Text := Text;
- Info^.ImageIndex := ImageIndex;
- Info^.SelectedIndex := SelectedIndex;
- Info^.OverlayIndex := OverlayIndex;
- Info^.StateIndex := StateIndex;
- Info^.Data := Data;
- ItemCount := Count;
- Info^.Count := ItemCount;
- Stream.WriteBuffer(Size, SizeOf(Size));
- Stream.WriteBuffer(Info^, Size);
- for I := 0 to ItemCount - 1 do Item[I].WriteData(Stream, Info);
- end;
-
- { TTreeNodes }
-
- constructor TTreeNodes.Create(AOwner: TCustomTreeView);
- begin
- inherited Create;
- FOwner := AOwner;
- end;
-
- destructor TTreeNodes.Destroy;
- begin
- Clear;
- inherited Destroy;
- end;
-
- function TTreeNodes.GetCount: Integer;
- begin
- if Owner.HandleAllocated then Result := TreeView_GetCount(Handle)
- else Result := 0;
- end;
-
- function TTreeNodes.GetHandle: HWND;
- begin
- Result := Owner.Handle;
- end;
-
- procedure TTreeNodes.Delete(Node: TTreeNode);
- begin
- if (Node.ItemId = nil) and Assigned(Owner.FOnDeletion) then
- Owner.FOnDeletion(Self, Node);
- Node.Delete;
- end;
-
- procedure TTreeNodes.Clear;
- begin
- if Owner.HandleAllocated then
- TreeView_DeleteAllItems(Handle);
- end;
-
- function TTreeNodes.AddChildFirst(Node: TTreeNode; const S: string): TTreeNode;
- begin
- Result := AddChildObjectFirst(Node, S, nil);
- end;
-
- function TTreeNodes.AddChildObjectFirst(Node: TTreeNode; const S: string;
- Ptr: Pointer): TTreeNode;
- begin
- Result := InternalAddObject(Node, S, Ptr, taAddFirst);
- end;
-
- function TTreeNodes.AddChild(Node: TTreeNode; const S: string): TTreeNode;
- begin
- Result := AddChildObject(Node, S, nil);
- end;
-
- function TTreeNodes.AddChildObject(Node: TTreeNode; const S: string;
- Ptr: Pointer): TTreeNode;
- begin
- Result := InternalAddObject(Node, S, Ptr, taAdd);
- end;
-
- function TTreeNodes.AddFirst(Node: TTreeNode; const S: string): TTreeNode;
- begin
- Result := AddObjectFirst(Node, S, nil);
- end;
-
- function TTreeNodes.AddObjectFirst(Node: TTreeNode; const S: string;
- Ptr: Pointer): TTreeNode;
- begin
- if Node <> nil then Node := Node.Parent;
- Result := InternalAddObject(Node, S, Ptr, taAddFirst);
- end;
-
- function TTreeNodes.Add(Node: TTreeNode; const S: string): TTreeNode;
- begin
- Result := AddObject(Node, S, nil);
- end;
-
- procedure TTreeNodes.Repaint(Node: TTreeNode);
- var
- R: TRect;
- begin
- while (Node <> nil) and not Node.IsVisible do Node := Node.Parent;
- if Node <> nil then
- begin
- R := Node.DisplayRect(False);
- InvalidateRect(Owner.Handle, @R, True);
- end;
- end;
-
- function TTreeNodes.AddObject(Node: TTreeNode; const S: string;
- Ptr: Pointer): TTreeNode;
- begin
- if Node <> nil then Node := Node.Parent;
- Result := InternalAddObject(Node, S, Ptr, taAdd);
- end;
-
- function TTreeNodes.Insert(Node: TTreeNode; const S: string): TTreeNode;
- begin
- Result := InsertObject(Node, S, nil);
- end;
-
- procedure TTreeNodes.AddedNode(Value: TTreeNode);
- begin
- Value := Value.Parent;
- if Value <> nil then
- begin
- Value.HasChildren := True;
- Repaint(Value);
- end;
- end;
-
- function TTreeNodes.InsertObject(Node: TTreeNode; const S: string;
- Ptr: Pointer): TTreeNode;
- var
- Item, ItemId: HTreeItem;
- Parent: TTreeNode;
- AddMode: TAddMode;
- begin
- Result := Owner.CreateNode;
- try
- Item := nil;
- ItemId := nil;
- AddMode := taInsert;
- if Node <> nil then
- begin
- Parent := Node.Parent;
- if Parent <> nil then Item := Parent.ItemId;
- Node := Node.GetPrevSibling;
- if Node <> nil then ItemId := Node.ItemId
- else AddMode := taAddFirst;
- end;
- Result.Data := Ptr;
- Result.Text := S;
- Item := AddItem(Item, ItemId, CreateItem(Result), AddMode);
- if Item = nil then
- raise EOutOfResources.CreateRes(sInsertError);
- Result.FItemId := Item;
- AddedNode(Result);
- except
- Result.Free;
- raise;
- end;
- end;
-
- function TTreeNodes.InternalAddObject(Node: TTreeNode; const S: string;
- Ptr: Pointer; AddMode: TAddMode): TTreeNode;
- var
- Item: HTreeItem;
- begin
- Result := Owner.CreateNode;
- try
- if Node <> nil then Item := Node.ItemId
- else Item := nil;
- Result.Data := Ptr;
- Result.Text := S;
- Item := AddItem(Item, nil, CreateItem(Result), AddMode);
- if Item = nil then
- raise EOutOfResources.CreateRes(sInsertError);
- Result.FItemId := Item;
- AddedNode(Result);
- except
- Result.Free;
- raise;
- end;
- end;
-
- function TTreeNodes.CreateItem(Node: TTreeNode): TTVItem;
- begin
- with Result do
- begin
- mask := TVIF_TEXT or TVIF_PARAM or TVIF_IMAGE or TVIF_SELECTEDIMAGE;
- lParam := Longint(Node);
- pszText := LPSTR_TEXTCALLBACK;
- iImage := I_IMAGECALLBACK;
- iSelectedImage := I_IMAGECALLBACK;
- end;
- end;
-
- function TTreeNodes.AddItem(Parent, Target: HTreeItem;
- const Item: TTVItem; AddMode: TAddMode): HTreeItem;
- var
- InsertStruct: TTVInsertStruct;
- begin
- with InsertStruct do
- begin
- hParent := Parent;
- case AddMode of
- taAddFirst:
- hInsertAfter := TVI_FIRST;
- taAdd:
- hInsertAfter := TVI_LAST;
- taInsert:
- hInsertAfter := Target;
- end;
- end;
- InsertStruct.item := Item;
- Result := TreeView_InsertItem(Handle, InsertStruct);
- end;
-
- function TTreeNodes.GetFirstNode: TTreeNode;
- begin
- Result := GetNode(TreeView_GetRoot(Handle));
- end;
-
- function TTreeNodes.GetNodeFromIndex(Index: Integer): TTreeNode;
- begin
- Result := GetFirstNode;
- while (Index <> 0) and (Result <> nil) do
- begin
- Result := Result.GetNext;
- Dec(Index);
- end;
- if Result = nil then TreeViewError(sInvalidIndex);
- end;
-
- function TTreeNodes.GetNode(ItemId: HTreeItem): TTreeNode;
- var
- Item: TTVItem;
- begin
- with Item do
- begin
- hItem := ItemId;
- mask := TVIF_PARAM;
- end;
- if TreeView_GetItem(Handle, Item) then Result := TTreeNode(Item.lParam)
- else Result := nil;
- end;
-
- procedure TTreeNodes.SetItem(Index: Integer; Value: TTreeNode);
- begin
- GetNodeFromIndex(Index).Assign(Value);
- end;
-
- procedure TTreeNodes.BeginUpdate;
- begin
- if FUpdateCount = 0 then SetUpdateState(True);
- Inc(FUpdateCount);
- end;
-
- procedure TTreeNodes.SetUpdateState(Updating: Boolean);
- begin
- SendMessage(Handle, WM_SETREDRAW, Ord(not Updating), 0);
- if not Updating then Owner.Refresh;
- end;
-
- procedure TTreeNodes.EndUpdate;
- begin
- Dec(FUpdateCount);
- if FUpdateCount = 0 then SetUpdateState(False);
- end;
-
- procedure TTreeNodes.Assign(Source: TPersistent);
- var
- TreeNodes: TTreeNodes;
- MemStream: TMemoryStream;
- begin
- if Source is TTreeNodes then
- begin
- TreeNodes := TTreeNodes(Source);
- Clear;
- MemStream := TMemoryStream.Create;
- try
- TreeNodes.WriteData(MemStream);
- MemStream.Position := 0;
- ReadData(MemStream);
- finally
- MemStream.Free;
- end;
- end
- else inherited Assign(Source);
- end;
-
- procedure TTreeNodes.DefineProperties(Filer: TFiler);
-
- function WriteNodes: Boolean;
- var
- I: Integer;
- Nodes: TTreeNodes;
- begin
- Nodes := TTreeNodes(Filer.Ancestor);
- if (Nodes <> nil) and (Nodes.Count = Count) then
- for I := 0 to Count - 1 do
- begin
- Result := not Item[I].IsEqual(Nodes[I]);
- if Result then Break;
- end
- else Result := Count > 0;
- end;
-
- begin
- inherited DefineProperties(Filer);
- Filer.DefineBinaryProperty('Data', ReadData, WriteData, WriteNodes);
- end;
-
- procedure TTreeNodes.ReadData(Stream: TStream);
- var
- I, Count: Integer;
- NodeInfo: TNodeInfo;
- begin
- Clear;
- Stream.ReadBuffer(Count, SizeOf(Count));
- for I := 0 to Count - 1 do
- Add(nil, '').ReadData(Stream, @NodeInfo);
- end;
-
- procedure TTreeNodes.WriteData(Stream: TStream);
- var
- I: Integer;
- Node: TTreeNode;
- NodeInfo: TNodeInfo;
- begin
- I := 0;
- Node := GetFirstNode;
- while Node <> nil do
- begin
- Inc(I);
- Node := Node.GetNextSibling;
- end;
- Stream.WriteBuffer(I, SizeOf(I));
- Node := GetFirstNode;
- while Node <> nil do
- begin
- Node.WriteData(Stream, @NodeInfo);
- Node := Node.GetNextSibling;
- end;
- end;
-
- type
- TTreeStrings = class(TStrings)
- private
- FOwner: TTreeNodes;
- protected
- function Get(Index: Integer): string; override;
- function GetCount: Integer; override;
- function GetObject(Index: Integer): TObject; override;
- procedure PutObject(Index: Integer; AObject: TObject); override;
- procedure SetUpdateState(Updating: Boolean); override;
- public
- constructor Create(AOwner: TTreeNodes);
- function Add(const S: string): Integer; override;
- procedure Clear; override;
- procedure Delete(Index: Integer); override;
- procedure Insert(Index: Integer; const S: string); override;
- property Owner: TTreeNodes read FOwner;
- end;
-
- constructor TTreeStrings.Create(AOwner: TTreeNodes);
- begin
- inherited Create;
- FOwner := AOwner;
- end;
-
- function TTreeStrings.Get(Index: Integer): string;
- const
- TAB = Chr(9);
- var
- Level, I: Integer;
- Node: TTreeNode;
- begin
- Result := '';
- Node := Owner.GetNodeFromIndex(Index);
- Level := Node.Level;
- for I := 0 to Level - 1 do Result := Result + TAB;
- Result := Result + Node.Text;
- end;
-
- function TTreeStrings.GetObject(Index: Integer): TObject;
- begin
- Result := Owner.GetNodeFromIndex(Index).Data;
- end;
-
- procedure TTreeStrings.PutObject(Index: Integer; AObject: TObject);
- begin
- Owner.GetNodeFromIndex(Index).Data := AObject;
- end;
-
- function TTreeStrings.GetCount: Integer;
- begin
- Result := Owner.Count;
- end;
-
- procedure TTreeStrings.Clear;
- begin
- Owner.Clear;
- end;
-
- procedure TTreeStrings.Delete(Index: Integer);
- begin
- Owner.GetNodeFromIndex(Index).Delete;
- end;
-
- procedure TTreeStrings.SetUpdateState(Updating: Boolean);
- begin
- SendMessage(Owner.Handle, WM_SETREDRAW, Ord(not Updating), 0);
- if not Updating then Owner.Owner.Refresh;
- end;
-
- function TTreeStrings.Add(const S: string): Integer;
- var
- Level, OldLevel, I: Integer;
- NewStr: string;
- Node: TTreeNode;
-
- function GetBufStart(Buffer: PChar; var Level: Integer): PChar;
- begin
- Level := 0;
- while Buffer^ in [' ', #9] do
- begin
- Inc(Buffer);
- Inc(Level);
- end;
- Result := Buffer;
- end;
-
- begin
- Result := GetCount;
- if (Length(S) = 1) and (S[1] = Chr($1A)) then Exit;
- Node := nil;
- OldLevel := 0;
- NewStr := GetBufStart(PChar(S), Level);
- if Result > 0 then
- begin
- Node := Owner.GetNodeFromIndex(Result - 1);
- OldLevel := Node.Level;
- end;
- if (Level > OldLevel) or (Node = nil) then
- begin
- if Level - OldLevel > 1 then TreeViewError(sInvalidLevel);
- end
- else begin
- for I := OldLevel downto Level do
- begin
- Node := Node.Parent;
- if (Node = nil) and (I - Level > 0) then
- TreeViewError(sInvalidLevel);
- end;
- end;
- Owner.AddChild(Node, NewStr);
- end;
-
- procedure TTreeStrings.Insert(Index: Integer; const S: string);
- begin
- with Owner do
- Insert(GetNodeFromIndex(Index), S);
- end;
-
- { TCustomTreeView }
-
- constructor TCustomTreeView.Create(AOwner: TComponent);
- begin
- inherited Create(AOwner);
- ControlStyle := ControlStyle - [csCaptureMouse] + [csDisplayDragImage];
- Width := 121;
- Height := 97;
- TabStop := True;
- ParentColor := False;
- FTreeNodes := TTreeNodes.Create(Self);
- FBorderStyle := bsSingle;
- FShowButtons := True;
- FShowRoot := True;
- FShowLines := True;
- FHideSelection := True;
- FDragImage := TImageList.CreateSize(32, 32);
- FSaveIndent := -1;
- FEditInstance := MakeObjectInstance(EditWndProc);
- FImageChangeLink := TChangeLink.Create;
- FImageChangeLink.OnChange := ImageListChange;
- FStateChangeLink := TChangeLink.Create;
- FStateChangeLink.OnChange := ImageListChange;
- end;
-
- destructor TCustomTreeView.Destroy;
- begin
- Items.Free;
- FSaveItems.Free;
- FDragImage.Free;
- FMemStream.Free;
- FreeObjectInstance(FEditInstance);
- FImageChangeLink.Free;
- FStateChangeLink.Free;
- inherited Destroy;
- end;
-
- procedure TCustomTreeView.CreateParams(var Params: TCreateParams);
- const
- BorderStyles: array[TBorderStyle] of Integer = (0, WS_BORDER);
- LineStyles: array[Boolean] of Integer = (0, TVS_HASLINES);
- RootStyles: array[Boolean] of Integer = (0, TVS_LINESATROOT);
- ButtonStyles: array[Boolean] of Integer = (0, TVS_HASBUTTONS);
- EditStyles: array[Boolean] of Integer = (TVS_EDITLABELS, 0);
- HideSelections: array[Boolean] of Integer = (TVS_SHOWSELALWAYS, 0);
- DragStyles: array[TDragMode] of Integer = (TVS_DISABLEDRAGDROP, 0);
- begin
- InitCommonControls;
- inherited CreateParams(Params);
- CreateSubClass(Params, WC_TREEVIEW);
- with Params do
- begin
- Style := Style or LineStyles[FShowLines] or BorderStyles[FBorderStyle] or
- RootStyles[FShowRoot] or ButtonStyles[FShowButtons] or
- EditStyles[FReadOnly] or HideSelections[FHideSelection] or
- DragStyles[DragMode];
- if Ctl3D and (FBorderStyle = bsSingle) then
- ExStyle := Params.ExStyle or WS_EX_CLIENTEDGE;
- end;
- end;
-
- procedure TCustomTreeView.CreateWnd;
- begin
- inherited CreateWnd;
- if FMemStream <> nil then
- begin
- Items.ReadData(FMemStream);
- FMemStream.Destroy;
- FMemStream := nil;
- SetTopItem(Items.GetNodeFromIndex(FSaveTopIndex));
- FSaveTopIndex := 0;
- SetSelection(Items.GetNodeFromIndex(FSaveIndex));
- FSaveIndex := 0;
- end;
- if FSaveIndent <> -1 then Indent := FSaveIndent;
- if (Images <> nil) and Images.HandleAllocated then
- SetImageList(Images.Handle, TVSIL_NORMAL);
- if (StateImages <> nil) and StateImages.HandleAllocated then
- SetImageList(StateImages.Handle, TVSIL_STATE);
- end;
-
- procedure TCustomTreeView.DestroyWnd;
- var
- Node: TTreeNode;
- begin
- if Items.Count > 0 then
- begin
- FMemStream := TMemoryStream.Create;
- Items.WriteData(FMemStream);
- FMemStream.Position := 0;
- Node := GetTopItem;
- if Node <> nil then FSaveTopIndex := Node.AbsoluteIndex;
- Node := Selected;
- if Node <> nil then FSaveIndex := Node.AbsoluteIndex;
- end;
- FSaveIndent := Indent;
- inherited DestroyWnd;
- end;
-
- procedure TCustomTreeView.EditWndProc(var Message: TMessage);
- begin
- try
- with Message do
- begin
- case Msg of
- WM_KEYDOWN,
- WM_SYSKEYDOWN: if DoKeyDown(TWMKey(Message)) then Exit;
- WM_CHAR: if DoKeyPress(TWMKey(Message)) then Exit;
- WM_KEYUP,
- WM_SYSKEYUP: if DoKeyUp(TWMKey(Message)) then Exit;
- CN_KEYDOWN,
- CN_CHAR, CN_SYSKEYDOWN,
- CN_SYSCHAR:
- begin
- WndProc(Message);
- Exit;
- end;
- end;
- Result := CallWindowProc(FDefEditProc, FEditHandle, Msg, WParam, LParam);
- end;
- except
- Application.HandleException(Self);
- end;
- end;
-
- procedure TCustomTreeView.CMColorChanged(var Message: TMessage);
- begin
- inherited;
- RecreateWnd;
- end;
-
- procedure TCustomTreeView.CMCtl3DChanged(var Message: TMessage);
- begin
- inherited;
- if FBorderStyle = bsSingle then RecreateWnd;
- end;
-
- function TCustomTreeView.AlphaSort: Boolean;
- var
- I: Integer;
- begin
- if HandleAllocated then
- begin
- Result := CustomSort(nil, 0);
- for I := 0 to Items.Count - 1 do
- with Items[I] do
- if HasChildren then AlphaSort;
- end
- else Result := False;
- end;
-
- function TCustomTreeView.CustomSort(SortProc: TTVCompare; Data: Longint): Boolean;
- var
- SortCB: TTVSortCB;
- I: Integer;
- Node: TTreeNode;
- begin
- Result := False;
- if HandleAllocated then
- begin
- with SortCB do
- begin
- if not Assigned(SortProc) then lpfnCompare := @DefaultTreeViewSort
- else lpfnCompare := SortProc;
- hParent := TVI_ROOT;
- lParam := Data;
- Result := TreeView_SortChildrenCB(Handle, SortCB, 0);
- end;
- for I := 0 to Items.Count - 1 do
- begin
- Node := Items[I];
- if Node.HasChildren then Node.CustomSort(SortProc, Data);
- end;
- end;
- end;
-
- procedure TCustomTreeView.SetSortType(Value: TSortType);
- begin
- if SortType <> Value then
- begin
- FSortType := Value;
- if ((SortType in [stData, stBoth]) and Assigned(OnCompare)) or
- (SortType in [stText, stBoth]) then
- AlphaSort;
- end;
- end;
-
- procedure TCustomTreeView.SetStyle(Value: Integer; UseStyle: Boolean);
- var
- Style: Integer;
- begin
- if HandleAllocated then
- begin
- Style := GetWindowLong(Handle, GWL_STYLE);
- if not UseStyle then Style := Style and not Value
- else Style := Style or Value;
- SetWindowLong(Handle, GWL_STYLE, Style);
- end;
- end;
-
- procedure TCustomTreeView.SetBorderStyle(Value: TBorderStyle);
- begin
- if BorderStyle <> Value then
- begin
- FBorderStyle := Value;
- RecreateWnd;
- end;
- end;
-
- procedure TCustomTreeView.SetDragMode(Value: TDragMode);
- begin
- if Value <> DragMode then
- SetStyle(TVS_DISABLEDRAGDROP, Value = dmManual);
- inherited;
- end;
-
- procedure TCustomTreeView.SetButtonStyle(Value: Boolean);
- begin
- if ShowButtons <> Value then
- begin
- FShowButtons := Value;
- SetStyle(TVS_HASBUTTONS, Value);
- end;
- end;
-
- procedure TCustomTreeView.SetLineStyle(Value: Boolean);
- begin
- if ShowLines <> Value then
- begin
- FShowLines := Value;
- SetStyle(TVS_HASLINES, Value);
- end;
- end;
-
- procedure TCustomTreeView.SetRootStyle(Value: Boolean);
- begin
- if ShowRoot <> Value then
- begin
- FShowRoot := Value;
- SetStyle(TVS_LINESATROOT, Value);
- end;
- end;
-
- procedure TCustomTreeView.SetReadOnly(Value: Boolean);
- begin
- if ReadOnly <> Value then
- begin
- FReadOnly := Value;
- SetStyle(TVS_EDITLABELS, not Value);
- end;
- end;
-
- procedure TCustomTreeView.SetHideSelection(Value: Boolean);
- begin
- if HideSelection <> Value then
- begin
- FHideSelection := Value;
- SetStyle(TVS_SHOWSELALWAYS, not Value);
- end;
- end;
-
- function TCustomTreeView.GetNodeAt(X, Y: Integer): TTreeNode;
- var
- HitTest: TTVHitTestInfo;
- begin
- with HitTest do
- begin
- pt.X := X;
- pt.Y := Y;
- if TreeView_HitTest(Handle, HitTest) <> nil then
- Result := Items.GetNode(HitTest.hItem)
- else Result := nil;
- end;
- end;
-
- function TCustomTreeView.GetHitTestInfoAt(X, Y: Integer): THitTests;
- var
- HitTest: TTVHitTestInfo;
- begin
- Result := [];
- with HitTest do
- begin
- pt.X := X;
- pt.Y := Y;
- TreeView_HitTest(Handle, HitTest);
- if (flags and TVHT_ABOVE) <> 0 then Include(Result, htAbove);
- if (flags and TVHT_BELOW) <> 0 then Include(Result, htBelow);
- if (flags and TVHT_NOWHERE) <> 0 then Include(Result, htNowhere);
- if (flags and TVHT_ONITEM) <> 0 then Include(Result, htOnItem);
- if (flags and TVHT_ONITEMBUTTON) <> 0 then Include(Result, htOnButton);
- if (flags and TVHT_ONITEMICON) <> 0 then Include(Result, htOnIcon);
- if (flags and TVHT_ONITEMINDENT) <> 0 then Include(Result, htOnIndent);
- if (flags and TVHT_ONITEMLABEL) <> 0 then Include(Result, htOnLabel);
- if (flags and TVHT_ONITEMRIGHT) <> 0 then Include(Result, htOnRight);
- if (flags and TVHT_ONITEMSTATEICON) <> 0 then Include(Result, htOnStateIcon);
- if (flags and TVHT_TOLEFT) <> 0 then Include(Result, htToLeft);
- if (flags and TVHT_TORIGHT) <> 0 then Include(Result, htToRight);
- end;
- end;
-
- procedure TCustomTreeView.SetTreeNodes(Value: TTreeNodes);
- begin
- Items.Assign(Value);
- end;
-
- procedure TCustomTreeView.SetIndent(Value: Integer);
- begin
- if Value <> Indent then TreeView_SetIndent(Handle, Value);
- end;
-
- function TCustomTreeView.GetIndent: Integer;
- begin
- Result := TreeView_GetIndent(Handle)
- end;
-
- procedure TCustomTreeView.FullExpand;
- var
- Node: TTreeNode;
- begin
- Node := Items.GetFirstNode;
- while Node <> nil do
- begin
- Node.Expand(True);
- Node := Node.GetNextSibling;
- end;
- end;
-
- procedure TCustomTreeView.FullCollapse;
- var
- Node: TTreeNode;
- begin
- Node := Items.GetFirstNode;
- while Node <> nil do
- begin
- Node.Collapse(True);
- Node := Node.GetNextSibling;
- end;
- end;
-
- procedure TCustomTreeView.Loaded;
- begin
- inherited Loaded;
- if csDesigning in ComponentState then FullExpand;
- end;
-
- function TCustomTreeView.GetTopItem: TTreeNode;
- begin
- if HandleAllocated then
- Result := Items.GetNode(TreeView_GetFirstVisible(Handle))
- else Result := nil;
- end;
-
- procedure TCustomTreeView.SetTopItem(Value: TTreeNode);
- begin
- if HandleAllocated and (Value <> nil) then
- TreeView_SelectSetFirstVisible(Handle, Value.ItemId);
- end;
-
- function TCustomTreeView.GetSelection: TTreeNode;
- begin
- if HandleAllocated then
- Result := Items.GetNode(TreeView_GetSelection(Handle))
- else Result := nil;
- end;
-
- procedure TCustomTreeView.SetSelection(Value: TTreeNode);
- begin
- if Value <> nil then Value.Selected := True
- else TreeView_SelectItem(Handle, nil);
- end;
-
- function TCustomTreeView.GetDropTarget: TTreeNode;
- begin
- if HandleAllocated then
- begin
- Result := Items.GetNode(TreeView_GetDropHilite(Handle));
- if Result = nil then Result := FLastDropTarget;
- end
- else Result := nil;
- end;
-
- procedure TCustomTreeView.SetDropTarget(Value: TTreeNode);
- begin
- if HandleAllocated then
- if Value <> nil then Value.DropTarget := True
- else TreeView_SelectDropTarget(Handle, nil);
- end;
-
- function TCustomTreeView.GetNodeFromItem(const Item: TTVItem): TTreeNode;
- begin
- with Item do
- if (state and TVIF_PARAM) <> 0 then Result := Pointer(lParam)
- else Result := Items.GetNode(hItem);
- end;
-
- function TCustomTreeView.IsEditing: Boolean;
- begin
- Result := TreeView_GetEditControl(Handle) <> 0;
- end;
-
- procedure TCustomTreeView.CNNotify(var Message: TWMNotify);
- var
- Node: TTreeNode;
- begin
- with Message.NMHdr^ do
- case code of
- TVN_BEGINDRAG:
- begin
- FDragged := True;
- with PNMTreeView(Pointer(Message.NMHdr))^ do
- FDragNode := GetNodeFromItem(ItemNew);
- end;
- TVN_BEGINLABELEDIT:
- begin
- with PTVDispInfo(Pointer(Message.NMHdr))^ do
- if Dragging or not CanEdit(GetNodeFromItem(item)) then
- Message.Result := 1;
- if Message.Result = 0 then
- begin
- FEditHandle := TreeView_GetEditControl(Handle);
- FDefEditProc := Pointer(GetWindowLong(FEditHandle, GWL_WNDPROC));
- SetWindowLong(FEditHandle, GWL_WNDPROC, LongInt(FEditInstance));
- end;
- end;
- TVN_ENDLABELEDIT:
- with PTVDispInfo(Pointer(Message.NMHdr))^ do
- Edit(item);
- TVN_ITEMEXPANDING:
- with PNMTreeView(Pointer(Message.NMHdr))^ do
- begin
- Node := GetNodeFromItem(ItemNew);
- if (action = TVE_EXPAND) and not CanExpand(Node) then
- Message.Result := 1
- else if (action = TVE_COLLAPSE) and
- not CanCollapse(Node) then Message.Result := 1;
- end;
- TVN_ITEMEXPANDED:
- with PNMTreeView(Pointer(Message.NMHdr))^ do
- begin
- Node := GetNodeFromItem(itemNew);
- if (action = TVE_EXPAND) then Expand(Node)
- else if (action = TVE_COLLAPSE) then Collapse(Node);
- end;
- TVN_SELCHANGING:
- with PNMTreeView(Pointer(Message.NMHdr))^ do
- if not CanChange(GetNodeFromItem(itemNew)) then
- Message.Result := 1;
- TVN_SELCHANGED:
- with PNMTreeView(Pointer(Message.NMHdr))^ do
- Change(GetNodeFromItem(itemNew));
- TVN_DELETEITEM:
- begin
- with PNMTreeView(Pointer(Message.NMHdr))^ do
- Node := GetNodeFromItem(itemOld);
- if Node <> nil then
- begin
- Node.FItemId := nil;
- Items.Delete(Node);
- end;
- end;
- TVN_SETDISPINFO:
- with PTVDispInfo(Pointer(Message.NMHdr))^ do
- begin
- Node := GetNodeFromItem(item);
- if (Node <> nil) and ((item.mask and TVIF_TEXT) <> 0) then
- Node.Text := item.pszText;
- end;
- TVN_GETDISPINFO:
- with PTVDispInfo(Pointer(Message.NMHdr))^ do
- begin
- Node := GetNodeFromItem(item);
- if Node <> nil then
- begin
- if (item.mask and TVIF_TEXT) <> 0 then
- StrLCopy(item.pszText, PChar(Node.Text), item.cchTextMax);
- if (item.mask and TVIF_IMAGE) <> 0 then
- begin
- GetImageIndex(Node);
- item.iImage := Node.ImageIndex;
- end;
- if (item.mask and TVIF_SELECTEDIMAGE) <> 0 then
- begin
- GetSelectedIndex(Node);
- item.iSelectedImage := Node.SelectedIndex;
- end;
- end;
- end;
- NM_RCLICK: FRClicked := True;
- end;
- end;
-
- function TCustomTreeView.GetDragImages: TCustomImageList;
- begin
- if FDragImage.Count > 0 then
- Result := FDragImage else
- Result := nil;
- end;
-
- procedure TCustomTreeView.WndProc(var Message: TMessage);
- begin
- if not (csDesigning in ComponentState) and ((Message.Msg = WM_LBUTTONDOWN) or
- (Message.Msg = WM_LBUTTONDBLCLK)) and not Dragging and (DragMode = dmAutomatic) then
- begin
- if not IsControlMouseMsg(TWMMouse(Message)) then
- begin
- ControlState := ControlState + [csLButtonDown];
- Dispatch(Message);
- end;
- end
- else inherited WndProc(Message);
- end;
-
- procedure TCustomTreeView.DoStartDrag(var DragObject: TDragObject);
- var
- ImageHandle: HImageList;
- DragNode: TTreeNode;
- P: TPoint;
- begin
- inherited DoStartDrag(DragObject);
- DragNode := FDragNode;
- FLastDropTarget := nil;
- FDragNode := nil;
- if DragNode = nil then
- begin
- GetCursorPos(P);
- with ScreenToClient(P) do DragNode := GetNodeAt(X, Y);
- end;
- if DragNode <> nil then
- begin
- ImageHandle := TreeView_CreateDragImage(Handle, DragNode.ItemId);
- if ImageHandle <> 0 then
- with FDragImage do
- begin
- Handle := ImageHandle;
- SetDragImage(0, 2, 2);
- end;
- end;
- end;
-
- procedure TCustomTreeView.DoEndDrag(Target: TObject; X, Y: Integer);
- begin
- inherited DoEndDrag(Target, X, Y);
- FLastDropTarget := nil;
- end;
-
- procedure TCustomTreeView.CMDrag(var Message: TCMDrag);
- begin
- inherited;
- if Message.Result <> 0 then
- with Message, DragRec^ do
- case DragMessage of
- dmDragMove: with ScreenToClient(Pos) do DoDragOver(Source, X, Y);
- dmDragLeave:
- begin
- TDragObject(Source).HideDragImage;
- FLastDropTarget := DropTarget;
- DropTarget := nil;
- TDragObject(Source).ShowDragImage;
- end;
- dmDragDrop: FLastDropTarget := nil;
- end;
- end;
-
- procedure TCustomTreeView.DoDragOver(Source: TDragObject; X, Y: Integer);
- var
- Node: TTreeNode;
- begin
- Node := GetNodeAt(X, Y);
- if (Node <> nil) and
- ((Node <> DropTarget) or (Node = FLastDropTarget)) then
- begin
- FLastDropTarget := nil;
- TDragObject(Source).HideDragImage;
- Node.DropTarget := True;
- TDragObject(Source).ShowDragImage;
- end;
- end;
-
- procedure TCustomTreeView.GetImageIndex(Node: TTreeNode);
- begin
- if Assigned(FOnGetImageIndex) then FOnGetImageIndex(Self, Node);
- end;
-
- procedure TCustomTreeView.GetSelectedIndex(Node: TTreeNode);
- begin
- if Assigned(FOnGetSelectedIndex) then FOnGetSelectedIndex(Self, Node);
- end;
-
- function TCustomTreeView.CanChange(Node: TTreeNode): Boolean;
- begin
- Result := True;
- if Assigned(FOnChanging) then FOnChanging(Self, Node, Result);
- end;
-
- procedure TCustomTreeView.Change(Node: TTreeNode);
- begin
- if Assigned(FOnChange) then FOnChange(Self, Node);
- end;
-
- procedure TCustomTreeView.Expand(Node: TTreeNode);
- begin
- if Assigned(FOnExpanded) then FOnExpanded(Self, Node);
- end;
-
- function TCustomTreeView.CanExpand(Node: TTreeNode): Boolean;
- begin
- Result := True;
- if Assigned(FOnExpanding) then FOnExpanding(Self, Node, Result);
- end;
-
- procedure TCustomTreeView.Collapse(Node: TTreeNode);
- begin
- if Assigned(FOnCollapsed) then FOnCollapsed(Self, Node);
- end;
-
- function TCustomTreeView.CanCollapse(Node: TTreeNode): Boolean;
- begin
- Result := True;
- if Assigned(FOnCollapsing) then FOnCollapsing(Self, Node, Result);
- end;
-
- function TCustomTreeView.CanEdit(Node: TTreeNode): Boolean;
- begin
- Result := True;
- if Assigned(FOnEditing) then FOnEditing(Self, Node, Result);
- end;
-
- procedure TCustomTreeView.Edit(const Item: TTVItem);
- var
- S: string;
- Node: TTreeNode;
- begin
- with Item do
- if pszText <> nil then
- begin
- S := pszText;
- Node := GetNodeFromItem(Item);
- if Assigned(FOnEdited) then FOnEdited(Self, Node, S);
- if Node <> nil then Node.Text := S;
- end;
- end;
-
- function TCustomTreeView.CreateNode: TTreeNode;
- begin
- Result := TTreeNode.Create(Items);
- end;
-
- procedure TCustomTreeView.SetImageList(Value: HImageList; Flags: Integer);
- begin
- if HandleAllocated then TreeView_SetImageList(Handle, Value, Flags);
- end;
-
- procedure TCustomTreeView.ImageListChange(Sender: TObject);
- var
- ImageHandle: HImageList;
- begin
- if HandleAllocated then
- begin
- ImageHandle := TImageList(Sender).Handle;
- if Sender = Images then
- SetImageList(ImageHandle, TVSIL_NORMAL)
- else if Sender = StateImages then
- SetImageList(ImageHandle, TVSIL_STATE);
- end;
- end;
-
- procedure TCustomTreeView.Notification(AComponent: TComponent;
- Operation: TOperation);
- begin
- inherited Notification(AComponent, Operation);
- if Operation = opRemove then
- begin
- if AComponent = Images then Images := nil;
- if AComponent = StateImages then StateImages := nil;
- end;
- end;
-
- procedure TCustomTreeView.SetImages(Value: TImageList);
- begin
- if Images <> nil then
- Images.UnRegisterChanges(FImageChangeLink);
- FImages := Value;
- if Images <> nil then
- begin
- Images.RegisterChanges(FImageChangeLink);
- SetImageList(Images.Handle, TVSIL_NORMAL)
- end
- else SetImageList(0, TVSIL_NORMAL);
- end;
-
- procedure TCustomTreeView.SetStateImages(Value: TImageList);
- begin
- if StateImages <> nil then
- StateImages.UnRegisterChanges(FStateChangeLink);
- FStateImages := Value;
- if StateImages <> nil then
- begin
- StateImages.RegisterChanges(FStateChangeLink);
- SetImageList(StateImages.Handle, TVSIL_STATE)
- end
- else SetImageList(0, TVSIL_STATE);
- end;
-
- procedure TCustomTreeView.LoadFromFile(const FileName: string);
- var
- Stream: TStream;
- begin
- Stream := TFileStream.Create(FileName, fmOpenRead);
- try
- LoadFromStream(Stream);
- finally
- Stream.Free;
- end;
- end;
-
- procedure TCustomTreeView.LoadFromStream(Stream: TStream);
- begin
- with TTreeStrings.Create(Items) do
- try
- LoadFromStream(Stream);
- finally
- Free;
- end;
- end;
-
- procedure TCustomTreeView.SaveToFile(const FileName: string);
- var
- Stream: TStream;
- begin
- Stream := TFileStream.Create(FileName, fmCreate);
- try
- SaveToStream(Stream);
- finally
- Stream.Free;
- end;
- end;
-
- procedure TCustomTreeView.SaveToStream(Stream: TStream);
- begin
- with TTreeStrings.Create(Items) do
- try
- SaveToStream(Stream);
- finally
- Free;
- end;
- end;
-
- procedure TCustomTreeView.WMRButtonDown(var Message: TWMRButtonDown);
- var
- MousePos: TPoint;
- begin
- FRClicked := False;
- inherited;
- if FRClicked then
- begin
- GetCursorPos(MousePos);
- with PointToSmallPoint(ScreenToClient(MousePos)) do
- Perform(WM_RBUTTONUP, 0, MakeLong(X, Y));
- end;
- end;
-
- procedure TCustomTreeView.WMLButtonDown(var Message: TWMLButtonDown);
- var
- Node: TTreeNode;
- MousePos: TPoint;
- begin
- FDragged := False;
- FDragNode := nil;
- try
- inherited;
- if DragMode = dmAutomatic then
- begin
- SetFocus;
- if not FDragged then
- begin
- GetCursorPos(MousePos);
- with PointToSmallPoint(ScreenToClient(MousePos)) do
- Perform(WM_LBUTTONUP, 0, MakeLong(X, Y));
- end
- else begin
- Node := GetNodeAt(Message.XPos, Message.YPos);
- if Node <> nil then
- begin
- Node.Focused := True;
- Node.Selected := True;
- BeginDrag(False);
- end;
- end;
- end;
- finally
- FDragNode := nil;
- end;
- end;
-
- { TTrackBar }
- constructor TTrackBar.Create(AOwner: TComponent);
- begin
- inherited Create(AOwner);
- Width := 150;
- Height := 45;
- TabStop := True;
- FMin := 0;
- FMax := 10;
- FLineSize := 1;
- FPageSize := 2;
- FFrequency := 1;
-
- FTickMarks := tmBottomRight;
- FTickStyle := tsAuto;
- FOrientation := trHorizontal;
- ControlStyle := ControlStyle - [csDoubleClicks];
- end;
-
- procedure TTrackBar.CreateParams(var Params: TCreateParams);
- const
- OrientationStyle: array[TTrackbarOrientation] of Longint = (TBS_HORZ, TBS_VERT);
- TickStyles: array[TTickStyle] of Longint = (TBS_NOTICKS, TBS_AUTOTICKS, 0);
- ATickMarks: array[TTickMark] of Longint = (TBS_BOTTOM, TBS_TOP, TBS_BOTH);
- begin
- InitCommonControls;
- inherited CreateParams(Params);
- CreateSubClass(Params, TRACKBAR_CLASS);
- Params.Style := Params.Style or OrientationStyle[FOrientation] or
- TickStyles[FTickStyle] or ATickMarks[FTickMarks] or TBS_ENABLESELRANGE;
- Params.WindowClass.style := Params.WindowClass.style or CS_DBLCLKS;
- end;
-
- procedure TTrackBar.CreateWnd;
- begin
- inherited CreateWnd;
- if HandleAllocated then
- begin
- SendMessage(Handle, TBM_SETLINESIZE, 0, FLineSize);
- SendMessage(Handle, TBM_SETPAGESIZE, 0, FPageSize);
- SendMessage(Handle, TBM_SETRANGEMIN, 0, FMin);
- SendMessage(Handle, TBM_SETRANGEMAX, 0, FMax);
- UpdateSelection;
- SendMessage(Handle, TBM_SETPOS, 1, FPosition);
- SendMessage(Handle, TBM_SETTICFREQ, FFrequency, 1);
- end;
- end;
-
- procedure TTrackBar.DestroyWnd;
- begin
- inherited DestroyWnd;
- end;
-
- procedure TTrackBar.CNHScroll(var Message: TWMHScroll);
- begin
- inherited;
- FPosition := SendMessage(Handle, TBM_GETPOS, 0, 0);
-
- if Assigned(FOnChange) then
- FOnChange(Self);
- Message.Result := 0;
- end;
-
- procedure TTrackBar.CNVScroll(var Message: TWMVScroll);
- begin
- inherited;
- FPosition := SendMessage(Handle, TBM_GETPOS, 0, 0);
-
- if Assigned(FOnChange) then
- FOnChange(Self);
- Message.Result := 0;
- end;
-
- procedure TTrackBar.SetOrientation(Value: TTrackBarOrientation);
- begin
- if Value <> FOrientation then
- begin
- FOrientation := Value;
- if ComponentState * [csLoading, csUpdating] = [] then
- SetBounds(Left, Top, Height, Width);
- RecreateWnd;
- end;
- end;
-
- procedure TTrackBar.SetParams(APosition, AMin, AMax: Integer);
- begin
- if AMax < AMin then
- raise EInvalidOperation.CreateResFmt(SPropertyOutOfRange, [Self.Classname]);
- if APosition < AMin then APosition := AMin;
- if APosition > AMax then APosition := AMax;
- if (FMin <> AMin) then
- begin
- FMin := AMin;
- if HandleAllocated then
- SendMessage(Handle, TBM_SETRANGEMIN, 1, AMin);
- end;
- if (FMax <> AMax) then
- begin
- FMax := AMax;
- if HandleAllocated then
- SendMessage(Handle, TBM_SETRANGEMAX, 1, AMax);
- end;
- if FPosition <> APosition then
- begin
- FPosition := APosition;
- if HandleAllocated then
- SendMessage(Handle, TBM_SETPOS, 1, APosition);
- end;
- end;
-
- procedure TTrackBar.SetPosition(Value: Integer);
- begin
- SetParams(Value, FMin, FMax);
- end;
-
- procedure TTrackBar.SetMin(Value: Integer);
- begin
- SetParams(FPosition, Value, FMax);
- end;
-
- procedure TTrackBar.SetMax(Value: Integer);
- begin
- SetParams(FPosition, FMin, Value);
- end;
-
- procedure TTrackBar.SetFrequency(Value: Integer);
- begin
- if Value <> FFrequency then
- begin
- FFrequency := Value;
- if HandleAllocated then
- SendMessage(Handle, TBM_SETTICFREQ, FFrequency, 1);
- end;
- end;
-
- procedure TTrackBar.SetTick(Value: Integer);
- begin
- if HandleAllocated then
- SendMessage(Handle, TBM_SETTIC, 0, Value);
- end;
-
- procedure TTrackBar.SetTickStyle(Value: TTickStyle);
- begin
- if Value <> FTickStyle then
- begin
- FTickStyle := Value;
- RecreateWnd;
- end;
- end;
-
- procedure TTrackBar.SetTickMarks(Value: TTickMark);
- begin
- if Value <> FTickMarks then
- begin
- FTickMarks := Value;
- RecreateWnd;
- end;
- end;
-
- procedure TTrackBar.SetLineSize(Value: Integer);
- begin
- if Value <> FLineSize then
- begin
- FLineSize := Value;
- if HandleAllocated then
- SendMessage(Handle, TBM_SETLINESIZE, 0, FLineSize);
- end;
- end;
-
- procedure TTrackBar.SetPageSize(Value: Integer);
- begin
- if Value <> FPageSize then
- begin
- FPageSize := Value;
- if HandleAllocated then
- SendMessage(Handle, TBM_SETPAGESIZE, 0, FPageSize);
- end;
- end;
-
- procedure TTrackBar.UpdateSelection;
- begin
- if HandleAllocated then
- begin
- if (FSelStart = 0) and (FSelEnd = 0) then
- SendMessage(Handle, TBM_CLEARSEL, 1, 0)
- else
- SendMessage(Handle, TBM_SETSEL, Integer(True), MakeLong(FSelStart, FSelEnd));
- end;
- end;
-
- procedure TTrackBar.SetSelStart(Value: Integer);
- begin
- if Value <> FSelStart then
- begin
- FSelStart := Value;
- UpdateSelection;
- end;
- end;
-
- procedure TTrackBar.SetSelEnd(Value: Integer);
- begin
- if Value <> FSelEnd then
- begin
- FSelEnd := Value;
- UpdateSelection;
- end;
- end;
-
- { TProgressBar }
- constructor TProgressBar.Create(AOwner: TComponent);
- begin
- inherited Create(AOwner);
- Width := 150;
- Height := GetSystemMetrics(SM_CYVSCROLL);
- FMin := 0;
- FMax := 100;
- FStep := 10;
- end;
-
- procedure TProgressBar.CreateParams(var Params: TCreateParams);
- begin
- InitCommonControls;
- inherited CreateParams(Params);
- CreateSubClass(Params, PROGRESS_CLASS);
- end;
-
- procedure TProgressBar.CreateWnd;
- begin
- inherited CreateWnd;
- SendMessage(Handle, PBM_SETRANGE, 0, MakeLong(FMin, FMax));
- SendMessage(Handle, PBM_SETSTEP, FStep, 0);
- Position := FPosition;
- end;
-
- function TProgressBar.GetPosition: TProgressRange;
- begin
- if HandleAllocated then
- Result := SendMessage(Handle, PBM_DELTAPOS, 0, 0) else
- Result := FPosition;
- end;
-
- procedure TProgressBar.SetParams(AMin, AMax: TProgressRange);
- begin
- if AMax < AMin then
- raise EInvalidOperation.CreateResFmt(SPropertyOutOfRange, [Self.Classname]);
- if (FMin <> AMin) or (FMax <> AMax) then
- begin
- if HandleAllocated then
- begin
- SendMessage(Handle, PBM_SETRANGE, 0, MakeLong(AMin, AMax));
- if FMin > AMin then // since Windows sets Position when increase Min..
- SendMessage(Handle, PBM_SETPOS, AMin, 0); // set it back if decrease
- end;
- FMin := AMin;
- FMax := AMax;
- end;
- end;
-
- procedure TProgressBar.SetMin(Value: TProgressRange);
- begin
- SetParams(Value, FMax);
- end;
-
- procedure TProgressBar.SetMax(Value: TProgressRange);
- begin
- SetParams(FMin, Value);
- end;
-
- procedure TProgressBar.SetPosition(Value: TProgressRange);
- begin
- if HandleAllocated then
- SendMessage(Handle, PBM_SETPOS, Value, 0) else
- FPosition := Value;
- end;
-
- procedure TProgressBar.SetStep(Value: TProgressRange);
- begin
- if Value <> FStep then
- begin
- FStep := Value;
- if HandleAllocated then
- SendMessage(Handle, PBM_SETSTEP, FStep, 0);
- end;
- end;
-
- procedure TProgressBar.StepIt;
- begin
- if HandleAllocated then
- SendMessage(Handle, PBM_STEPIT, 0, 0);
- end;
-
- procedure TProgressBar.StepBy(Delta: TProgressRange);
- begin
- if HandleAllocated then
- SendMessage(Handle, PBM_DELTAPOS, Delta, 0);
- end;
-
- { TTextAttributes }
-
- constructor TTextAttributes.Create(AOwner: TCustomRichEdit;
- AttributeType: TAttributeType);
- begin
- inherited Create;
- RichEdit := AOwner;
- FType := AttributeType;
- end;
-
- procedure TTextAttributes.InitFormat(var Format: TCharFormat);
- begin
- FillChar(Format, SizeOf(TCharFormat), 0);
- Format.cbSize := SizeOf(TCharFormat);
- end;
-
- function TTextAttributes.GetConsistentAttributes: TConsistentAttributes;
- var
- Format: TCharFormat;
- begin
- Result := [];
- if RichEdit.HandleAllocated and (FType = atSelected) then
- begin
- InitFormat(Format);
- SendMessage(RichEdit.Handle, EM_GETCHARFORMAT,
- WPARAM(FType = atSelected), LPARAM(@Format));
- with Format do
- begin
- if (dwMask and CFM_BOLD) <> 0 then Include(Result, caBold);
- if (dwMask and CFM_COLOR) <> 0 then Include(Result, caColor);
- if (dwMask and CFM_FACE) <> 0 then Include(Result, caFace);
- if (dwMask and CFM_ITALIC) <> 0 then Include(Result, caItalic);
- if (dwMask and CFM_SIZE) <> 0 then Include(Result, caSize);
- if (dwMask and CFM_STRIKEOUT) <> 0 then Include(Result, caStrikeOut);
- if (dwMask and CFM_UNDERLINE) <> 0 then Include(Result, caUnderline);
- if (dwMask and CFM_PROTECTED) <> 0 then Include(Result, caProtected);
- end;
- end;
- end;
-
- procedure TTextAttributes.GetAttributes(var Format: TCharFormat);
- begin
- InitFormat(Format);
- if RichEdit.HandleAllocated then
- SendMessage(RichEdit.Handle, EM_GETCHARFORMAT,
- WPARAM(FType = atSelected), LPARAM(@Format));
- end;
-
- procedure TTextAttributes.SetAttributes(var Format: TCharFormat);
- var
- Flag: Longint;
- begin
- if FType = atSelected then Flag := SCF_SELECTION
- else Flag := 0;
- if RichEdit.HandleAllocated then
- SendMessage(RichEdit.Handle, EM_SETCHARFORMAT, Flag, LPARAM(@Format))
- end;
-
- function TTextAttributes.GetProtected: Boolean;
- var
- Format: TCharFormat;
- begin
- GetAttributes(Format);
- with Format do
- if (dwEffects and CFE_PROTECTED) <> 0 then
- Result := True else
- Result := False;
- end;
-
- procedure TTextAttributes.SetProtected(Value: Boolean);
- var
- Format: TCharFormat;
- begin
- InitFormat(Format);
- with Format do
- begin
- dwMask := CFM_PROTECTED;
- if Value then dwEffects := CFE_PROTECTED;
- end;
- SetAttributes(Format);
- end;
-
- function TTextAttributes.GetColor: TColor;
- var
- Format: TCharFormat;
- begin
- GetAttributes(Format);
- with Format do
- if (dwEffects and CFE_AUTOCOLOR) <> 0 then
- Result := clWindowText else
- Result := crTextColor;
- end;
-
- procedure TTextAttributes.SetColor(Value: TColor);
- var
- Format: TCharFormat;
- begin
- InitFormat(Format);
- with Format do
- begin
- dwMask := CFM_COLOR;
- if Value = clWindowText then
- dwEffects := CFE_AUTOCOLOR else
- crTextColor := ColorToRGB(Value);
- end;
- SetAttributes(Format);
- end;
-
- function TTextAttributes.GetName: TFontName;
- var
- Format: TCharFormat;
- begin
- GetAttributes(Format);
- Result := Format.szFaceName;
- end;
-
- procedure TTextAttributes.SetName(Value: TFontName);
- var
- Format: TCharFormat;
- begin
- InitFormat(Format);
- with Format do
- begin
- dwMask := CFM_FACE;
- StrPLCopy(szFaceName, Value, SizeOf(szFaceName));
- end;
- SetAttributes(Format);
- end;
-
- function TTextAttributes.GetStyle: TFontStyles;
- var
- Format: TCharFormat;
- begin
- Result := [];
- GetAttributes(Format);
- with Format do
- begin
- if (dwEffects and CFE_BOLD) <> 0 then Include(Result, fsBold);
- if (dwEffects and CFE_ITALIC) <> 0 then Include(Result, fsItalic);
- if (dwEffects and CFE_UNDERLINE) <> 0 then Include(Result, fsUnderline);
- if (dwEffects and CFE_STRIKEOUT) <> 0 then Include(Result, fsStrikeOut);
- end;
- end;
-
- procedure TTextAttributes.SetStyle(Value: TFontStyles);
- var
- Format: TCharFormat;
- begin
- InitFormat(Format);
- with Format do
- begin
- dwMask := CFM_BOLD or CFM_ITALIC or CFM_UNDERLINE or CFM_STRIKEOUT;
- if fsBold in Value then dwEffects := dwEffects or CFE_BOLD;
- if fsItalic in Value then dwEffects := dwEffects or CFE_ITALIC;
- if fsUnderline in Value then dwEffects := dwEffects or CFE_UNDERLINE;
- if fsStrikeOut in Value then dwEffects := dwEffects or CFE_STRIKEOUT;
- end;
- SetAttributes(Format);
- end;
-
- function TTextAttributes.GetSize: Integer;
- var
- Format: TCharFormat;
- begin
- GetAttributes(Format);
- Result := Format.yHeight div 20;
- end;
-
- procedure TTextAttributes.SetSize(Value: Integer);
- var
- Format: TCharFormat;
- begin
- InitFormat(Format);
- with Format do
- begin
- dwMask := CFM_SIZE;
- yHeight := Value * 20;
- end;
- SetAttributes(Format);
- end;
-
- function TTextAttributes.GetHeight: Integer;
- begin
- Result := MulDiv(Size, RichEdit.FScreenLogPixels, 72);
- end;
-
- procedure TTextAttributes.SetHeight(Value: Integer);
- begin
- Size := MulDiv(Value, 72, RichEdit.FScreenLogPixels);
- end;
-
- function TTextAttributes.GetPitch: TFontPitch;
- var
- Format: TCharFormat;
- begin
- GetAttributes(Format);
- case (Format.bPitchAndFamily and $03) of
- DEFAULT_PITCH: Result := fpDefault;
- VARIABLE_PITCH: Result := fpVariable;
- FIXED_PITCH: Result := fpFixed;
- else
- Result := fpDefault;
- end;
- end;
-
- procedure TTextAttributes.SetPitch(Value: TFontPitch);
- var
- Format: TCharFormat;
- begin
- InitFormat(Format);
- with Format do
- begin
- case Value of
- fpVariable: Format.bPitchAndFamily := VARIABLE_PITCH;
- fpFixed: Format.bPitchAndFamily := FIXED_PITCH;
- else
- Format.bPitchAndFamily := DEFAULT_PITCH;
- end;
- end;
- SetAttributes(Format);
- end;
-
- procedure TTextAttributes.Assign(Source: TPersistent);
- begin
- if Source is TFont then
- begin
- Color := TFont(Source).Color;
- Name := TFont(Source).Name;
- Style := TFont(Source).Style;
- Size := TFont(Source).Size;
- Pitch := TFont(Source).Pitch;
- end
- else if Source is TTextAttributes then
- begin
- Color := TTextAttributes(Source).Color;
- Name := TTextAttributes(Source).Name;
- Style := TTextAttributes(Source).Style;
- Pitch := TTextAttributes(Source).Pitch;
- end
- else inherited Assign(Source);
- end;
-
- procedure TTextAttributes.AssignTo(Dest: TPersistent);
- begin
- if Dest is TFont then
- begin
- TFont(Dest).Color := Color;
- TFont(Dest).Name := Name;
- TFont(Dest).Style := Style;
- TFont(Dest).Size := Size;
- TFont(Dest).Pitch := Pitch;
- end
- else if Dest is TTextAttributes then
- begin
- TTextAttributes(Dest).Color := Color;
- TTextAttributes(Dest).Name := Name;
- TTextAttributes(Dest).Style := Style;
- TTextAttributes(Dest).Pitch := Pitch;
- end
- else inherited AssignTo(Dest);
- end;
-
- { TParaAttributes }
-
- constructor TParaAttributes.Create(AOwner: TCustomRichEdit);
- begin
- inherited Create;
- RichEdit := AOwner;
- end;
-
- procedure TParaAttributes.InitPara(var Paragraph: TParaFormat);
- begin
- FillChar(Paragraph, SizeOf(TParaFormat), 0);
- Paragraph.cbSize := SizeOf(TParaFormat);
- end;
-
- procedure TParaAttributes.GetAttributes(var Paragraph: TParaFormat);
- begin
- InitPara(Paragraph);
- if RichEdit.HandleAllocated then
- SendMessage(RichEdit.Handle, EM_GETPARAFORMAT, 0, LPARAM(@Paragraph));
- end;
-
- procedure TParaAttributes.SetAttributes(var Paragraph: TParaFormat);
- begin
- if RichEdit.HandleAllocated then
- SendMessage(RichEdit.Handle, EM_SETPARAFORMAT, 0, LPARAM(@Paragraph))
- end;
-
- function TParaAttributes.GetAlignment: TAlignment;
- var
- Paragraph: TParaFormat;
- begin
- GetAttributes(Paragraph);
- Result := TAlignment(Paragraph.wAlignment - 1);
- end;
-
- procedure TParaAttributes.SetAlignment(Value: TAlignment);
- var
- Paragraph: TParaFormat;
- begin
- InitPara(Paragraph);
- with Paragraph do
- begin
- dwMask := PFM_ALIGNMENT;
- wAlignment := Ord(Value) + 1;
- end;
- SetAttributes(Paragraph);
- end;
-
- function TParaAttributes.GetNumbering: TNumberingStyle;
- var
- Paragraph: TParaFormat;
- begin
- GetAttributes(Paragraph);
- Result := TNumberingStyle(Paragraph.wNumbering);
- end;
-
- procedure TParaAttributes.SetNumbering(Value: TNumberingStyle);
- var
- Paragraph: TParaFormat;
- begin
- case Value of
- nsBullet: if LeftIndent < 10 then LeftIndent := 10;
- nsNone: LeftIndent := 0;
- end;
- InitPara(Paragraph);
- with Paragraph do
- begin
- dwMask := PFM_NUMBERING;
- wNumbering := Ord(Value);
- end;
- SetAttributes(Paragraph);
- end;
-
- function TParaAttributes.GetFirstIndent: Longint;
- var
- Paragraph: TParaFormat;
- begin
- GetAttributes(Paragraph);
- Result := Paragraph.dxStartIndent div 20
- end;
-
- procedure TParaAttributes.SetFirstIndent(Value: Longint);
- var
- Paragraph: TParaFormat;
- begin
- InitPara(Paragraph);
- with Paragraph do
- begin
- dwMask := PFM_STARTINDENT;
- dxStartIndent := Value * 20;
- end;
- SetAttributes(Paragraph);
- end;
-
- function TParaAttributes.GetLeftIndent: Longint;
- var
- Paragraph: TParaFormat;
- begin
- GetAttributes(Paragraph);
- Result := Paragraph.dxOffset div 20;
- end;
-
- procedure TParaAttributes.SetLeftIndent(Value: Longint);
- var
- Paragraph: TParaFormat;
- begin
- InitPara(Paragraph);
- with Paragraph do
- begin
- dwMask := PFM_OFFSET;
- dxOffset := Value * 20;
- end;
- SetAttributes(Paragraph);
- end;
-
- function TParaAttributes.GetRightIndent: Longint;
- var
- Paragraph: TParaFormat;
- begin
- GetAttributes(Paragraph);
- Result := Paragraph.dxRightIndent div 20;
- end;
-
- procedure TParaAttributes.SetRightIndent(Value: Longint);
- var
- Paragraph: TParaFormat;
- begin
- InitPara(Paragraph);
- with Paragraph do
- begin
- dwMask := PFM_RIGHTINDENT;
- dxRightIndent := Value * 20;
- end;
- SetAttributes(Paragraph);
- end;
-
- function TParaAttributes.GetTab(Index: Byte): Longint;
- var
- Paragraph: TParaFormat;
- begin
- GetAttributes(Paragraph);
- Result := Paragraph.rgxTabs[Index] div 20;
- end;
-
- procedure TParaAttributes.SetTab(Index: Byte; Value: Longint);
- var
- Paragraph: TParaFormat;
- begin
- GetAttributes(Paragraph);
- with Paragraph do
- begin
- rgxTabs[Index] := Value * 20;
- dwMask := PFM_TABSTOPS;
- if cTabCount < Index then cTabCount := Index;
- SetAttributes(Paragraph);
- end;
- end;
-
- function TParaAttributes.GetTabCount: Integer;
- var
- Paragraph: TParaFormat;
- begin
- GetAttributes(Paragraph);
- Result := Paragraph.cTabCount;
- end;
-
- procedure TParaAttributes.SetTabCount(Value: Integer);
- var
- Paragraph: TParaFormat;
- begin
- GetAttributes(Paragraph);
- with Paragraph do
- begin
- dwMask := PFM_TABSTOPS;
- cTabCount := Value;
- SetAttributes(Paragraph);
- end;
- end;
-
- procedure TParaAttributes.Assign(Source: TPersistent);
- var
- I: Integer;
- begin
- if Source is TParaAttributes then
- begin
- Alignment := TParaAttributes(Source).Alignment;
- FirstIndent := TParaAttributes(Source).FirstIndent;
- LeftIndent := TParaAttributes(Source).LeftIndent;
- RightIndent := TParaAttributes(Source).RightIndent;
- Numbering := TParaAttributes(Source).Numbering;
- for I := 0 to MAX_TAB_STOPS - 1 do
- Tab[I] := TParaAttributes(Source).Tab[I];
- end
- else inherited Assign(Source);
- end;
-
- { TConversion }
-
- function TConversion.ConvertReadStream(Stream: TStream; Buffer: PChar; BufSize: Integer): Integer;
- begin
- Result := Stream.Read(Buffer^, BufSize);
- end;
-
- function TConversion.ConvertWriteStream(Stream: TStream; Buffer: PChar; BufSize: Integer): Integer;
- begin
- Result := Stream.Write(Buffer^, BufSize);
- end;
-
- { TRichEditStrings }
-
- const
- ReadError = $0001;
- WriteError = $0002;
- NoError = $0000;
-
- type
- TSelection = record
- StartPos, EndPos: Integer;
- end;
-
- TRichEditStrings = class(TStrings)
- private
- RichEdit: TCustomRichEdit;
- FPlainText: Boolean;
- FConverter: TConversion;
- protected
- function Get(Index: Integer): string; override;
- function GetCount: Integer; override;
- procedure Put(Index: Integer; const S: string); override;
- procedure SetUpdateState(Updating: Boolean); override;
- public
- procedure Clear; override;
- procedure AddStrings(Strings: TStrings); override;
- procedure Delete(Index: Integer); override;
- procedure Insert(Index: Integer; const S: string); override;
- procedure LoadFromFile(const FileName: string); override;
- procedure LoadFromStream(Stream: TStream); override;
- procedure SaveToFile(const FileName: string); override;
- procedure SaveToStream(Stream: TStream); override;
- property PlainText: Boolean read FPlainText write FPlainText;
- end;
-
- procedure TRichEditStrings.AddStrings(Strings: TStrings);
- var
- SelChange: TNotifyEvent;
- begin
- SelChange := RichEdit.OnSelectionChange;
- RichEdit.OnSelectionChange := nil;
- try
- inherited AddStrings(Strings);
- finally
- RichEdit.OnSelectionChange := SelChange;
- end;
- end;
-
- function TRichEditStrings.GetCount: Integer;
- begin
- Result := SendMessage(RichEdit.Handle, EM_GETLINECOUNT, 0, 0);
- if SendMessage(RichEdit.Handle, EM_LINELENGTH, SendMessage(RichEdit.Handle,
- EM_LINEINDEX, Result - 1, 0), 0) = 0 then Dec(Result);
- end;
-
- function TRichEditStrings.Get(Index: Integer): string;
- var
- Text: array[0..4095] of Char;
- L: Integer;
- begin
- Word((@Text)^) := SizeOf(Text);
- L := SendMessage(RichEdit.Handle, EM_GETLINE, Index, Longint(@Text));
- if (Text[L - 2] = #13) and (Text[L - 1] = #10) then Dec(L, 2);
- SetString(Result, Text, L);
- end;
-
- procedure TRichEditStrings.Put(Index: Integer; const S: string);
- var
- Selection: TSelection;
- begin
- if Index >= 0 then
- begin
- Selection.StartPos := SendMessage(RichEdit.Handle, EM_LINEINDEX, Index, 0);
- if Selection.StartPos <> -1 then
- begin
- Selection.EndPos := Selection.StartPos +
- SendMessage(RichEdit.Handle, EM_LINELENGTH, Selection.StartPos, 0);
- SendMessage(RichEdit.Handle, EM_SETSEL, Selection.StartPos, Selection.EndPos);
- SendMessage(RichEdit.Handle, EM_REPLACESEL, 0, Longint(PChar(S)));
- end;
- end;
- end;
-
- procedure TRichEditStrings.Insert(Index: Integer; const S: string);
- var
- L: Integer;
- Selection: TSelection;
- Fmt: PChar;
- Str: string;
- begin
- if Index >= 0 then
- begin
- Selection.StartPos := SendMessage(RichEdit.Handle, EM_LINEINDEX, Index, 0);
- if Selection.StartPos >= 0 then Fmt := '%s'#13#10
- else begin
- Selection.StartPos :=
- SendMessage(RichEdit.Handle, EM_LINEINDEX, Index - 1, 0);
- if Selection.StartPos < 0 then Exit;
- L := SendMessage(RichEdit.Handle, EM_LINELENGTH, Selection.StartPos, 0);
- if L = 0 then Exit;
- Inc(Selection.StartPos, L);
- Fmt := #13#10'%s';
- end;
- Selection.EndPos := Selection.StartPos;
- SendMessage(RichEdit.Handle, EM_SETSEL, Selection.StartPos, Selection.EndPos);
- Str := Format(Fmt, [S]);
- SendMessage(RichEdit.Handle, EM_REPLACESEL, 0, LongInt(PChar(Str)));
- if RichEdit.SelStart <> (Selection.EndPos + Length(Str)) then
- raise EOutOfResources.CreateRes(sRichEditInsertError);
- end;
- end;
-
- procedure TRichEditStrings.Delete(Index: Integer);
- const
- Empty: PChar = '';
- var
- Selection: TSelection;
- begin
- if Index < 0 then Exit;
- Selection.StartPos := SendMessage(RichEdit.Handle, EM_LINEINDEX, Index, 0);
- if Selection.StartPos <> -1 then
- begin
- Selection.EndPos := SendMessage(RichEdit.Handle, EM_LINEINDEX, Index + 1, 0);
- if Selection.EndPos = -1 then
- Selection.EndPos := Selection.StartPos +
- SendMessage(RichEdit.Handle, EM_LINELENGTH, Selection.StartPos, 0);
- SendMessage(RichEdit.Handle, EM_SETSEL, Selection.StartPos, Selection.EndPos);
- SendMessage(RichEdit.Handle, EM_REPLACESEL, 0, Longint(Empty));
- end;
- end;
-
- procedure TRichEditStrings.Clear;
- begin
- RichEdit.Clear;
- end;
-
- procedure TRichEditStrings.SetUpdateState(Updating: Boolean);
- begin
- SendMessage(RichEdit.Handle, WM_SETREDRAW, Ord(not Updating), 0);
- if not Updating then RichEdit.Refresh;
- end;
-
- function AdjustLineBreaks(Dest, Source: PChar): Integer; assembler;
- asm
- PUSH ESI
- PUSH EDI
- MOV EDI,EAX
- MOV ESI,EDX
- MOV EDX,EAX
- CLD
- @@1: LODSB
- @@2: OR AL,AL
- JE @@4
- CMP AL,0AH
- JE @@3
- STOSB
- CMP AL,0DH
- JNE @@1
- MOV AL,0AH
- STOSB
- LODSB
- CMP AL,0AH
- JE @@1
- JMP @@2
- @@3: MOV EAX,0A0DH
- STOSW
- JMP @@1
- @@4: STOSB
- LEA EAX,[EDI-1]
- SUB EAX,EDX
- POP EDI
- POP ESI
- end;
-
- function StreamSave(dwCookie: Longint; pbBuff: PByte;
- cb: Longint; var pcb: Longint): Longint; stdcall;
- var
- StreamInfo: PRichEditStreamInfo;
- begin
- Result := NoError;
- StreamInfo := PRichEditStreamInfo(Pointer(dwCookie));
- try
- pcb := 0;
- if StreamInfo^.Converter <> nil then
- pcb := StreamInfo^.Converter.ConvertWriteStream(StreamInfo^.Stream, PChar(pbBuff), cb);
- except
- Result := WriteError;
- end;
- end;
-
- function StreamLoad(dwCookie: Longint; pbBuff: PByte;
- cb: Longint; var pcb: Longint): Longint; stdcall;
- var
- Buffer, pBuff: PChar;
- StreamInfo: PRichEditStreamInfo;
- begin
- Result := NoError;
- StreamInfo := PRichEditStreamInfo(Pointer(dwCookie));
- Buffer := StrAlloc(cb + 1);
- try
- cb := cb div 2;
- pcb := 0;
- pBuff := Buffer + cb;
- try
- if StreamInfo^.Converter <> nil then
- pcb := StreamInfo^.Converter.ConvertReadStream(StreamInfo^.Stream, pBuff, cb);
- if pcb > 0 then
- begin
- pBuff[pcb] := #0;
- if pBuff[pcb - 1] = #13 then pBuff[pcb - 1] := #0;
- pcb := AdjustLineBreaks(Buffer, pBuff);
- Move(Buffer^, pbBuff^, pcb);
- end;
- except
- Result := ReadError;
- end;
- finally
- StrDispose(Buffer);
- end;
- end;
-
- procedure TRichEditStrings.LoadFromStream(Stream: TStream);
- var
- EditStream: TEditStream;
- Position: Longint;
- TextType: Longint;
- StreamInfo: TRichEditStreamInfo;
- Converter: TConversion;
- begin
- StreamInfo.Stream := Stream;
- if FConverter <> nil then
- Converter := FConverter else
- Converter := RichEdit.DefaultConverter.Create;
- StreamInfo.Converter := Converter;
- try
- with EditStream do
- begin
- dwCookie := LongInt(Pointer(@StreamInfo));
- pfnCallBack := @StreamLoad;
- dwError := 0;
- end;
- Position := Stream.Position;
- if PlainText then TextType := SF_TEXT
- else TextType := SF_RTF;
- SendMessage(RichEdit.Handle, EM_STREAMIN, TextType, Longint(@EditStream));
- if (TextType = SF_RTF) and (EditStream.dwError <> 0) then
- begin
- Stream.Position := Position;
- if PlainText then TextType := SF_RTF
- else TextType := SF_TEXT;
- SendMessage(RichEdit.Handle, EM_STREAMIN, TextType, Longint(@EditStream));
- if EditStream.dwError <> 0 then
- raise EOutOfResources.CreateRes(sRichEditLoadFail);
- end;
- finally
- if FConverter = nil then Converter.Free;
- end;
- end;
-
- procedure TRichEditStrings.SaveToStream(Stream: TStream);
- var
- EditStream: TEditStream;
- TextType: Longint;
- StreamInfo: TRichEditStreamInfo;
- Converter: TConversion;
- begin
- if FConverter <> nil then
- Converter := FConverter else
- Converter := RichEdit.DefaultConverter.Create;
- StreamInfo.Stream := Stream;
- StreamInfo.Converter := Converter;
- try
- with EditStream do
- begin
- dwCookie := LongInt(Pointer(@StreamInfo));
- pfnCallBack := @StreamSave;
- dwError := 0;
- end;
- if PlainText then TextType := SF_TEXT
- else TextType := SF_RTF;
- SendMessage(RichEdit.Handle, EM_STREAMOUT, TextType, Longint(@EditStream));
- if EditStream.dwError <> 0 then
- raise EOutOfResources.CreateRes(sRichEditSaveFail);
- finally
- if FConverter = nil then Converter.Free;
- end;
- end;
-
- procedure TRichEditStrings.LoadFromFile(const FileName: string);
- var
- Ext: string;
- Convert: PConversionFormat;
- begin
- Ext := LowerCase(Copy(ExtractFileExt(Filename), 2, Maxint));
- Convert := ConversionFormatList;
- while Convert <> nil do
- with Convert^ do
- if Extension <> Ext then Convert := Next
- else Break;
- if Convert = nil then
- Convert := @TextConversionFormat;
- FConverter := Convert^.ConversionClass.Create;
- try
- inherited LoadFromFile(FileName);
- except
- FConverter.Free;
- FConverter := nil;
- raise;
- end;
- end;
-
- procedure TRichEditStrings.SaveToFile(const FileName: string);
- var
- Ext: string;
- Convert: PConversionFormat;
- begin
- Ext := LowerCase(Copy(ExtractFileExt(Filename), 2, Maxint));
- Convert := ConversionFormatList;
- while Convert <> nil do
- with Convert^ do
- if Extension <> Ext then Convert := Next
- else Break;
- if Convert = nil then
- Convert := @TextConversionFormat;
- FConverter := Convert^.ConversionClass.Create;
- try
- inherited SaveToFile(FileName);
- except
- FConverter.Free;
- FConverter := nil;
- raise;
- end;
- end;
-
- { TRichEdit }
-
- constructor TCustomRichEdit.Create(AOwner: TComponent);
- var
- DC: HDC;
- begin
- inherited Create(AOwner);
- FSelAttributes := TTextAttributes.Create(Self, atSelected);
- FDefAttributes := TTextAttributes.Create(Self, atDefaultText);
- FParagraph := TParaAttributes.Create(Self);
- FRichEditStrings := TRichEditStrings.Create;
- TRichEditStrings(FRichEditStrings).RichEdit := Self;
- TabStop := True;
- Width := 185;
- Height := 89;
- AutoSize := False;
- FHideSelection := True;
- HideScrollBars := True;
- DC := GetDC(0);
- FScreenLogPixels := GetDeviceCaps(DC, LOGPIXELSY);
- DefaultConverter := TConversion;
- ReleaseDC(0, DC);
- end;
-
- destructor TCustomRichEdit.Destroy;
- begin
- FSelAttributes.Free;
- FDefAttributes.Free;
- FParagraph.Free;
- FRichEditStrings.Free;
- FMemStream.Free;
- inherited Destroy;
- end;
-
- procedure TCustomRichEdit.CreateParams(var Params: TCreateParams);
- const
- RichEditModuleName = 'RICHED32.DLL';
- HideScrollBars: array[Boolean] of Longint = (ES_DISABLENOSCROLL, 0);
- HideSelections: array[Boolean] of Longint = (ES_NOHIDESEL, 0);
- var
- OldError: Longint;
- begin
- OldError := SetErrorMode(SEM_NOOPENFILEERRORBOX);
- FLibHandle := LoadLibrary(RichEditModuleName);
- if FLibHandle < HINSTANCE_ERROR then FLibHandle := 0;
- SetErrorMode(OldError);
- inherited CreateParams(Params);
- CreateSubClass(Params, 'RICHEDIT');
- with Params do
- Style := Style or HideScrollBars[FHideScrollBars] or
- HideSelections[HideSelection];
- end;
-
- procedure TCustomRichEdit.CreateWnd;
- var
- Plain: Boolean;
- begin
- inherited CreateWnd;
- SendMessage(Handle, EM_SETEVENTMASK, 0,
- ENM_CHANGE or ENM_SELCHANGE or ENM_REQUESTRESIZE or
- ENM_PROTECTED);
- SendMessage(Handle, EM_SETBKGNDCOLOR, 0, ColorToRGB(Color));
- if FMemStream <> nil then
- begin
- Plain := PlainText;
- PlainText := False;
- try
- Lines.LoadFromStream(FMemStream);
- FMemStream.Free;
- FMemStream := nil;
- finally
- PlainText := Plain;
- end;
- end;
- Modified := FModified;
- end;
-
- procedure TCustomRichEdit.DestroyWnd;
- var
- Plain: Boolean;
- begin
- FModified := Modified;
- FMemStream := TMemoryStream.Create;
- Plain := PlainText;
- PlainText := False;
- try
- Lines.SaveToStream(FMemStream);
- FMemStream.Position := 0;
- finally
- PlainText := Plain;
- end;
- inherited DestroyWnd;
- end;
-
- procedure TCustomRichEdit.WMNCDestroy(var Message: TWMNCDestroy);
- begin
- inherited;
- if FLibHandle <> 0 then FreeLibrary(FLibHandle);
- end;
-
- procedure TCustomRichEdit.WMSetFont(var Message: TWMSetFont);
- begin
- FDefAttributes.Assign(Font);
- end;
-
- procedure TCustomRichEdit.CMFontChanged(var Message: TMessage);
- begin
- FDefAttributes.Assign(Font);
- end;
-
- procedure TCustomRichEdit.SetHideScrollBars(Value: Boolean);
- begin
- if HideScrollBars <> Value then
- begin
- FHideScrollBars := value;
- RecreateWnd;
- end;
- end;
-
- procedure TCustomRichEdit.SetHideSelection(Value: Boolean);
- begin
- if HideSelection <> Value then
- begin
- FHideSelection := Value;
- SendMessage(Handle, EM_HIDESELECTION, Ord(HideSelection), LongInt(True));
- end;
- end;
-
- procedure TCustomRichEdit.SetSelAttributes(Value: TTextAttributes);
- begin
- SelAttributes.Assign(Value);
- end;
-
- procedure TCustomRichEdit.SetDefAttributes(Value: TTextAttributes);
- begin
- DefAttributes.Assign(Value);
- end;
-
- function TCustomRichEdit.GetPlainText: Boolean;
- begin
- Result := TRichEditStrings(Lines).PlainText;
- end;
-
- procedure TCustomRichEdit.SetPlainText(Value: Boolean);
- begin
- TRichEditStrings(Lines).PlainText := Value;
- end;
-
- procedure TCustomRichEdit.CMColorChanged(var Message: TMessage);
- begin
- inherited;
- SendMessage(Handle, EM_SETBKGNDCOLOR, 0, ColorToRGB(Color))
- end;
-
- procedure TCustomRichEdit.SetRichEditStrings(Value: TStrings);
- begin
- FRichEditStrings.Assign(Value);
- end;
-
- procedure TCustomRichEdit.Print(const Caption: string);
- var
- Range: TFormatRange;
- LastChar, MaxLen, LogX, LogY: Integer;
- begin
- FillChar(Range, SizeOf(TFormatRange), 0);
- with Printer, Range do
- begin
- LogX := GetDeviceCaps(Handle, LOGPIXELSX);
- LogY := GetDeviceCaps(Handle, LOGPIXELSY);
- hdc := Handle;
- hdcTarget := hdc;
- if IsRectEmpty(PageRect) then
- begin
- rc.right := PageWidth * 1440 div LogX;
- rc.bottom := PageHeight * 1440 div LogY;
- end
- else begin
- rc.left := PageRect.Left * 1440 div LogX;
- rc.top := PageRect.Top * 1440 div LogY;
- rc.right := PageRect.Right * 1440 div LogX;
- rc.bottom := PageRect.Bottom * 1440 div LogY;
- end;
- rcPage := rc;
- Title := Caption;
- BeginDoc;
- LastChar := 0;
- MaxLen := GetTextLen;
- chrg.cpMax := -1;
- repeat
- chrg.cpMin := LastChar;
- LastChar := SendMessage(Self.Handle, EM_FORMATRANGE, 1, Longint(@Range));
- if (LastChar < MaxLen) and (LastChar <> -1) then NewPage;
- until (LastChar >= MaxLen) or (LastChar = -1);
- EndDoc;
- end;
- SendMessage(Handle, EM_FORMATRANGE, 0, 0);
- end;
-
- var
- Painting: Boolean = False;
-
- procedure TCustomRichEdit.WMPaint(var Message: TWMPaint);
- var
- R, R1: TRect;
- begin
- if GetUpdateRect(Handle, R, True) then
- begin
- with ClientRect do R1 := Rect(Right - 3, Top, Right, Bottom);
- if IntersectRect(R, R, R1) then InvalidateRect(Handle, @R1, True);
- end;
- if Painting then
- Invalidate
- else begin
- Painting := True;
- try
- inherited;
- finally
- Painting := False;
- end;
- end;
- end;
-
- procedure TCustomRichEdit.WMSetCursor(var Message: TWMSetCursor);
- var
- P: TPoint;
- begin
- inherited;
- if Message.Result = 0 then
- begin
- Message.Result := 1;
- GetCursorPos(P);
- with PointToSmallPoint(P) do
- case Perform(WM_NCHITTEST, 0, MakeLong(X, Y)) of
- HTVSCROLL,
- HTHSCROLL:
- Windows.SetCursor(Screen.Cursors[crArrow]);
- HTCLIENT:
- Windows.SetCursor(Screen.Cursors[crIBeam]);
- end;
- end;
- end;
-
- procedure TCustomRichEdit.CNNotify(var Message: TWMNotify);
- begin
- with Message.NMHdr^ do
- case code of
- EN_SELCHANGE: SelectionChange;
- EN_REQUESTRESIZE: RequestSize(PReqSize(Pointer(Message.NMHdr))^.rc);
- EN_SAVECLIPBOARD:
- with PENSaveClipboard(Pointer(Message.NMHdr))^ do
- if not SaveClipboard(cObjectCount, cch) then Message.Result := 1;
- EN_PROTECTED:
- with PENProtected(Pointer(Message.NMHdr))^.chrg do
- if not ProtectChange(cpMin, cpMax) then Message.Result := 1;
- end;
- end;
-
- function TCustomRichEdit.SaveClipboard(NumObj, NumChars: Integer): Boolean;
- begin
- Result := True;
- if Assigned(OnSaveClipboard) then OnSaveClipboard(Self, NumObj, NumChars, Result);
- end;
-
- function TCustomRichEdit.ProtectChange(StartPos, EndPos: Integer): Boolean;
- begin
- Result := False;
- if Assigned(OnProtectChange) then OnProtectChange(Self, StartPos, EndPos, Result);
- end;
-
- procedure TCustomRichEdit.SelectionChange;
- begin
- if Assigned(OnSelectionChange) then OnSelectionChange(Self);
- end;
-
- procedure TCustomRichEdit.RequestSize(const Rect: TRect);
- begin
- if Assigned(OnResizeRequest) then OnResizeRequest(Self, Rect);
- end;
-
- function TCustomRichEdit.FindText(const SearchStr: string;
- StartPos, Length: Integer; Options: TSearchTypes): Integer;
- var
- Find: TFindText;
- Flags: Integer;
- begin
- with Find.chrg do
- begin
- cpMin := StartPos;
- cpMax := cpMin + Length;
- end;
- Flags := 0;
- if stWholeWord in Options then Flags := Flags or FT_WHOLEWORD;
- if stMatchCase in Options then Flags := Flags or FT_MATCHCASE;
- Find.lpstrText := PChar(SearchStr);
- Result := SendMessage(Handle, EM_FINDTEXT, Flags, LongInt(@Find));
- end;
-
- procedure AppendConversionFormat(const Ext: string; AClass: TConversionClass);
- var
- NewRec: PConversionFormat;
- begin
- New(NewRec);
- with NewRec^ do
- begin
- Extension := LowerCase(Ext);
- ConversionClass := AClass;
- Next := ConversionFormatList;
- end;
- ConversionFormatList := NewRec;
- end;
-
- class procedure TCustomRichEdit.RegisterConversionFormat(const AExtension: string;
- AConversionClass: TConversionClass);
- begin
- AppendConversionFormat(AExtension, AConversionClass);
- end;
-
- { TUpDown }
-
- constructor TCustomUpDown.Create(AOwner: TComponent);
- begin
- inherited Create(AOwner);
- Width := GetSystemMetrics(SM_CXVSCROLL);
- Height := GetSystemMetrics(SM_CYVSCROLL);
- Height := Height + (Height div 2);
- FArrowKeys := True;
- FMax := 100;
- FIncrement := 1;
- FAlignButton := udRight;
- FOrientation := udVertical;
- FThousands := True;
- ControlStyle := ControlStyle - [csDoubleClicks];
- end;
-
- procedure TCustomUpDown.CreateParams(var Params: TCreateParams);
- begin
- InitCommonControls;
- inherited CreateParams(Params);
- with Params do
- begin
- Style := Style or UDS_SETBUDDYINT;
- if FAlignButton = udRight then Style := Style or UDS_ALIGNRIGHT
- else Style := Style or UDS_ALIGNLEFT;
- if FOrientation = udHorizontal then Style := Style or UDS_HORZ;
- if FArrowKeys then Style := Style or UDS_ARROWKEYS;
- if not FThousands then Style := Style or UDS_NOTHOUSANDS;
- if FWrap then Style := Style or UDS_WRAP;
- end;
- CreateSubClass(Params, UPDOWN_CLASS);
- Params.WindowClass.style := Params.WindowClass.style or CS_DBLCLKS;
- end;
-
- procedure TCustomUpDown.CreateWnd;
- var
- OrigWidth: Integer;
- AccelArray: array [0..0] of TUDAccel;
- begin
- OrigWidth := Width; { control resizes width - disallowing user to set width }
- inherited CreateWnd;
- Width := OrigWidth;
- SendMessage(Handle, UDM_SETRANGE, 0, MakeLong(FMax, FMin));
- SendMessage(Handle, UDM_SETPOS, 0, MakeLong(FPosition, 0));
- SendMessage(Handle, UDM_GETACCEL, 1, Longint(@AccelArray));
- AccelArray[0].nInc := FIncrement;
- SendMessage(Handle, UDM_SETACCEL, 1, Longint(@AccelArray));
-
- if FAssociate <> nil then
- begin
- UndoAutoResizing(FAssociate);
- SendMessage(Handle, UDM_SETBUDDY, FAssociate.Handle, 0);
- end;
- end;
-
- procedure TCustomUpDown.WMVScroll(var Message: TWMVScroll);
- begin
- inherited;
- if Message.ScrollCode = SB_THUMBPOSITION then
- begin
- if Message.Pos > FPosition then Click(btNext)
- else if Message.Pos < FPosition then Click(btPrev);
- FPosition := Message.Pos;
- end;
- end;
-
- procedure TCustomUpDown.WMHScroll(var Message: TWMHScroll);
- begin
- inherited;
- if Message.ScrollCode = SB_THUMBPOSITION then
- begin
- if Message.Pos > FPosition then Click(btNext)
- else if Message.Pos < FPosition then Click(btPrev);
- FPosition := Message.Pos;
- end;
- end;
-
- function TCustomUpDown.CanChange: Boolean;
- begin
- Result := True;
- if Assigned(FOnChanging) then
- FOnChanging(Self, Result);
- end;
-
- procedure TCustomUpDown.CNNotify(var Message: TWMNotify);
- begin
- with Message.NMHdr^ do
- begin
- case code of
- UDN_DELTAPOS: LongBool(Message.Result) := not CanChange;
- end;
- end;
- end;
-
- procedure TCustomUpDown.Click(Button: TUDBtnType);
- begin
- if Assigned(FOnClick) then FOnClick(Self, Button);
- end;
-
- procedure TCustomUpDown.SetAssociate(Value: TWinControl);
- var
- I: Integer;
-
- function IsClass(ClassType: TClass; const Name: string): Boolean;
- begin
- Result := True;
- while ClassType <> nil do
- begin
- if ClassType.ClassNameIs(Name) then Exit;
- ClassType := ClassType.ClassParent;
- end;
- Result := False;
- end;
-
- begin
- for I := 0 to Parent.ControlCount - 1 do
- if (Parent.Controls[I] is TCustomUpDown) and (Parent.Controls[I] <> Self) then
- if TCustomUpDown(Parent.Controls[I]).Associate = Value then
- raise Exception.CreateResFmt(sUDAssociated,
- [Value.Name, Parent.Controls[I].Name]);
-
- if FAssociate <> nil then { undo the current associate control }
- begin
- if HandleAllocated then
- SendMessage(Handle, UDM_SETBUDDY, 0, 0);
- FAssociate := nil;
- end;
-
- if (Value <> nil) and (Value.Parent = Self.Parent) and
- not (Value is TCustomUpDown) and
- not (Value is TCustomTreeView) and not (Value is TCustomListView) and
- not IsClass(Value.ClassType, 'TDBEdit') and
- not IsClass(Value.ClassType, 'TDBMemo') then
- begin
- if HandleAllocated then
- begin
- UndoAutoResizing(Value);
- SendMessage(Handle, UDM_SETBUDDY, Value.Handle, 0);
- end;
- FAssociate := Value;
- if Value is TCustomEdit then
- TCustomEdit(Value).Text := IntToStr(FPosition);
- end;
- end;
-
- procedure TCustomUpDown.UndoAutoResizing(Value: TWinControl);
- var
- OrigWidth, NewWidth, DeltaWidth: Integer;
- OrigLeft, NewLeft, DeltaLeft: Integer;
- begin
- { undo Window's auto-resizing }
- OrigWidth := Value.Width;
- OrigLeft := Value.Left;
- SendMessage(Handle, UDM_SETBUDDY, Value.Handle, 0);
- NewWidth := Value.Width;
- NewLeft := Value.Left;
- DeltaWidth := OrigWidth - NewWidth;
- DeltaLeft := NewLeft - OrigLeft;
- Value.Width := OrigWidth + DeltaWidth;
- Value.Left := OrigLeft - DeltaLeft;
- end;
-
- procedure TCustomUpDown.Notification(AComponent: TComponent;
- Operation: TOperation);
- begin
- inherited Notification(AComponent, Operation);
- if (Operation = opRemove) and (AComponent = FAssociate) then
- if HandleAllocated then
- begin
- SendMessage(Handle, UDM_SETBUDDY, 0, 0);
- FAssociate := nil;
- end;
- end;
-
- function TCustomUpDown.GetPosition: SmallInt;
- begin
- if HandleAllocated then
- begin
- Result := LoWord(SendMessage(Handle, UDM_GETPOS, 0, 0));
- FPosition := Result;
- end
- else Result := FPosition;
- end;
-
- procedure TCustomUpDown.SetMin(Value: SmallInt);
- begin
- if Value <> FMin then
- begin
- FMin := Value;
- if HandleAllocated then
- SendMessage(Handle, UDM_SETRANGE, 0, MakeLong(FMax, FMin));
- end;
- end;
-
- procedure TCustomUpDown.SetMax(Value: SmallInt);
- begin
- if Value <> FMax then
- begin
- FMax := Value;
- if HandleAllocated then
- SendMessage(Handle, UDM_SETRANGE, 0, MakeLong(FMax, FMin));
- end;
- end;
-
- procedure TCustomUpDown.SetIncrement(Value: Integer);
- var
- AccelArray: array [0..0] of TUDAccel;
- begin
- if Value <> FIncrement then
- begin
- FIncrement := Value;
- if HandleAllocated then
- begin
- SendMessage(Handle, UDM_GETACCEL, 1, Longint(@AccelArray));
- AccelArray[0].nInc := Value;
- SendMessage(Handle, UDM_SETACCEL, 1, Longint(@AccelArray));
- end;
- end;
- end;
-
- procedure TCustomUpDown.SetPosition(Value: SmallInt);
- begin
- if Value <> FPosition then
- begin
- FPosition := Value;
- if (csDesigning in ComponentState) and (FAssociate <> nil) then
- if FAssociate is TCustomEdit then
- TCustomEdit(FAssociate).Text := IntToStr(FPosition);
- if HandleAllocated then
- SendMessage(Handle, UDM_SETPOS, 0, MakeLong(FPosition, 0));
- end;
- end;
-
- procedure TCustomUpDown.SetOrientation(Value: TUDOrientation);
- begin
- if Value <> FOrientation then
- begin
- FOrientation := Value;
- if ComponentState * [csLoading, csUpdating] = [] then
- SetBounds(Left, Top, Height, Width);
- if HandleAllocated then
- SendMessage(Handle, UDM_SETBUDDY, 0, 0);
- RecreateWnd;
- end;
- end;
-
- procedure TCustomUpDown.SetAlignButton(Value: TUDAlignButton);
- begin
- if Value <> FAlignButton then
- begin
- FAlignButton := Value;
- if HandleAllocated then
- SendMessage(Handle, UDM_SETBUDDY, 0, 0);
- RecreateWnd;
- end;
- end;
-
- procedure TCustomUpDown.SetArrowKeys(Value: Boolean);
- begin
- if Value <> FArrowKeys then
- begin
- FArrowKeys := Value;
- if HandleAllocated then
- SendMessage(Handle, UDM_SETBUDDY, 0, 0);
- RecreateWnd;
- end;
- end;
-
- procedure TCustomUpDown.SetThousands(Value: Boolean);
- begin
- if Value <> FThousands then
- begin
- FThousands := Value;
- if HandleAllocated then
- SendMessage(Handle, UDM_SETBUDDY, 0, 0);
- RecreateWnd;
- end;
- end;
-
- procedure TCustomUpDown.SetWrap(Value: Boolean);
- begin
- if Value <> FWrap then
- begin
- FWrap := Value;
- if HandleAllocated then
- SendMessage(Handle, UDM_SETBUDDY, 0, 0);
- RecreateWnd;
- end;
- end;
-
- { THotKey }
-
- constructor TCustomHotKey.Create(AOwner: TComponent);
- begin
- inherited Create(AOwner);
- Width := 121;
- Height := 25;
- TabStop := True;
- ParentColor := False;
- FAutoSize := True;
- FInvalidKeys := [hcNone, hcShift];
- FModifiers := [hkAlt];
- FHotKey := $0041; // default - 'Alt+A'
- AdjustHeight;
- end;
-
- procedure TCustomHotKey.CreateParams(var Params: TCreateParams);
- begin
- InitCommonControls;
- inherited CreateParams(Params);
- CreateSubClass(Params, HOTKEYCLASS);
- end;
-
- procedure TCustomHotKey.CreateWnd;
- begin
- inherited CreateWnd;
- SendMessage(Handle, HKM_SETRULES, Byte(FInvalidKeys), MakeLong(Byte(FModifiers), 0));
- SendMessage(Handle, HKM_SETHOTKEY, MakeWord(Byte(FHotKey), Byte(FModifiers)), 0);
- end;
-
- procedure TCustomHotKey.SetAutoSize(Value: Boolean);
- begin
- if FAutoSize <> Value then
- begin
- FAutoSize := Value;
- UpdateHeight;
- end;
- end;
-
- procedure TCustomHotKey.SetModifiers(Value: THKModifiers);
- begin
- if Value <> FModifiers then
- begin
- FModifiers := Value;
- SendMessage(Handle, HKM_SETRULES, Byte(FInvalidKeys), MakeLong(Byte(Value), 0));
- SendMessage(Handle, HKM_SETHOTKEY, MakeWord(Byte(FHotKey), Byte(FModifiers)), 0);
- end;
- end;
-
- procedure TCustomHotKey.SetInvalidKeys(Value: THKInvalidKeys);
- begin
- if Value <> FInvalidKeys then
- begin
- FInvalidKeys := Value;
- SendMessage(Handle, HKM_SETRULES, Byte(Value), MakeLong(Byte(FModifiers), 0));
- SendMessage(Handle, HKM_SETHOTKEY, MakeWord(Byte(FHotKey), Byte(FModifiers)), 0);
- end;
- end;
-
- function TCustomHotKey.GetHotKey: TShortCut;
- var
- HK: Longint;
- begin
- HK := SendMessage(Handle, HKM_GETHOTKEY, 0, 0);
- Result := HotKeyToShortCut(HK);
- end;
-
- procedure TCustomHotKey.SetHotKey(Value: TShortCut);
- begin
- ShortCutToHotKey(Value);
- SendMessage(Handle, HKM_SETHOTKEY, MakeWord(Byte(FHotKey), Byte(FModifiers)), 0);
- end;
-
- procedure TCustomHotKey.UpdateHeight;
- begin
- if FAutoSize then
- begin
- ControlStyle := ControlStyle + [csFixedHeight];
- AdjustHeight;
- end else
- ControlStyle := ControlStyle - [csFixedHeight];
- end;
-
- procedure TCustomHotKey.AdjustHeight;
- var
- DC: HDC;
- SaveFont: HFont;
- I: Integer;
- SysMetrics, Metrics: TTextMetric;
- begin
- DC := GetDC(0);
- GetTextMetrics(DC, SysMetrics);
- SaveFont := SelectObject(DC, Font.Handle);
- GetTextMetrics(DC, Metrics);
- SelectObject(DC, SaveFont);
- ReleaseDC(0, DC);
- if NewStyleControls then
- begin
- if Ctl3D then I := 8 else I := 6;
- I := GetSystemMetrics(SM_CYBORDER) * I;
- end else
- begin
- I := SysMetrics.tmHeight;
- if I > Metrics.tmHeight then I := Metrics.tmHeight;
- I := I div 4 + GetSystemMetrics(SM_CYBORDER) * 4;
- end;
- Height := Metrics.tmHeight + I;
- end;
-
- procedure TCustomHotKey.ShortCutToHotKey(Value: TShortCut);
- begin
- FHotKey := Value and not (scShift + scCtrl + scAlt);
- FModifiers := [];
- if Value and scShift <> 0 then Include(FModifiers, hkShift);
- if Value and scCtrl <> 0 then Include(FModifiers, hkCtrl);
- if Value and scAlt <> 0 then Include(FModifiers, hkAlt);
- end;
-
- function TCustomHotKey.HotKeyToShortCut(Value: Longint): TShortCut;
- begin
- Byte(FModifiers) := LoWord(HiByte(Value));
- FHotKey := LoWord(LoByte(Value));
- Result := FHotKey;
- if hkShift in FModifiers then Inc(Result, scShift);
- if hkCtrl in FModifiers then Inc(Result, scCtrl);
- if hkAlt in FModifiers then Inc(Result, scAlt);
- end;
-
- { TListColumn }
-
- constructor TListColumn.Create(Collection: TCollection);
- var
- Column: TLVColumn;
- begin
- inherited Create(Collection);
- FWidth := 50;
- FAlignment := taLeftJustify;
- with Column do
- begin
- mask := LVCF_FMT or LVCF_WIDTH;
- fmt := LVCFMT_LEFT;
- cx := FWidth;
- end;
- ListView_InsertColumn(TListColumns(Collection).Owner.Handle, Index, Column);
- end;
-
- destructor TListColumn.Destroy;
- begin
- if TListColumns(Collection).Owner.HandleAllocated then
- ListView_DeleteColumn(TListColumns(Collection).Owner.Handle, Index);
- inherited Destroy;
- end;
-
- procedure TListColumn.DefineProperties(Filer: TFiler);
- begin
- inherited DefineProperties(Filer);
- Filer.DefineProperty('WidthType', ReadData, WriteData,
- WidthType <= ColumnTextWidth);
- end;
-
- procedure TListColumn.ReadData(Reader: TReader);
- begin
- with Reader do
- begin
- ReadListBegin;
- Width := TWidth(ReadInteger);
- ReadListEnd;
- end;
- end;
-
- procedure TListColumn.WriteData(Writer: TWriter);
- begin
- with Writer do
- begin
- WriteListBegin;
- WriteInteger(Ord(WidthType));
- WriteListEnd;
- end;
- end;
-
- procedure TListColumn.DoChange;
- var
- I: Integer;
- begin
- for I := 0 to Collection.Count - 1 do
- if TListColumn(Collection.Items[I]).WidthType <= ColumnTextWidth then Break;
- Changed(I <> Collection.Count);
- end;
-
- procedure TListColumn.SetCaption(const Value: string);
- begin
- if FCaption <> Value then
- begin
- FCaption := Value;
- DoChange;
- end;
- end;
-
- function TListColumn.GetWidth: TWidth;
- var
- Column: TLVColumn;
- ListView: TCustomListView;
- begin
- ListView := TListColumns(Collection).Owner;
- if ListView.HandleAllocated then
- begin
- Column.mask := LVCF_WIDTH;
- ListView_GetColumn(ListView.Handle, Index, Column);
- Result := Column.cx;
- if WidthType > ColumnTextWidth then FWidth := Result;
- end
- else Result := 0;
- end;
-
- procedure TListColumn.SetWidth(Value: TWidth);
- begin
- if Width <> Value then
- begin
- FWidth := Value;
- DoChange;
- end;
- end;
-
- procedure TListColumn.SetAlignment(Value: TAlignment);
- begin
- if (Alignment <> Value) and (Index <> 0) then
- begin
- FAlignment := Value;
- Changed(False);
- TListColumns(Collection).Owner.Repaint;
- end;
- end;
-
- procedure TListColumn.Assign(Source: TPersistent);
- var
- Column: TListColumn;
- begin
- if Source is TListColumn then
- begin
- Column := TListColumn(Source);
- Alignment := Column.Alignment;
- Width := Column.Width;
- Caption := Column.Caption;
- end
- else inherited Assign(Source);
- end;
-
- { TListColumns }
-
- constructor TListColumns.Create(AOwner: TCustomListView);
- begin
- inherited Create(TListColumn);
- FOwner := AOwner;
- end;
-
- function TListColumns.GetItem(Index: Integer): TListColumn;
- begin
- Result := TListColumn(inherited GetItem(Index));
- end;
-
- procedure TListColumns.SetItem(Index: Integer; Value: TListColumn);
- begin
- inherited SetItem(Index, Value);
- end;
-
- function TListColumns.Add: TListColumn;
- begin
- Result := TListColumn(inherited Add);
- end;
-
- procedure TListColumns.Update(Item: TCollectionItem);
- begin
- if Item <> nil then Owner.UpdateColumn(Item.Index)
- else Owner.UpdateColumns;
- end;
-
- { TSubItems }
-
- type
- TSubItems = class(TStringList)
- private
- FOwner: TListItem;
- procedure SetColumnWidth(Index: Integer);
- protected
- function GetHandle: HWND;
- procedure SetUpdateState(Updating: Boolean); override;
- public
- constructor Create(AOwner: TListItem);
- function Add(const S: string): Integer; override;
- procedure Insert(Index: Integer; const S: string); override;
- property Handle: HWND read GetHandle;
- property Owner: TListItem read FOwner;
- end;
-
- constructor TSubItems.Create(AOwner: TListItem);
- begin
- inherited Create;
- FOwner := AOwner;
- end;
-
- function TSubItems.GetHandle: HWND;
- begin
- Result := Owner.Owner.Handle;
- end;
-
- procedure TSubItems.SetColumnWidth(Index: Integer);
- var
- ListView: TCustomListView;
- begin
- ListView := Owner.ListView;
- if ListView.ColumnsShowing and
- (ListView.Columns.Count > Index) and
- (ListView.Column[Index].WidthType = ColumnTextWidth) then
- ListView.UpdateColumn(Index);
- end;
-
- function TSubItems.Add(const S: string): Integer;
- begin
- Result := inherited Add(S);
- ListView_SetItemText(Handle, Owner.Index, Count, LPSTR_TEXTCALLBACK);
- SetColumnWidth(Count);
- end;
-
- procedure TSubItems.Insert(Index: Integer; const S: string);
- begin
- inherited Insert(Index, S);
- ListView_SetItemText(Handle, Owner.Index, Index + 1, LPSTR_TEXTCALLBACK);
- SetColumnWidth(Index + 1);
- end;
-
- procedure TSubItems.SetUpdateState(Updating: Boolean);
- begin
- Owner.Owner.SetUpdateState(Updating);
- end;
-
- { TListItem }
-
- constructor TListItem.Create(AOwner: TListItems);
- begin
- FOwner := AOwner;
- FSubItems := TSubItems.Create(Self);
- FOverlayIndex := -1;
- FStateIndex := -1;
- end;
-
- destructor TListItem.Destroy;
- begin
- FDeleting := True;
- if ListView.HandleAllocated then ListView_DeleteItem(Handle, Index);
- FSubItems.Free;
- inherited Destroy;
- end;
-
- function TListItem.GetListView: TCustomListView;
- begin
- Result := Owner.Owner;
- end;
-
- procedure TListItem.Delete;
- begin
- if not FDeleting then Free;
- end;
-
- function TListItem.GetHandle: HWND;
- begin
- Result := ListView.Handle;
- end;
-
- procedure TListItem.MakeVisible(PartialOK: Boolean);
- begin
- ListView_EnsureVisible(Handle, Index, PartialOK);
- end;
-
- function TListItem.GetLeft: Integer;
- begin
- Result := GetPosition.X;
- end;
-
- procedure TListItem.SetLeft(Value: Integer);
- begin
- SetPosition(Point(Value, 0));
- end;
-
- function TListItem.GetTop: Integer;
- begin
- Result := GetPosition.Y;
- end;
-
- procedure TListItem.SetTop(Value: Integer);
- begin
- SetPosition(Point(0, Value));
- end;
-
- procedure TListItem.Update;
- begin
- ListView_Update(Handle, Index);
- end;
-
- procedure TListItem.SetCaption(const Value: string);
- begin
- FCaption := Value;
- ListView_SetItemText(Handle, Index, 0, LPSTR_TEXTCALLBACK);
- if ListView.ColumnsShowing and
- (ListView.Columns.Count > 0) and
- (ListView.Column[0].WidthType <= ColumnTextWidth) then
- ListView.UpdateColumns;
- if ListView.SortType in [stBoth, stText] then ListView.AlphaSort;
- end;
-
- procedure TListItem.SetData(Value: Pointer);
- begin
- FData := Value;
- if ListView.SortType in [stBoth, stData] then ListView.AlphaSort;
- end;
-
- function TListItem.EditCaption: Boolean;
- begin
- Result := ListView_EditLabel(Handle, Index) <> 0;
- end;
-
- procedure TListItem.CancelEdit;
- begin
- ListView_EditLabel(Handle, -1);
- end;
-
- function TListItem.GetState(Index: Integer): Boolean;
- var
- Mask: Integer;
- begin
- case Index of
- 0: Mask := LVIS_CUT;
- 1: Mask := LVIS_DROPHILITED;
- 2: Mask := LVIS_FOCUSED;
- 3: Mask := LVIS_SELECTED;
- end;
- Result := ListView_GetItemState(Handle, Self.Index, Mask) and Mask <> 0;
- end;
-
- procedure TListItem.SetState(Index: Integer; State: Boolean);
- var
- Mask: Integer;
- Data: Integer;
- begin
- case Index of
- 0: Mask := LVIS_CUT;
- 1: Mask := LVIS_DROPHILITED;
- 2: Mask := LVIS_FOCUSED;
- 3: Mask := LVIS_SELECTED;
- end;
- if State then Data := Mask
- else Data := 0;
- ListView_SetItemState(Handle, Self.Index, Data, Mask);
- end;
-
- procedure TListItem.SetImage(Index: Integer; Value: Integer);
- var
- Item: TLVItem;
- begin
- case Index of
- 0:
- begin
- FImageIndex := Value;
- with Item do
- begin
- mask := LVIF_IMAGE;
- iImage := I_IMAGECALLBACK;
- iItem := Self.Index;
- iSubItem := 0;
- end;
- ListView_SetItem(Handle, Item);
- end;
- 1:
- begin
- FOverlayIndex := Value;
- ListView_SetItemState(Handle, Self.Index,
- IndexToOverlayMask(OverlayIndex + 1), LVIS_OVERLAYMASK);
- end;
- 2:
- begin
- FStateIndex := Value;
- ListView_SetItemState(Handle, Self.Index,
- IndexToStateImageMask(StateIndex + 1), LVIS_STATEIMAGEMASK);
- end;
- end;
- ListView.UpdateItems(Self.Index, Self.Index);
- end;
-
- procedure TListItem.Assign(Source: TPersistent);
- begin
- if Source is TListItem then
- with Source as TListItem do
- begin
- Self.Caption := Caption;
- Self.Data := Data;
- Self.ImageIndex := ImageIndex;
- Self.OverlayIndex := OverlayIndex;
- Self.StateIndex := StateIndex;
- Self.SubItems := SubItems;
- end
- else inherited Assign(Source);
- end;
-
- function TListItem.IsEqual(Item: TListItem): Boolean;
- begin
- Result := (Caption = Item.Caption) and (Data = Item.Data);
- end;
-
- procedure TListItem.SetSubItems(Value: TStrings);
- begin
- if Value <> nil then FSubItems.Assign(Value);
- end;
-
- function TListItem.GetIndex: Integer;
- begin
- Result := Owner.IndexOf(Self);
- end;
-
- function TListItem.GetPosition: TPoint;
- begin
- ListView_GetItemPosition(Handle, Index, Result);
- end;
-
- procedure TListItem.SetPosition(const Value: TPoint);
- begin
- if ListView.ViewStyle in [vsSmallIcon, vsIcon] then
- ListView_SetItemPosition32(Handle, Index, Value.X, Value.Y);
- end;
-
- function TListItem.DisplayRect(Code: TDisplayCode): TRect;
- const
- Codes: array[TDisplayCode] of Longint = (LVIR_BOUNDS, LVIR_ICON, LVIR_LABEL,
- LVIR_SELECTBOUNDS);
- begin
- ListView_GetItemRect(Handle, Index, Result, Codes[Code]);
- end;
-
- { TListItems }
-
- type
- PItemHeader = ^TItemHeader;
- TItemHeader = packed record
- Size, Count: Integer;
- Items: record end;
- end;
- PItemInfo = ^TItemInfo;
- TItemInfo = packed record
- ImageIndex: Integer;
- StateIndex: Integer;
- OverlayIndex: Integer;
- SubItemCount: Integer;
- Data: Pointer;
- Caption: string[255];
- end;
- ShortStr = string[255];
- PShortStr = ^ShortStr;
-
- constructor TListItems.Create(AOwner: TCustomListView);
- begin
- inherited Create;
- FOwner := AOwner;
- end;
-
- destructor TListItems.Destroy;
- begin
- Clear;
- inherited Destroy;
- end;
-
- function TListItems.Add: TListItem;
- begin
- Result := Owner.CreateListItem;
- ListView_InsertItem(Handle, CreateItem(Count, Result));
- end;
-
- function TListItems.Insert(Index: Integer): TListItem;
- begin
- Result := Owner.CreateListItem;
- ListView_InsertItem(Handle, CreateItem(Index, Result));
- end;
-
- function TListItems.GetCount: Integer;
- begin
- if Owner.HandleAllocated then Result := ListView_GetItemCount(Handle)
- else Result := 0;
- end;
-
- function TListItems.GetHandle: HWND;
- begin
- Result := Owner.Handle;
- end;
-
- function TListItems.GetItem(Index: Integer): TListItem;
- var
- Item: TLVItem;
- begin
- Result := nil;
- if Owner.HandleAllocated then
- begin
- with Item do
- begin
- mask := LVIF_PARAM;
- iItem := Index;
- iSubItem := 0;
- end;
- if ListView_GetItem(Handle, Item) then Result := TListItem(Item.lParam);
- end;
- end;
-
- function TListItems.IndexOf(Value: TListItem): Integer;
- var
- Info: TLVFindInfo;
- begin
- with Info do
- begin
- flags := LVFI_PARAM;
- lParam := Integer(Value);
- end;
- Result := ListView_FindItem(Handle, -1, Info);
- end;
-
- procedure TListItems.SetItem(Index: Integer; Value: TListItem);
- begin
- Item[Index].Assign(Value);
- end;
-
- procedure TListItems.Clear;
- begin
- if Owner.HandleAllocated then ListView_DeleteAllItems(Handle);
- end;
-
- procedure TListItems.BeginUpdate;
- begin
- if FUpdateCount = 0 then SetUpdateState(True);
- Inc(FUpdateCount);
- end;
-
- procedure TListItems.SetUpdateState(Updating: Boolean);
- begin
- if Updating then
- begin
- SendMessage(Handle, WM_SETREDRAW, 0, 0);
- if Owner.ColumnsShowing and Owner.ValidHeaderHandle then
- SendMessage(Owner.FHeaderHandle, WM_SETREDRAW, 0, 0);
- end
- else if FUpdateCount = 0 then
- begin
- FNoRedraw := True;
- try
- SendMessage(Handle, WM_SETREDRAW, 1, 0);
- Owner.Invalidate;
- finally
- FNoRedraw := False;
- end;
- if Owner.ColumnsShowing and Owner.ValidHeaderHandle then
- SendMessage(Owner.FHeaderHandle, WM_SETREDRAW, 1, 0);
- end;
- end;
-
- procedure TListItems.EndUpdate;
- begin
- Dec(FUpdateCount);
- if FUpdateCount = 0 then SetUpdateState(False);
- end;
-
- procedure TListItems.Assign(Source: TPersistent);
- var
- Items: TListItems;
- I: Integer;
- begin
- if Source is TListItems then
- begin
- Clear;
- Items := TListItems(Source);
- for I := 0 to Items.Count - 1 do Add.Assign(Items[I]);
- end
- else inherited Assign(Source);
- end;
-
- procedure TListItems.DefineProperties(Filer: TFiler);
-
- function WriteItems: Boolean;
- var
- I: Integer;
- Items: TListItems;
- begin
- Items := TListItems(Filer.Ancestor);
- if (Items <> nil) and (Items.Count = Count) then
- for I := 0 to Count - 1 do
- begin
- Result := not Item[I].IsEqual(Items[I]);
- if Result then Break;
- end
- else Result := Count > 0;
- end;
-
- begin
- inherited DefineProperties(Filer);
- Filer.DefineBinaryProperty('Data', ReadData, WriteData, WriteItems);
- end;
-
- procedure TListItems.ReadData(Stream: TStream);
- var
- I, J, Size, L, Len: Integer;
- ItemHeader: PItemHeader;
- ItemInfo: PItemInfo;
- PStr: PShortStr;
- begin
- Clear;
- Stream.ReadBuffer(Size, SizeOf(Integer));
- ItemHeader := AllocMem(Size);
- try
- Stream.ReadBuffer(ItemHeader^.Count, Size - SizeOf(Integer));
- ItemInfo := @ItemHeader^.Items;
- for I := 0 to ItemHeader^.Count - 1 do
- begin
- with Add do
- begin
- Caption := ItemInfo^.Caption;
- ImageIndex := ItemInfo^.ImageIndex;
- OverlayIndex := ItemInfo^.OverlayIndex;
- StateIndex := ItemInfo^.StateIndex;
- Data := ItemInfo^.Data;
- PStr := @ItemInfo^.Caption;
- Inc(Integer(PStr), Length(PStr^) + 1);
- Len := 0;
- for J := 0 to ItemInfo^.SubItemCount - 1 do
- begin
- SubItems.Add(PStr^);
- L := Length(PStr^);
- Inc(Len, L + 1);
- Inc(Integer(PStr), L + 1);
- end;
- end;
- Inc(Integer(ItemInfo), SizeOf(TItemInfo) - 255 +
- Length(ItemInfo.Caption) + Len);
- end;
- finally
- FreeMem(ItemHeader, Size);
- end;
- end;
-
- procedure TListItems.WriteData(Stream: TStream);
- var
- I, J, Size, L, Len: Integer;
- ItemHeader: PItemHeader;
- ItemInfo: PItemInfo;
- PStr: PShortStr;
-
- function GetLength(const S: string): Integer;
- begin
- Result := Length(S);
- if Result > 255 then Result := 255;
- end;
-
- begin
- Size := SizeOf(TItemHeader);
- for I := 0 to Count - 1 do
- begin
- L := GetLength(Item[I].Caption);
- for J := 0 to Item[I].SubItems.Count - 1 do
- Inc(L, GetLength(Item[I].SubItems[J]) + 1);
- Inc(Size, SizeOf(TItemInfo) - 255 + L);
- end;
- ItemHeader := AllocMem(Size);
- try
- ItemHeader^.Size := Size;
- ItemHeader^.Count := Count;
- ItemInfo := @ItemHeader^.Items;
- for I := 0 to Count - 1 do
- begin
- with Item[I] do
- begin
- ItemInfo^.Caption := Caption;
- ItemInfo^.ImageIndex := ImageIndex;
- ItemInfo^.OverlayIndex := OverlayIndex;
- ItemInfo^.StateIndex := StateIndex;
- ItemInfo^.Data := Data;
- ItemInfo^.SubItemCount := SubItems.Count;
- PStr := @ItemInfo^.Caption;
- Inc(Integer(PStr), Length(ItemInfo^.Caption) + 1);
- Len := 0;
- for J := 0 to SubItems.Count - 1 do
- begin
- PStr^ := SubItems[J];
- L := Length(PStr^);
- Inc(Len, L + 1);
- Inc(Integer(PStr), L + 1);
- end;
- end;
- Inc(Integer(ItemInfo), SizeOf(TItemInfo) - 255 +
- Length(ItemInfo^.Caption) + Len);
- end;
- Stream.WriteBuffer(ItemHeader^, Size);
- finally
- FreeMem(ItemHeader, Size);
- end;
- end;
-
- procedure TListItems.Delete(Index: Integer);
- begin
- Item[Index].Delete;
- end;
-
- function TListItems.CreateItem(Index: Integer;
- ListItem: TListItem): TLVItem;
- begin
- with Result do
- begin
- mask := LVIF_PARAM or LVIF_IMAGE;
- iItem := Index;
- iSubItem := 0;
- iImage := I_IMAGECALLBACK;
- lParam := Longint(ListItem);
- end;
- end;
-
- { TIconOptions }
-
- constructor TIconOptions.Create(AOwner: TCustomListView);
- begin
- inherited Create;
- if AOwner = nil then raise Exception.CreateRes(sInvalidOwner);
- FListView := AOwner;
- Arrangement := iaTop;
- AutoArrange := False;
- WrapText := True;
- end;
-
- procedure TIconOptions.SetArrangement(Value: TIconArrangement);
- begin
- if Value <> Arrangement then
- begin;
- FArrangement := Value;
- FListView.RecreateWnd;
- {FListView.SetIconArrangement(Value);}
- end;
- end;
-
- procedure TIconOptions.SetAutoArrange(Value: Boolean);
- begin
- if Value <> AutoArrange then
- begin
- FAutoArrange := Value;
- FListView.RecreateWnd;
- end;
- end;
-
- procedure TIconOptions.SetWrapText(Value: Boolean);
- begin
- if Value <> WrapText then
- begin
- FWrapText := Value;
- FListView.RecreateWnd;
- end;
- end;
-
- { TCustomListView }
-
- function DefaultListViewSort(Item1, Item2: TListItem;
- lParam: Integer): Integer; stdcall;
- begin
- with Item1 do
- if Assigned(ListView.OnCompare) then
- ListView.OnCompare(ListView, Item1, Item2, lParam, Result)
- else Result := lstrcmp(PChar(Item1.Caption), PChar(Item2.Caption));
- end;
-
- constructor TCustomListView.Create(AOwner: TComponent);
- begin
- inherited Create(AOwner);
- ControlStyle := ControlStyle - [csCaptureMouse] + [csDisplayDragImage];
- Width := 250;
- Height := 150;
- BorderStyle := bsSingle;
- ViewStyle := vsIcon;
- ParentColor := False;
- TabStop := True;
- HideSelection := True;
- ShowColumnHeaders := True;
- ColumnClick := True;
- FDragIndex := -1;
- FListColumns := TListColumns.Create(Self);
- FListItems := TListItems.Create(Self);
- FIconOptions := TIconOptions.Create(Self);
- FDragImage := TImageList.CreateSize(32, 32);
- FEditInstance := MakeObjectInstance(EditWndProc);
- FHeaderInstance := MakeObjectInstance(HeaderWndProc);
- FLargeChangeLink := TChangeLink.Create;
- FLargeChangeLink.OnChange := ImageListChange;
- FSmallChangeLink := TChangeLink.Create;
- FSmallChangeLink.OnChange := ImageListChange;
- FStateChangeLink := TChangeLink.Create;
- FStateChangeLink.OnChange := ImageListChange;
- end;
-
- destructor TCustomListView.Destroy;
- begin
- FDragImage.Free;
- FListColumns.Free;
- FListItems.Free;
- FIconOptions.Free;
- FMemStream.Free;
- FreeObjectInstance(FEditInstance);
- if FHeaderHandle <> 0 then
- SetWindowLong(FHeaderHandle, GWL_WNDPROC, LongInt(FDefHeaderProc));
- FreeObjectInstance(FHeaderInstance);
- FLargeChangeLink.Free;
- FSmallChangeLink.Free;
- FStateChangeLink.Free;
- inherited Destroy;
- end;
-
- procedure TCustomListView.CreateParams(var Params: TCreateParams);
- const
- BorderStyles: array[TBorderStyle] of Integer = (0, WS_BORDER);
- EditStyles: array[Boolean] of Integer = (LVS_EDITLABELS, 0);
- MultiSelections: array[Boolean] of Integer = (LVS_SINGLESEL, 0);
- HideSelections: array[Boolean] of Integer = (LVS_SHOWSELALWAYS, 0);
- Arrangements: array[TIconArrangement] of Integer = (LVS_ALIGNTOP,
- LVS_ALIGNLEFT);
- AutoArrange: array[Boolean] of Integer = (0, LVS_AUTOARRANGE);
- WrapText: array[Boolean] of Integer = (LVS_NOLABELWRAP, 0);
- ViewStyles: array[TViewStyle] of Integer = (LVS_ICON, LVS_SMALLICON,
- LVS_LIST, LVS_REPORT);
- ShowColumns: array[Boolean] of Integer = (LVS_NOCOLUMNHEADER, 0);
- ColumnClicks: array[Boolean] of Integer = (LVS_NOSORTHEADER, 0);
- begin
- InitCommonControls;
- inherited CreateParams(Params);
- CreateSubClass(Params, WC_LISTVIEW);
- with Params do
- begin
- Style := Style or WS_CLIPCHILDREN or ViewStyles[ViewStyle] or
- BorderStyles[BorderStyle] or Arrangements[IconOptions.Arrangement] or
- EditStyles[ReadOnly] or MultiSelections[MultiSelect] or
- HideSelections[HideSelection] or
- AutoArrange[IconOptions.AutoArrange] or
- WrapText[IconOptions.WrapText] or
- ShowColumns[ShowColumnHeaders] or
- ColumnClicks[ColumnClick] or
- LVS_SHAREIMAGELISTS;
- if Ctl3D and (FBorderStyle = bsSingle) then
- ExStyle := Params.ExStyle or WS_EX_CLIENTEDGE;
- end;
- end;
-
- procedure TCustomListView.CreateWnd;
- begin
- inherited CreateWnd;
- SetTextBKColor(Color);
- SetTextColor(Font.Color);
- SetAllocBy(AllocBy);
- if FMemStream <> nil then
- begin
- Items.BeginUpdate;
- try
- Columns.Clear;
- FMemStream.ReadComponentRes(Self);
- FMemStream.Destroy;
- FMemStream := nil;
- Font := Font;
- finally
- Items.EndUpdate;
- end;
- end;
- if (LargeImages <> nil) and LargeImages.HandleAllocated then
- SetImageList(LargeImages.Handle, LVSIL_NORMAL);
- if (SmallImages <> nil) and SmallImages.HandleAllocated then
- SetImageList(SmallImages.Handle, LVSIL_SMALL);
- if (StateImages <> nil) and StateImages.HandleAllocated then
- SetImageList(StateImages.Handle, TVSIL_STATE);
- end;
-
- procedure TCustomListView.DestroyWnd;
- begin
- FMemStream := TMemoryStream.Create;
- FMemStream.WriteComponentRes(ClassName, Self);
- FMemStream.Position := 0;
- inherited DestroyWnd;
- end;
-
- procedure TCustomListView.SetImageList(Value: HImageList; Flags: Integer);
- begin
- if HandleAllocated then ListView_SetImageList(Handle, Value, Flags);
- end;
-
- procedure TCustomListView.ImageListChange(Sender: TObject);
- var
- ImageHandle: HImageList;
- begin
- if HandleAllocated then
- begin
- ImageHandle := TImageList(Sender).Handle;
- if Sender = LargeImages then SetImageList(ImageHandle, LVSIL_NORMAL)
- else if Sender = SmallImages then SetImageList(ImageHandle, LVSIL_SMALL)
- else if Sender = StateImages then SetImageList(ImageHandle, LVSIL_STATE);
- end;
- end;
-
- procedure TCustomListView.Notification(AComponent: TComponent;
- Operation: TOperation);
- begin
- inherited Notification(AComponent, Operation);
- if Operation = opRemove then
- begin
- if AComponent = LargeImages then LargeImages := nil;
- if AComponent = SmallImages then SmallImages := nil;
- if AComponent = StateImages then StateImages := nil;
- end;
- end;
-
- procedure TCustomListView.HeaderWndProc(var Message: TMessage);
- begin
- try
- with Message do
- begin
- case Msg of
- WM_NCHITTEST:
- with TWMNCHitTest(Message) do
- if csDesigning in ComponentState then
- begin
- Result := Windows.HTTRANSPARENT;
- Exit;
- end;
- WM_NCDESTROY:
- begin
- Result := CallWindowProc(FDefHeaderProc, FHeaderHandle, Msg, WParam, LParam);
- FHeaderHandle := 0;
- FDefHeaderProc := nil;
- Exit;
- end;
- end;
- Result := CallWindowProc(FDefHeaderProc, FHeaderHandle, Msg, WParam, LParam);
- end;
- except
- Application.HandleException(Self);
- end;
- end;
-
- procedure TCustomListView.EditWndProc(var Message: TMessage);
- begin
- try
- with Message do
- begin
- case Msg of
- WM_KEYDOWN,
- WM_SYSKEYDOWN: if DoKeyDown(TWMKey(Message)) then Exit;
- WM_CHAR: if DoKeyPress(TWMKey(Message)) then Exit;
- WM_KEYUP,
- WM_SYSKEYUP: if DoKeyUp(TWMKey(Message)) then Exit;
- CN_KEYDOWN,
- CN_CHAR, CN_SYSKEYDOWN,
- CN_SYSCHAR:
- begin
- WndProc(Message);
- Exit;
- end;
- end;
- Result := CallWindowProc(FDefEditProc, FEditHandle, Msg, WParam, LParam);
- end;
- except
- Application.HandleException(Self);
- end;
- end;
-
- procedure TCustomListView.UpdateItems(FirstIndex, LastIndex: Integer);
- begin
- ListView_RedrawItems(Handle, FirstIndex, LastIndex);
- end;
-
- procedure TCustomListView.SetBorderStyle(Value: TBorderStyle);
- begin
- if BorderStyle <> Value then
- begin
- FBorderStyle := Value;
- RecreateWnd;
- end;
- end;
-
- procedure TCustomListView.SetColumnClick(Value: Boolean);
- begin
- if ColumnClick <> Value then
- begin
- FColumnClick := Value;
- RecreateWnd;
- end;
- end;
-
- procedure TCustomListView.SetMultiSelect(Value: Boolean);
- begin
- if Value <> MultiSelect then
- begin
- FMultiSelect := Value;
- RecreateWnd;
- end;
- end;
-
- procedure TCustomListView.SetColumnHeaders(Value: Boolean);
- begin
- if Value <> ShowColumnHeaders then
- begin
- FShowColumnHeaders := Value;
- RecreateWnd;
- end;
- end;
-
- procedure TCustomListView.SetTextColor(Value: TColor);
- begin
- ListView_SetTextColor(Handle, ColorToRGB(Font.Color));
- end;
-
- procedure TCustomListView.SetTextBkColor(Value: TColor);
- begin
- ListView_SetTextBkColor(Handle, ColorToRGB(Color));
- end;
-
- procedure TCustomListView.SetAllocBy(Value: Integer);
- begin
- if AllocBy <> Value then
- begin
- FAllocBy := Value;
- if HandleAllocated then ListView_SetItemCount(Handle, Value);
- end;
- end;
-
- procedure TCustomListView.CMColorChanged(var Message: TMessage);
- begin
- inherited;
- SetTextBkColor(Color);
- end;
-
- procedure TCustomListView.CMCtl3DChanged(var Message: TMessage);
- begin
- if FBorderStyle = bsSingle then RecreateWnd;
- inherited;
- end;
-
- procedure TCustomListView.WMNotify(var Message: TWMNotify);
- begin
- inherited;
- if ValidHeaderHandle then
- with Message.NMHdr^ do
- if (hWndFrom = FHeaderHandle) and (code = HDN_BEGINTRACK) then
- with PHDNotify(Pointer(Message.NMHdr))^, PItem^ do
- if (Mask and HDI_WIDTH) <> 0 then
- Column[Item].Width := cxy;
- end;
-
- function TCustomListView.ColumnsShowing: Boolean;
- begin
- Result := (ViewStyle = vsReport);
- end;
-
- function TCustomListView.ValidHeaderHandle: Boolean;
- begin
- Result := FHeaderHandle <> 0;
- end;
-
- procedure TCustomListView.CMFontChanged(var Message: TMessage);
- begin
- inherited;
- if HandleAllocated then
- begin
- SetTextColor(Font.Color);
- if ValidHeaderHandle then
- InvalidateRect(FHeaderHandle, nil, True);
- end;
- end;
-
- procedure TCustomListView.SetHideSelection(Value: Boolean);
- begin
- if Value <> HideSelection then
- begin
- FHideSelection := Value;
- RecreateWnd;
- end;
- end;
-
- procedure TCustomListView.SetReadOnly(Value: Boolean);
- begin
- if Value <> ReadOnly then
- begin
- FReadOnly := Value;
- RecreateWnd;
- end;
- end;
-
- procedure TCustomListView.SetIconOptions(Value: TIconOptions);
- begin
- with FIconOptions do
- begin
- Arrangement := Value.Arrangement;
- AutoArrange := Value.AutoArrange;
- WrapText := Value.WrapText;
- end;
- end;
-
- procedure TCustomListView.SetIconArrangement(Value: TIconArrangement);
- const
- Arrangements: array[TIconArrangement] of Integer = (LVS_ALIGNTOP,
- LVS_ALIGNLEFT);
- var
- Style: Longint;
- begin
- if HandleAllocated then
- begin
- Style := GetWindowLong(Handle, GWL_STYLE);
- Style := Style and (not LVS_ALIGNMASK);
- Style := Style or Arrangements[Value];
- SetWindowLong(Handle, GWL_STYLE, Style);
- end;
- end;
-
- procedure TCustomListView.SetViewStyle(Value: TViewStyle);
- const
- ViewStyles: array[TViewStyle] of Integer = (LVS_ICON, LVS_SMALLICON,
- LVS_LIST, LVS_REPORT);
- var
- Style: Longint;
- begin
- if Value <> FViewStyle then
- begin
- FViewStyle := Value;
- if HandleAllocated then
- begin
- Style := GetWindowLong(Handle, GWL_STYLE);
- Style := Style and (not LVS_TYPEMASK);
- Style := Style or ViewStyles[FViewStyle];
- SetWindowLong(Handle, GWL_STYLE, Style);
- UpdateColumns;
- case ViewStyle of
- vsIcon,
- vsSmallIcon:
- if IconOptions.Arrangement = iaTop then
- Arrange(arAlignTop) else
- Arrange(arAlignLeft);
- end;
- end;
- end;
- end;
-
- procedure TCustomListView.WMParentNotify(var Message: TWMParentNotify);
- begin
- with Message do
- if (Event = WM_CREATE) and (FHeaderHandle = 0) then
- begin
- FHeaderHandle := ChildWnd;
- FDefHeaderProc := Pointer(GetWindowLong(FHeaderHandle, GWL_WNDPROC));
- SetWindowLong(FHeaderHandle, GWL_WNDPROC, LongInt(FHeaderInstance));
- end;
- inherited;
- end;
-
- function TCustomListView.GetItemIndex(Value: TListItem): Integer;
- var
- I: Integer;
- begin
- Result := -1;
- for I := 0 to Items.Count - 1 do if Items[I] = Value then Break;
- if I < Items.Count then Result := I;
- end;
-
- function TCustomListView.CreateListItem: TListItem;
- begin
- Result := TListItem.Create(Items);
- end;
-
- function TCustomListView.GetItem(Value: TLVItem): TListItem;
- begin
- with Value do
- if (mask and LVIF_PARAM) <> 0 then Result := TListItem(lParam)
- else Result := Items[IItem];
- end;
-
- function TCustomListView.GetSelCount: Integer;
- begin
- Result := ListView_GetSelectedCount(Handle);
- end;
-
- procedure TCustomListView.CNNotify(var Message: TWMNotify);
- var
- Item: TListItem;
- I: Integer;
- begin
- with Message.NMHdr^ do
- case code of
- LVN_BEGINDRAG:
- with PNMListView(Pointer(Message.NMHdr))^ do
- FDragIndex := iItem;
- LVN_DELETEITEM:
- with PNMListView(Pointer(Message.NMHdr))^ do
- Delete(TListItem(lParam));
- LVN_DELETEALLITEMS:
- for I := Items.Count - 1 downto 0 do Delete(Items[I]);
- LVN_GETDISPINFO:
- begin
- Item := GetItem(PLVDispInfo(Pointer(Message.NMHdr))^.item);
- with PLVDispInfo(Pointer(Message.NMHdr))^.item do
- begin
- if (mask and LVIF_TEXT) <> 0 then
- if iSubItem = 0 then
- StrPLCopy(pszText, Item.Caption, cchTextMax)
- else
- with Item.SubItems do
- if iSubItem <= Count then
- StrPLCopy(pszText, Strings[iSubItem - 1], cchTextMax)
- else pszText[0] := #0;
- if (mask and LVIF_IMAGE) <> 0 then iImage := Item.ImageIndex;
- end;
- end;
- LVN_BEGINLABELEDIT:
- begin
- Item := GetItem(PLVDispInfo(Pointer(Message.NMHdr))^.item);
- if not CanEdit(Item) then Message.Result := 1;
- if Message.Result = 0 then
- begin
- FEditHandle := ListView_GetEditControl(Handle);
- FDefEditProc := Pointer(GetWindowLong(FEditHandle, GWL_WNDPROC));
- SetWindowLong(FEditHandle, GWL_WNDPROC, LongInt(FEditInstance));
- end;
- end;
- LVN_ENDLABELEDIT:
- with PLVDispInfo(Pointer(Message.NMHdr))^ do
- if (item.pszText <> nil) and (item.IItem <> -1) then
- Edit(item);
- LVN_COLUMNCLICK:
- with PNMListView(Pointer(Message.NMHdr))^ do
- ColClick(Column[iSubItem]);
- LVN_INSERTITEM:
- with PNMListView(Pointer(Message.NMHdr))^ do
- InsertItem(Items[iItem]);
- LVN_ITEMCHANGING:
- with PNMListView(Pointer(Message.NMHdr))^ do
- if not CanChange(Items[iItem], uChanged) then Message.Result := 1;
- LVN_ITEMCHANGED:
- with PNMListView(Pointer(Message.NMHdr))^ do
- Change(Items[iItem], uChanged);
- NM_CLICK: FClicked := True;
- NM_RCLICK: FRClicked := True;
- end;
- end;
-
- procedure TCustomListView.ColClick(Column: TListColumn);
- begin
- if Assigned(FOnColumnClick) then FOnColumnClick(Self, Column);
- end;
-
- procedure TCustomListView.InsertItem(Item: TListItem);
- begin
- if Assigned(FOnInsert) then FOnInsert(Self, Item);
- end;
-
- function TCustomListView.CanChange(Item: TListItem; Change: Integer): Boolean;
- var
- ItemChange: TItemChange;
- begin
- Result := True;
- case Change of
- LVIF_TEXT: ItemChange := ctText;
- LVIF_IMAGE: ItemChange := ctImage;
- LVIF_STATE: ItemChange := ctState;
- end;
- if Assigned(FOnChanging) then FOnChanging(Self, Item, ItemChange, Result);
- end;
-
- procedure TCustomListView.Change(Item: TListItem; Change: Integer);
- var
- ItemChange: TItemChange;
- begin
- case Change of
- LVIF_TEXT: ItemChange := ctText;
- LVIF_IMAGE: ItemChange := ctImage;
- LVIF_STATE: ItemChange := ctState;
- end;
- if Assigned(FOnChange) then FOnChange(Self, Item, ItemChange);
- end;
-
- procedure TCustomListView.Delete(Item: TListItem);
- begin
- if (Item <> nil) and not Item.FProcessedDeleting then
- begin
- if Assigned(FOnDeletion) then FOnDeletion(Self, Item);
- Item.FProcessedDeleting := True;
- Item.Delete;
- end;
- end;
-
- function TCustomListView.CanEdit(Item: TListItem): Boolean;
- begin
- Result := True;
- if Assigned(FOnEditing) then FOnEditing(Self, Item, Result);
- end;
-
- procedure TCustomListView.Edit(const Item: TLVItem);
- var
- S: string;
- EditItem: TListItem;
- begin
- with Item do
- begin
- S := pszText;
- EditItem := GetItem(Item);
- if Assigned(FOnEdited) then FOnEdited(Self, EditItem, S);
- if EditItem <> nil then EditItem.Caption := S;
- end;
- end;
-
- function TCustomListView.IsEditing: Boolean;
- begin
- Result := ListView_GetEditControl(Handle) <> 0;
- end;
-
- function TCustomListView.GetDragImages: TCustomImageList;
- begin
- if SelCount = 1 then
- Result := FDragImage else
- Result := nil;
- end;
-
- procedure TCustomListView.WndProc(var Message: TMessage);
- begin
- if not (csDesigning in ComponentState) and ((Message.Msg = WM_LBUTTONDOWN) or
- (Message.Msg = WM_LBUTTONDBLCLK)) and not Dragging and (DragMode = dmAutomatic) then
- begin
- if not IsControlMouseMsg(TWMMouse(Message)) then
- begin
- ControlState := ControlState + [csLButtonDown];
- Dispatch(Message);
- end;
- end
- else if not (((Message.Msg = WM_PAINT) or (Message.Msg = WM_ERASEBKGND)) and
- Items.FNoRedraw) then
- inherited WndProc(Message);
- end;
-
- procedure TCustomListView.DoStartDrag(var DragObject: TDragObject);
- var
- P, P1: TPoint;
- ImageHandle: HImageList;
- DragItem: TListItem;
- begin
- inherited DoStartDrag(DragObject);
- FLastDropTarget := nil;
- GetCursorPos(P);
- P := ScreenToClient(P);
- if FDragIndex <> -1 then
- DragItem := Items[FDragIndex]
- else DragItem := nil;
- FDragIndex := -1;
- if DragItem = nil then
- with P do DragItem := GetItemAt(X, Y);
- if DragItem <> nil then
- begin
- ImageHandle := ListView_CreateDragImage(Handle, DragItem.Index, P1);
- if ImageHandle <> 0 then
- with FDragImage do
- begin
- Handle := ImageHandle;
- with P, DragItem.DisplayRect(drBounds) do
- SetDragImage(0, X - Left , Y - Top);
- end;
- end;
- end;
-
- procedure TCustomListView.DoEndDrag(Target: TObject; X, Y: Integer);
- begin
- inherited DoEndDrag(Target, X, Y);
- FLastDropTarget := nil;
- end;
-
- procedure TCustomListView.CMDrag(var Message: TCMDrag);
- begin
- inherited;
- if Message.Result <> 0 then
- with Message, DragRec^ do
- case DragMessage of
- dmDragMove: with ScreenToClient(Pos) do DoDragOver(Source, X, Y);
- dmDragLeave:
- begin
- TDragObject(Source).HideDragImage;
- FLastDropTarget := DropTarget;
- DropTarget := nil;
- Update;
- TDragObject(Source).ShowDragImage;
- end;
- dmDragDrop: FLastDropTarget := nil;
- end;
- end;
-
- procedure TCustomListView.DoDragOver(Source: TDragObject; X, Y: Integer);
- var
- Item: TListItem;
- Target: TListItem;
- begin
- Item := GetItemAt(X, Y);
- if Item <> nil then
- begin
- Target := DropTarget;
- if (Item <> Target) or (Item = FLastDropTarget) then
- begin
- FLastDropTarget := nil;
- TDragObject(Source).HideDragImage;
- if Target <> nil then
- Target.DropTarget := False;
- Item.DropTarget := True;
- Update;
- TDragObject(Source).ShowDragImage;
- end;
- end;
- end;
-
- procedure TCustomListView.SetItems(Value: TListItems);
- begin
- FListItems.Assign(Value);
- end;
-
- procedure TCustomListView.SetListColumns(Value: TListColumns);
- begin
- FListColumns.Assign(Value);
- end;
-
- function TCustomListView.CustomSort(SortProc: TLVCompare; lParam: Longint): Boolean;
- begin
- Result := False;
- if HandleAllocated then
- begin
- if not Assigned(SortProc) then SortProc := @DefaultListViewSort;
- Result := ListView_SortItems(Handle, SortProc, lParam);
- end;
- end;
-
- function TCustomListView.AlphaSort: Boolean;
- begin
- if HandleAllocated then
- Result := ListView_SortItems(Handle, @DefaultListViewSort, 0)
- else Result := False;
- end;
-
- procedure TCustomListView.SetSortType(Value: TSortType);
- begin
- if SortType <> Value then
- begin
- FSortType := Value;
- if ((SortType in [stData, stBoth]) and Assigned(OnCompare)) or
- (SortType in [stText, stBoth]) then
- AlphaSort;
- end;
- end;
-
- function TCustomListView.GetVisibleRowCount: Integer;
- begin
- if ViewStyle in [vsReport, vsList] then
- Result := ListView_GetCountPerPage(Handle)
- else Result := 0;
- end;
-
- function TCustomListView.GetViewOrigin: TPoint;
- begin
- ListView_GetOrigin(Handle, Result);
- end;
-
- function TCustomListView.GetTopItem: TListItem;
- var
- Index: Integer;
- begin
- Result := nil;
- if not (ViewStyle in [vsSmallIcon, vsIcon]) then
- begin
- Index := ListView_GetTopIndex(Handle);
- if Index <> -1 then Result := Items[Index];
- end;
- end;
-
- function TCustomListView.GetBoundingRect: TRect;
- begin
- ListView_GetViewRect(Handle, Result);
- end;
-
- procedure TCustomListView.Scroll(DX, DY: Integer);
- begin
- ListView_Scroll(Handle, DX, DY);
- end;
-
- procedure TCustomListView.SetLargeImages(Value: TImageList);
- begin
- if LargeImages <> nil then
- LargeImages.UnRegisterChanges(FLargeChangeLink);
- FLargeImages := Value;
- if LargeImages <> nil then
- begin
- LargeImages.RegisterChanges(FLargeChangeLink);
- SetImageList(LargeImages.Handle, LVSIL_NORMAL)
- end
- else SetImageList(0, LVSIL_NORMAL);
- end;
-
- procedure TCustomListView.SetSmallImages(Value: TImageList);
- begin
- if SmallImages <> nil then
- SmallImages.UnRegisterChanges(FSmallChangeLink);
- FSmallImages := Value;
- if SmallImages <> nil then
- begin
- SmallImages.RegisterChanges(FSmallChangeLink);
- SetImageList(SmallImages.Handle, LVSIL_SMALL)
- end
- else SetImageList(0, LVSIL_SMALL);
- end;
-
- procedure TCustomListView.SetStateImages(Value: TImageList);
- begin
- if StateImages <> nil then
- StateImages.UnRegisterChanges(FStateChangeLink);
- FStateImages := Value;
- if StateImages <> nil then
- begin
- StateImages.RegisterChanges(FStateChangeLink);
- SetImageList(StateImages.Handle, LVSIL_STATE)
- end
- else SetImageList(0, LVSIL_STATE);
- end;
-
- function TCustomListView.GetColumnFromIndex(Index: Integer): TListColumn;
- begin
- Result := FListColumns[Index];
- end;
-
- function TCustomListView.FindCaption(StartIndex: Integer; Value: string;
- Partial, Inclusive, Wrap: Boolean): TListItem;
- const
- FullString: array[Boolean] of Integer = (0, LVFI_PARTIAL);
- Wraps: array[Boolean] of Integer = (0, LVFI_WRAP);
- var
- Info: TLVFindInfo;
- Index: Integer;
- begin
- with Info do
- begin
- flags := LVFI_STRING or FullString[Partial] or Wraps[Wrap];
- psz := PChar(Value);
- end;
- if Inclusive then Dec(StartIndex);
- Index := ListView_FindItem(Handle, StartIndex, Info);
- if Index <> -1 then Result := Items[Index]
- else Result := nil;
- end;
-
- function TCustomListView.FindData(StartIndex: Integer; Value: Pointer;
- Inclusive, Wrap: Boolean): TListItem;
- var
- I: Integer;
- begin
- Result := nil;
- if Inclusive then Dec(StartIndex);
- for I := StartIndex + 1 to Items.Count - 1 do
- if Items[I].Data = Value then Break;
- if I <= Items.Count - 1 then Result := Items[I]
- else if Wrap then
- begin
- if Inclusive then Inc(StartIndex);
- for I := 0 to StartIndex - 1 do
- if Items[I].Data = Value then Break;
- if I <= StartIndex then Result := Items[I];
- end;
- end;
-
- function TCustomListView.GetSelection: TListItem;
- begin
- Result := GetNextItem(nil, sdAll, [isSelected]);
- end;
-
- procedure TCustomListView.SetSelection(Value: TListItem);
- var
- I: Integer;
- begin
- if Value <> nil then Value.Selected := True
- else begin
- Value := Selected;
- for I := 0 to SelCount - 1 do
- if Value <> nil then
- begin
- Value.Selected := False;
- Value := GetNextItem(Value, sdAll, [isSelected]);
- end;
- end;
- end;
-
- function TCustomListView.GetDropTarget: TListItem;
- begin
- Result := GetNextItem(nil, sdAll, [isDropHilited]);
- if Result = nil then Result := FLastDropTarget;
- end;
-
- procedure TCustomListView.SetDropTarget(Value: TListItem);
- begin
- if HandleAllocated then
- if Value <> nil then Value.DropTarget := True
- else begin
- Value := DropTarget;
- if Value <> nil then Value.DropTarget := False;
- end;
- end;
-
- function TCustomListView.GetFocused: TListItem;
- begin
- Result := GetNextItem(nil, sdAll, [isFocused]);
- end;
-
- procedure TCustomListView.SetFocused(Value: TListItem);
- begin
- if HandleAllocated then
- if Value <> nil then Value.Focused := True
- else begin
- Value := ItemFocused;
- if Value <> nil then Value.Focused := False;
- end;
- end;
-
- function TCustomListView.GetNextItem(StartItem: TListItem;
- Direction: TSearchDirection; States: TItemStates): TListItem;
- var
- Flags, Index: Integer;
- begin
- Result := nil;
- if HandleAllocated then
- begin
- Flags := 0;
- case Direction of
- sdAbove: Flags := LVNI_ABOVE;
- sdBelow: Flags := LVNI_BELOW;
- sdLeft: Flags := LVNI_TOLEFT;
- sdRight: Flags := LVNI_TORIGHT;
- sdAll: Flags := LVNI_ALL;
- end;
- if StartItem <> nil then Index := StartItem.Index
- else Index := -1;
- if isCut in States then Flags := Flags or LVNI_CUT;
- if isDropHilited in States then Flags := Flags or LVNI_DROPHILITED;
- if isFocused in States then Flags := Flags or LVNI_FOCUSED;
- if isSelected in States then Flags := Flags or LVNI_SELECTED;
- Index := ListView_GetNextItem(Handle, Index, Flags);
- if Index <> -1 then Result := Items[Index];
- end;
- end;
-
- function TCustomListView.GetNearestItem(Point: TPoint;
- Direction: TSearchDirection): TListItem;
- const
- Directions: array[TSearchDirection] of Integer = (VK_LEFT, VK_RIGHT,
- VK_UP, VK_DOWN, 0);
- var
- Info: TLVFindInfo;
- Index: Integer;
- begin
- with Info do
- begin
- flags := LVFI_NEARESTXY;
- pt := Point;
- vkDirection := Directions[Direction];
- end;
- Index := ListView_FindItem(Handle, -1, Info);
- if Index <> -1 then Result := Items[Index]
- else Result := nil;
- end;
-
- function TCustomListView.GetItemAt(X, Y: Integer): TListItem;
- var
- Info: TLVHitTestInfo;
- var
- Index: Integer;
- begin
- Result := nil;
- if HandleAllocated then
- begin
- Info.pt := Point(X, Y);
- Index := ListView_HitTest(Handle, Info);
- if Index <> -1 then Result := Items[Index];
- end;
- end;
-
- procedure TCustomListView.Arrange(Code: TListArrangement);
- const
- Codes: array[TListArrangement] of Longint = (LVA_ALIGNBOTTOM, LVA_ALIGNLEFT,
- LVA_ALIGNRIGHT, LVA_ALIGNTOP, LVA_DEFAULT, LVA_SNAPTOGRID);
- begin
- ListView_Arrange(Handle, Codes[Code]);
- end;
-
- function TCustomListView.StringWidth(S: string): Integer;
- begin
- Result := ListView_GetStringWidth(Handle, PChar(S));
- end;
-
- procedure TCustomListView.UpdateColumns;
- var
- I: Integer;
- begin
- if HandleAllocated then
- for I := 0 to Columns.Count - 1 do UpdateColumn(I);
- end;
-
- procedure TCustomListView.UpdateColumn(Index: Integer);
- var
- Column: TLVColumn;
- begin
- if HandleAllocated then
- with Column, Columns.Items[Index] do
- begin
- mask := LVCF_TEXT or LVCF_FMT;
- pszText := PChar(Caption);
- if Index <> 0 then
- case Alignment of
- taLeftJustify: fmt := LVCFMT_LEFT;
- taCenter: fmt := LVCFMT_CENTER;
- taRightJustify: fmt := LVCFMT_RIGHT;
- end
- else fmt := LVCFMT_LEFT;
- if WidthType > ColumnTextWidth then
- begin
- mask := mask or LVCF_WIDTH;
- cx := FWidth;
- ListView_SetColumn(Handle, Index, Column);
- end
- else begin
- ListView_SetColumn(Handle, Index, Column);
- if ViewStyle = vsList then
- ListView_SetColumnWidth(Handle, -1, WidthType)
- else if ViewStyle = vsReport then
- ListView_SetColumnWidth(Handle, Index, WidthType);
- end;
- end;
- end;
-
- procedure TCustomListView.WMRButtonDown(var Message: TWMRButtonDown);
- var
- MousePos: TPoint;
- begin
- FRClicked := False;
- inherited;
- if FRClicked then
- begin
- GetCursorPos(MousePos);
- with PointToSmallPoint(ScreenToClient(MousePos)) do
- Perform(WM_RBUTTONUP, 0, MakeLong(X, Y));
- end;
- end;
-
- procedure TCustomListView.WMLButtonDown(var Message: TWMLButtonDown);
- var
- Item: TListItem;
- MousePos: TPoint;
- ShiftState: TShiftState;
- begin
- SetFocus;
- ShiftState := KeysToShiftState(Message.Keys);
- FClicked := False;
- FDragIndex := -1;
- inherited;
- if (DragMode = dmAutomatic) and MultiSelect then
- begin
- if not (ssShift in ShiftState) and not (ssCtrl in ShiftState) then
- begin
- if not FClicked then
- begin
- Item := GetItemAt(Message.XPos, Message.YPos);
- if (Item <> nil) and Item.Selected then
- begin
- BeginDrag(False);
- Exit;
- end;
- end;
- end;
- end;
- if FClicked then
- begin
- GetCursorPos(MousePos);
- with PointToSmallPoint(ScreenToClient(MousePos)) do
- if not Dragging then Perform(WM_LBUTTONUP, 0, MakeLong(X, Y))
- else SendMessage(GetCapture, WM_LBUTTONUP, 0, MakeLong(X, Y));
- end
- else if (DragMode = dmAutomatic) and not (MultiSelect and
- ((ssShift in ShiftState) or (ssCtrl in ShiftState))) then
- begin
- Item := GetItemAt(Message.XPos, Message.YPos);
- if (Item <> nil) and Item.Selected then
- BeginDrag(False);
- end;
- end;
-
- function TCustomListView.GetSearchString: string;
- var
- Buffer: array[0..1023] of char;
- begin
- Result := '';
- if HandleAllocated and ListView_GetISearchString(Handle, Buffer) then
- Result := Buffer;
- end;
-
- end.
-