?? tflatchecklistboxunit.pas
字號:
unit TFlatCheckListBoxUnit;
interface
{$I DFS.inc}
uses
Windows, Messages, SysUtils, Classes, Graphics, Controls, ExtCtrls, FlatUtilitys;
type
TFlatCheckListBox = class(TCustomControl)
private
FSelected: Integer;
FTransparent: TTransparentMode;
FOnClickCheck: TNotifyEvent;
cWheelMessage: Cardinal;
scrollType: TScrollType;
firstItem: Integer;
maxItems: Integer;
FSorted: Boolean;
FItems: TStringList;
FItemsRect: TList;
FItemsHeight: Integer;
FChecked: set of Byte;
FScrollBars: Boolean;
FUseAdvColors: Boolean;
FAdvColorBorder: TAdvColors;
FArrowColor: TColor;
FCheckColor: TColor;
FBorderColor: TColor;
FItemsRectColor: TColor;
FItemsSelectColor: TColor;
procedure SetColors (Index: Integer; Value: TColor);
procedure SetAdvColors (Index: Integer; Value: TAdvColors);
procedure SetUseAdvColors (Value: Boolean);
procedure SetSorted (Value: Boolean);
procedure SetItems (Value: TStringList);
procedure SetItemsRect;
procedure SetItemsHeight (Value: Integer);
function GetChecked (Index: Integer): Boolean;
procedure SetChecked (Index: Integer; Value: Boolean);
function GetSelCount: Integer;
procedure SetScrollBars (Value: Boolean);
function GetItemIndex: Integer;
procedure SetItemIndex (Value: Integer);
procedure WMSize (var Message: TWMSize); message WM_SIZE;
procedure WMMove (var Message: TWMMove); message WM_MOVE;
procedure CMEnabledChanged (var Message: TMessage); message CM_ENABLEDCHANGED;
procedure CMSysColorChange (var Message: TMessage); message CM_SYSCOLORCHANGE;
procedure CMParentColorChanged (var Message: TWMNoParams); message CM_PARENTCOLORCHANGED;
procedure ScrollTimerHandler (Sender: TObject);
procedure ItemsChanged (Sender: TObject);
procedure WMSetFocus (var Message: TWMSetFocus); message WM_SETFOCUS;
procedure WMKillFocus (var Message: TWMKillFocus); message WM_KILLFOCUS;
procedure CNKeyDown (var Message: TWMKeyDown); message CN_KEYDOWN;
procedure WMMouseWheel (var Message: TMessage); message WM_MOUSEWHEEL;
procedure SetTransparent (const Value: TTransparentMode);
protected
procedure CalcAdvColors;
procedure DrawCheckRect (canvas: TCanvas; start: TPoint; checked: Boolean);
procedure DrawScrollBar (canvas: TCanvas);
procedure Paint; override;
procedure Loaded; override;
procedure MouseDown (Button: TMouseButton; Shift: TShiftState; X, Y: Integer); override;
procedure MouseUp (Button: TMouseButton; Shift: TShiftState; X, Y: Integer); override;
procedure WndProc (var Message: TMessage); override;
{$IFDEF DFS_COMPILER_4_UP}
procedure SetBiDiMode(Value: TBiDiMode); override;
{$ENDIF}
public
constructor Create (AOwner: TComponent); override;
destructor Destroy; override;
property Checked [Index: Integer]: Boolean read GetChecked write SetChecked;
property SelCount: Integer read GetSelCount;
procedure Clear;
property ItemIndex: Integer read GetItemIndex write SetItemIndex;
published
property Items: TStringList read FItems write SetItems;
property ItemHeight: Integer read FItemsHeight write SetItemsHeight default 17;
property ScrollBars: Boolean read FScrollBars write SetScrollBars default false;
property Color default $00E1EAEB;
property ColorArrow: TColor index 0 read FArrowColor write SetColors default clBlack;
property ColorBorder: TColor index 1 read FBorderColor write SetColors default $008396A0;
property ColorItemsRect: TColor index 2 read FItemsRectColor write SetColors default clWhite;
property ColorCheck: TColor index 4 read FCheckColor write SetColors default clBlack;
property AdvColorBorder: TAdvColors index 0 read FAdvColorBorder write SetAdvColors default 40;
property UseAdvColors: Boolean read FUseAdvColors write SetUseAdvColors default false;
property Sorted: Boolean read FSorted write SetSorted default false;
property TransparentMode: TTransparentMode read FTransparent write SetTransparent default tmNone;
property Align;
property Font;
property ParentFont;
property ParentColor;
property ParentShowHint;
property Enabled;
property Visible;
property PopupMenu;
property ShowHint;
property OnClick;
property OnClickCheck: TNotifyEvent read FOnClickCheck write FOnClickCheck;
property OnMouseMove;
property OnMouseDown;
property OnMouseUp;
{$IFDEF DFS_COMPILER_4_UP}
property Anchors;
property BiDiMode write SetBidiMode;
property Constraints;
property DragKind;
property ParentBiDiMode;
property OnEndDock;
property OnStartDock;
{$ENDIF}
end;
implementation
var
ScrollTimer: TTimer = nil;
const
FTimerInterval = 600;
FScrollSpeed = 100;
constructor TFlatCheckListBox.Create (AOwner: TComponent);
begin
inherited;
if ScrollTimer = nil then
begin
ScrollTimer := TTimer.Create(nil);
ScrollTimer.Enabled := False;
ScrollTimer.Interval := FTimerInterval;
end;
ControlStyle := ControlStyle + [csOpaque];
SetBounds(Left, Top, 137, 99);
FItems := TStringList.Create;
FItemsRect := TList.Create;
FItemsHeight := 17;
TStringList(FItems).OnChange := ItemsChanged;
FScrollBars := false;
firstItem := 0;
FArrowColor := clBlack;
FBorderColor := $008396A0;
FItemsRectColor := clWhite;
FItemsSelectColor := $009CDEF7;
FCheckColor := clBlack;
ParentColor := True;
ParentFont := True;
Enabled := true;
Visible := true;
FUseAdvColors := false;
FAdvColorBorder := 40;
FSorted := false;
FTransparent := tmNone;
FSelected := -1;
cWheelMessage:= RegisterWindowMessage(MSH_MOUSEWHEEL);
end;
destructor TFlatCheckListBox.Destroy;
var
counter: Integer;
begin
ScrollTimer.Free;
ScrollTimer := nil;
FItems.Free;
for counter := 0 to FItemsRect.Count - 1 do
Dispose(FItemsRect.Items[counter]);
FItemsRect.Free;
inherited;
end;
procedure TFlatCheckListBox.WndProc (var Message: TMessage);
begin
if Message.Msg = cWheelMessage then
begin
SendMessage (Self.Handle, WM_MOUSEWHEEL, Message.wParam, Message.lParam);
end;
inherited;
end;
procedure TFlatCheckListBox.WMMouseWheel (var Message: TMessage);
var
fScrollLines: Integer;
begin
if not(csDesigning in ComponentState) then
begin
SystemParametersInfo(SPI_GETWHEELSCROLLLINES, 0, @fScrollLines, 0);
if (fScrollLines = 0) then
fScrollLines := maxItems;
if ShortInt(Message.WParamHi) = -WHEEL_DELTA then
if firstItem + maxItems + fScrollLines <= FItems.Count then
Inc(firstItem, fScrollLines)
else
if FItems.Count - maxItems < 0 then
firstItem := 0
else
firstItem := FItems.Count - maxItems
else
if ShortInt(Message.WParamHi) = WHEEL_DELTA then
if firstItem - fScrollLines < 0 then
firstItem := 0
else
dec(firstItem, fScrollLines);
Invalidate;
end;
end;
procedure TFlatCheckListBox.ItemsChanged (Sender: TObject);
begin
if Enabled then
begin
FChecked := FChecked - [0..High(Byte)];
Invalidate;
end;
end;
procedure TFlatCheckListBox.SetColors (Index: Integer; Value: TColor);
begin
case Index of
0: FArrowColor := Value;
1: FBorderColor := Value;
2: FItemsRectColor := Value;
3: FItemsSelectColor := Value;
4: FCheckColor := Value;
end;
Invalidate;
end;
procedure TFlatCheckListBox.CalcAdvColors;
begin
if FUseAdvColors then
begin
FBorderColor := CalcAdvancedColor(Color, FBorderColor, FAdvColorBorder, darken);
end;
end;
procedure TFlatCheckListBox.SetAdvColors (Index: Integer; Value: TAdvColors);
begin
case Index of
0: FAdvColorBorder := Value;
end;
CalcAdvColors;
Invalidate;
end;
procedure TFlatCheckListBox.SetUseAdvColors (Value: Boolean);
begin
if Value <> FUseAdvColors then
begin
FUseAdvColors := Value;
ParentColor := Value;
CalcAdvColors;
Invalidate;
end;
end;
procedure TFlatCheckListBox.SetSorted (Value: Boolean);
begin
if Value <> FSorted then
begin
FSorted := Value;
FItems.Sorted := Value;
FChecked := FChecked - [0..High(Byte)];
Invalidate;
end;
end;
procedure TFlatCheckListBox.SetItems (Value: TStringList);
var
counter: Integer;
begin
if Value.Count - 1 > High(Byte) then
Exit;
// delete all spaces at left and right
for counter := 0 to Value.Count - 1 do
Value[counter] := Trim(Value[counter]);
FItems.Assign(Value);
Invalidate;
end;
procedure TFlatCheckListBox.SetItemsRect;
var
counter: Integer;
ItemRect: ^TRect;
position: TPoint;
begin
// Delete all curent Rects
FItemsRect.Clear;
// calculate the maximum items to draw
if ScrollBars then
maxItems := (Height - 24) div (FItemsHeight + 2)
else
maxItems := (Height - 4) div (FItemsHeight + 2);
// set left/top position for the the first item
if ScrollBars then
position := Point(ClientRect.left + 3, ClientRect.top + 13)
else
position := Point(ClientRect.left + 3, ClientRect.top + 3);
for counter := 0 to maxItems - 1 do
begin
// create a new Item-Rect
New(ItemRect);
// calculate the Item-Rect
ItemRect^ := Rect(position.x, position.y, ClientRect.Right - 3, position.y + FItemsHeight);
// set left/top position for next Item-Rect
position := Point(position.x, position.y + FItemsHeight + 2);
// add the Item-Rect to the Items-Rect-List
FItemsRect.Add(ItemRect);
end;
Invalidate;
end;
procedure TFlatCheckListBox.SetItemsHeight (Value: Integer);
begin
if Value < 1 then
Value := 1;
FItemsHeight := Value;
if not (csLoading in ComponentState) then
if ScrollBars then
SetBounds(Left, Top, Width, maxItems * (FItemsHeight + 2) + 24)
else
SetBounds(Left, Top, Width, maxItems * (FItemsHeight + 2) + 4);
SetItemsRect;
end;
function TFlatCheckListBox.GetChecked (Index: Integer): Boolean;
begin
Result := Index in FChecked;
end;
procedure TFlatCheckListBox.SetChecked (Index: Integer; Value: Boolean);
begin
if Value then
Include(FChecked, Index)
else
Exclude(FChecked, Index);
Invalidate;
end;
{$IFDEF DFS_COMPILER_4_UP}
procedure TFlatCheckListBox.SetBiDiMode(Value: TBiDiMode);
begin
inherited;
Invalidate;
end;
{$ENDIF}
function TFlatCheckListBox.GetSelCount: Integer;
var
counter: Integer;
begin
Result := 0;
for counter := 0 to High(Byte) do
if counter in FChecked then
Inc(Result);
end;
procedure TFlatCheckListBox.SetScrollBars (Value: Boolean);
begin
if FScrollBars <> Value then
begin
FScrollBars := Value;
if not (csLoading in ComponentState) then
if Value then
Height := Height + 20
else
Height := Height - 20;
SetItemsRect;
end;
end;
procedure TFlatCheckListBox.DrawScrollBar (canvas: TCanvas);
var
x, y: Integer;
begin
// Draw the ScrollBar background
canvas.Brush.Color := Color;
canvas.FillRect(Rect(ClientRect.Left, ClientRect.Top, ClientRect.Right, ClientRect.Top + 11));
canvas.FillRect(Rect(ClientRect.Left, ClientRect.Bottom - 11, ClientRect.Right, ClientRect.Bottom));
// Draw the ScrollBar border
canvas.Brush.Color := FBorderColor;
canvas.FrameRect(Rect(ClientRect.Left, ClientRect.Top, ClientRect.Right, ClientRect.Top + 11));
canvas.FrameRect(Rect(ClientRect.Left, ClientRect.Bottom - 11, ClientRect.Right, ClientRect.Bottom));
// Draw the up arrow
x := (ClientRect.Right - ClientRect.Left) div 2 - 6;
y := ClientRect.Top + 4;
if (firstItem <> 0) and Enabled then
begin
canvas.Brush.Color := FArrowColor;
canvas.Pen.Color := FArrowColor;
canvas.Polygon([Point(x + 4, y + 2), Point(x + 8, y + 2), Point(x + 6, y)]);
end
else
begin
canvas.Brush.Color := clWhite;
canvas.Pen.Color := clWhite;
Inc(x); Inc(y);
canvas.Polygon([Point(x + 4, y + 2), Point(x + 8, y + 2), Point(x + 6, y)]);
Dec(x); Dec(y);
canvas.Brush.Color := clGray;
canvas.Pen.Color := clGray;
canvas.Polygon([Point(x + 4, y + 2), Point(x + 8, y + 2), Point(x + 6, y)]);
end;
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -