Componentes.Terceros.PNGCom.../internal/1.2.0/1/Source/PngButtonFunctions.pas

121 lines
3.9 KiB
ObjectPascal

unit PngButtonFunctions;
interface
uses
Windows, Buttons, Graphics, pngimage;
{$IF RTLVersion < 20.0 }
type
TPngImage = TPNGObject;
{$IFEND}
procedure CalcButtonLayout(Canvas: TCanvas; PngImage: TPngImage; const Client:
TRect; Pressed, Down: Boolean; const Caption: string; Layout: TButtonLayout;
Margin, Spacing: Integer; var GlyphPos, TextPos: TPoint; BiDiFlags: LongInt);
implementation
uses
Classes;
procedure CalcButtonLayout(Canvas: TCanvas; PngImage: TPngImage; const Client:
TRect; Pressed, Down: Boolean; const Caption: string; Layout: TButtonLayout;
Margin, Spacing: Integer; var GlyphPos, TextPos: TPoint; BiDiFlags: LongInt);
var
ClientSize, GlyphSize, TextSize, TotalSize: TPoint;
TextBounds: TRect;
begin
if (BiDiFlags and DT_RIGHT) = DT_RIGHT then begin
if Layout = blGlyphLeft then
Layout := blGlyphRight
else if Layout = blGlyphRight then
Layout := blGlyphLeft;
end;
//Calculate the item sizes
ClientSize := Point(Client.Right - Client.Left, Client.Bottom - Client.Top);
if PngImage <> nil then
GlyphSize := Point(PngImage.Width, PngImage.Height)
else
GlyphSize := Point(0, 0);
if Length(Caption) > 0 then begin
TextBounds := Rect(0, 0, Client.Right - Client.Left, 0);
DrawText(Canvas.Handle, PChar(Caption), Length(Caption), TextBounds,
DT_CALCRECT or BiDiFlags);
TextSize := Point(TextBounds.Right - TextBounds.Left, TextBounds.Bottom -
TextBounds.Top);
end
else begin
TextBounds := Rect(0, 0, 0, 0);
TextSize := Point(0, 0);
end;
//If the layout has the glyph on the right or the left, then both the
//text and the glyph are centered vertically. If the glyph is on the top
//or the bottom, then both the text and the glyph are centered horizontally.
if Layout in [blGlyphLeft, blGlyphRight] then
GlyphPos.Y := (ClientSize.Y - GlyphSize.Y + 1) div 2
else
GlyphPos.X := (ClientSize.X - GlyphSize.X + 1) div 2;
//If there is no text or no bitmap, then Spacing is irrelevant
if (TextSize.X = 0) or (GlyphSize.X = 0) then
Spacing := 0;
//Adjust Margin and Spacing
if Margin = -1 then begin
if Spacing = -1 then begin
TotalSize := Point(GlyphSize.X + TextSize.X, GlyphSize.Y + TextSize.Y);
if Layout in [blGlyphLeft, blGlyphRight] then
Margin := (ClientSize.X - TotalSize.X) div 3
else
Margin := (ClientSize.Y - TotalSize.Y) div 3;
end
else begin
TotalSize := Point(GlyphSize.X + Spacing + TextSize.X, GlyphSize.Y +
Spacing + TextSize.Y);
if Layout in [blGlyphLeft, blGlyphRight] then
Margin := (ClientSize.X - TotalSize.X) div 2
else
Margin := (ClientSize.Y - TotalSize.Y) div 2;
end
end
else if Spacing = -1 then begin
TotalSize := Point(ClientSize.X - (Margin + GlyphSize.X), ClientSize.Y -
(Margin + GlyphSize.Y));
end;
case Layout of
blGlyphLeft: GlyphPos.X := Margin;
blGlyphRight: GlyphPos.X := ClientSize.X - Margin - GlyphSize.X;
blGlyphTop: GlyphPos.Y := Margin;
blGlyphBottom: GlyphPos.Y := ClientSize.Y - Margin - GlyphSize.Y;
end;
if Layout in [blGlyphLeft, blGlyphRight] then
TextPos.Y := (ClientSize.Y - TextSize.Y) div 2
else
TextPos.X := (ClientSize.X - TextSize.X) div 2;
case Layout of
blGlyphLeft: TextPos.X := GlyphPos.X + GlyphSize.X + Spacing;
blGlyphRight: TextPos.X := GlyphPos.X - Spacing - TextSize.X;
blGlyphTop: TextPos.Y := GlyphPos.Y + GlyphSize.Y + Spacing;
blGlyphBottom: TextPos.Y := GlyphPos.Y - Spacing - TextSize.Y;
end;
//Fixup the result variables
with GlyphPos do begin
Inc(X, Client.Left + Integer(Pressed or Down));
Inc(Y, Client.Top + Integer(Pressed or Down));
end;
with TextPos do begin
Inc(X, Client.Left + Integer(Pressed or Down));
Inc(Y, Client.Top + Integer(Pressed or Down));
end;
end;
end.