lazarus/components/customdrawn/customdrawnutils.pas
2010-12-31 13:41:58 +00:00

554 lines
19 KiB
ObjectPascal

{
Copyright (C) 2010 Felipe Monteiro de Carvalho
License: The same modifying LGPL with static linking exception as the LCL
Utility functions utilized by the custom drawn controls
}
unit customdrawnutils;
{$mode objfpc}{$H+}
interface
uses
Classes, SysUtils, LCLType, LCLIntf, LMessages, LCLProc, Controls, Graphics,
Forms, Types, IntfGraphics, FPImage, Math, FPImgCanv, FPCanvas;
function GetAColor(Color: TColor; Rate: byte): TColor;
function GetUColor(Color: TColor; Rate: byte): TColor;
procedure GradientFill(Clr1, Clr2: TColor; Canvas: TCanvas);
procedure GradientFillRect(Clr1, Clr2: TColor; Canvas: TFPCustomCanvas; lRect: TRect);
procedure GradFill(Canvas: TFPCustomCanvas; aRect: TRect; Clr1, Clr2: TColor);
procedure GradCenterFill(Canvas: TFPCustomCanvas; aRect: TRect;
Clr1, Clr2: TColor; rate: float);
procedure DrawAndroidButton(Canvas: TCanvas; Color: TColor);
procedure DrawXPTaskbarButton(Canvas: TCanvas; Color: TColor);
procedure FPImgCloneRect(IntfImg1, IntfImg2: TLazIntfImage; lRect: TRect; Fast: boolean);
function GetUniqueName(const Name: string; PControl: TComponent): string;
procedure DrawTabHead(aDest: TFPCustomCanvas; aRect: TRect; HeadColor: TColor;
IsActive: boolean);
procedure DrawTabHeadMask(aDest: TFPCustomCanvas; aRect: TRect;
HeadColor: TColor; IsActive: boolean);
procedure DrawArrow(aDest: TFPCustomCanvas; aRect: TRect; R: boolean);
type
PRGBTripleArray = ^TRGBTripleArray;
TRGBTripleArray = array[0..32767] of TRGBTriple;
implementation
procedure DrawArrow(aDest: TFPCustomCanvas; aRect: TRect; R: boolean);
var
CenColor, CenColor2: TFPColor;
lWidth, lHeight, lCenter: integer;
begin
lWidth := aRect.Right - aRect.Left;
lHeight := aRect.Bottom - aRect.Top;
CenColor := aDest.Colors[aRect.Left + lWidth div 4, aRect.Top + lHeight div 2];
CenColor2 := aDest.Colors[aRect.Left + 3 * lWidth div 4, aRect.Top + lHeight div 2];
if R then
begin
aDest.Line(aRect.Left + lWidth div 4 - 1, aRect.Top + lHeight div 2,
aRect.Left + lWidth div 4 + 3, aRect.Top + lHeight div 2);
aDest.Line(aRect.Left + lWidth div 4 + 3, aRect.Top + lHeight div 2 - 4,
aRect.Left + lWidth div 4 + 3, aRect.Top + lHeight div 2 + 4);
aDest.Line(aRect.Left + lWidth div 4 + 2, aRect.Top + lHeight div 2 - 3,
aRect.Left + lWidth div 4 + 2, aRect.Top + lHeight div 2 + 3);
aDest.Line(aRect.Left + lWidth div 4 + 1, aRect.Top + lHeight div 2 - 2,
aRect.Left + lWidth div 4 + 1, aRect.Top + lHeight div 2 + 2);
aDest.Line(aRect.Left + lWidth div 4, aRect.Top + lHeight div 2 - 1,
aRect.Left + lWidth div 4, aRect.Top + lHeight div 2 + 1);
//aDest.Colors[aRect.Left + lWidth div 4 - 3, aRect.Top + lHeight div 2] := aDest.Brush.FPColor;
end
else
begin
aDest.Line(aRect.Left + 3 * lWidth div 4 - 1, aRect.Top + lHeight div 2,
aRect.Left + 3 * lWidth div 4 + 3, aRect.Top + lHeight div 2);
aDest.Line(aRect.Left + 3 * lWidth div 4 + 2, aRect.Top + lHeight div 2 - 1,
aRect.Left + 3 * lWidth div 4 + 2, aRect.Top + lHeight div 2 + 1);
aDest.Line(aRect.Left + 3 * lWidth div 4 + 1, aRect.Top + lHeight div 2 - 2,
aRect.Left + 3 * lWidth div 4 + 1, aRect.Top + lHeight div 2 + 2);
aDest.Line(aRect.Left + 3 * lWidth div 4 + 0, aRect.Top + lHeight div 2 - 3,
aRect.Left + 3 * lWidth div 4 + 0, aRect.Top + lHeight div 2 + 3);
aDest.Line(aRect.Left + 3 * lWidth div 4 - 1, aRect.Top + lHeight div 2 - 4,
aRect.Left + 3 * lWidth div 4 - 1, aRect.Top + lHeight div 2 + 4);
//aDest.Colors[aRect.Left + 3 * lWidth div 4, aRect.Top + lHeight div 2] := aDest.Brush.FPColor;
end;
end;
procedure DrawTabHead(aDest: TFPCustomCanvas; aRect: TRect; HeadColor: TColor;
IsActive: boolean);
var
lRect: TRect;
CC: TFPColor;
begin
lRect.Bottom := aRect.Bottom;
lRect.Right := aRect.Right;
lRect.Left := aRect.Left;
lRect.Top := aRect.Top + 3;
if not IsActive then
GradientFillRect(clWhite, HeadColor, aDest, lREct)
else
begin
aDest.Brush.FPColor := TColorToFPColor(ColorToRGB(HeadColor));
aDest.Pen.FPColor := aDest.Brush.FPColor;
aDest.Rectangle(lRect);
end;
aDest.Pen.FPColor := TColorToFPColor(ColorToRGB(clWhite));
aDest.Line(lRect.Left + 2, aRect.Top + 1, lRect.Right - 2, aRect.Top + 1);
aDest.Line(lRect.Left + 1, aRect.Top + 2, lRect.Right - 1, aRect.Top + 2);
ADest.Pen.FPColor := TColorToFPColor(ColorToRGB($009C9B91));
aDest.Line(lRect.Left, lRect.Top, lRect.Left, lRect.Bottom);
//aDest.Line(lRect.Left + 3, aRect.Top, lRect.Right - 3, aRect.Top);
aDest.Line(lRect.Left + 3, aRect.Top, lRect.Right - 2, aRect.Top);
aDest.Line(lRect.Right, lRect.Top, lRect.Right, lRect.Bottom);
if not IsActive then
aDest.Line(aRect.Left, aRect.Bottom - 1, aRect.Right, aRect.Bottom - 1);
//aDest.Line();
{ aDest.Colors[aRect.Left + 1, aRect.Top + 2] := aDest.Pen.FPColor;
aDest.Colors[aRect.Left + 2, aRect.Top + 1] := aDest.Pen.FPColor;
aDest.Colors[aRect.Right - 1, aRect.Top + 2] := aDest.Pen.FPColor;
aDest.Colors[aRect.Right - 2, aRect.Top + 1] := aDest.Pen.FPColor; }
if IsActive then
begin
aDest.Pen.FPColor := TColorToFPColor(ColorToRGB($003CC7FF));
aDest.Line(lRect.Left, aRect.Top + 2, lRect.Right, aRect.Top + 2);
aDest.Line(lRect.Left + 1, aRect.Top + 1, lRect.Right - 1, aRect.Top + 1);
aDest.Pen.FPColor := TColorToFPColor(ColorToRGB($001CA7DF));
aDest.Line(lRect.Left + 2, aRect.Top, lRect.Right - 2, aRect.Top);
CC := TColorToFPColor(ColorToRGB($001CA7DF));
aDest.Colors[aRect.Left + 1, aRect.Top + 1] := CC;
aDest.Colors[aRect.Left, aRect.Top + 2] := CC;
aDest.Colors[aRect.Left + 2, aRect.Top] := CC;
aDest.Colors[aRect.Right - 1, aRect.Top + 1] := CC;
aDest.Colors[aRect.Right, aRect.Top + 2] := CC;
aDest.Colors[aRect.Right - 2, aRect.Top] := CC;
{ CC := TColorToFPColor(ColorToRGB($005CE7FF));
aDest.Colors[aRect.Left, aRect.Top + 1] := CC;
aDest.Colors[aRect.Left + 1, aRect.Top] := CC;
aDest.Colors[aRect.Left + 2, aRect.Top + 1] := CC;
aDest.Colors[aRect.Left + 1, aRect.Top + 2] := CC;
aDest.Colors[aRect.Right, aRect.Top + 1] := CC;
aDest.Colors[aRect.Right - 1, aRect.Top] := CC;
aDest.Colors[aRect.Right - 1, aRect.Top + 2] := CC;
aDest.Colors[aRect.Right - 2, aRect.Top + 1] := CC; }
end
else
begin
CC := TColorToFPColor(ColorToRGB($00BCBBB1));
aDest.Colors[aRect.Left + 1, aRect.Top + 1] := CC;
aDest.Colors[aRect.Left, aRect.Top + 2] := CC;
aDest.Colors[aRect.Left + 2, aRect.Top] := CC;
aDest.Colors[aRect.Right - 1, aRect.Top + 1] := CC;
aDest.Colors[aRect.Right, aRect.Top + 2] := CC;
aDest.Colors[aRect.Right - 2, aRect.Top] := CC;
CC := TColorToFPColor(ColorToRGB($00DCDBD1));
aDest.Colors[aRect.Left, aRect.Top + 1] := CC;
aDest.Colors[aRect.Left + 1, aRect.Top] := CC;
aDest.Colors[aRect.Left + 2, aRect.Top + 1] := CC;
aDest.Colors[aRect.Left + 1, aRect.Top + 2] := CC;
aDest.Colors[aRect.Right, aRect.Top + 1] := CC;
aDest.Colors[aRect.Right - 1, aRect.Top] := CC;
aDest.Colors[aRect.Right - 1, aRect.Top + 2] := CC;
aDest.Colors[aRect.Right - 2, aRect.Top + 1] := CC;
end;
end;
procedure DrawTabHeadMask(aDest: TFPCustomCanvas; aRect: TRect;
HeadColor: TColor; IsActive: boolean);
var
lRect: TRect;
CC: TFPColor;
begin
lRect.Bottom := aRect.Bottom;
lRect.Right := aRect.Right;
lRect.Left := aRect.Left;
lRect.Top := aRect.Top + 3;
CC := TColorToFPColor(ColorToRGB(HeadColor));
aDest.Pen.FPColor := CC;
aDest.Brush.FPColor := CC;
aDest.Rectangle(lRect);
aDest.Line(lRect.Left, lRect.Top, lRect.Left, lRect.Bottom);
aDest.Line(lRect.Left + 3, aRect.Top, lRect.Right - 2, aRect.Top);
aDest.Line(lRect.Right, lRect.Top, lRect.Right, lRect.Bottom);
aDest.Line(aRect.Left, aRect.Bottom - 1, aRect.Right, aRect.Bottom - 1);
aDest.Line(lRect.Left + 1, lRect.Top - 1, lRect.Right, lRect.Top - 1);
aDest.Line(lRect.Left + 2, lRect.Top - 2, lRect.Right - 1, lRect.Top - 2);
aDest.Colors[aRect.Left + 1, aRect.Top + 1] := CC;
aDest.Colors[aRect.Left, aRect.Top + 2] := CC;
aDest.Colors[aRect.Left + 2, aRect.Top] := CC;
aDest.Colors[aRect.Right - 1, aRect.Top + 1] := CC;
aDest.Colors[aRect.Right, aRect.Top + 2] := CC;
aDest.Colors[aRect.Right - 2, aRect.Top] := CC;
end;
function GetUniqueName(const Name: string; PControl: TComponent): string;
var
i: integer;
TName: string;
function GetTheName: boolean;
var
j: integer;
begin
Result := False;
for j := 0 to PControl.ComponentCount - 1 do
begin
if PControl.Components[j].Name = TName then
begin
Result := True;
exit;
end;
//ShowMessage(TName);
end;
end;
begin
TName := Name;
i := 0;
repeat
Inc(i);
TName := Name + IntToStr(i);
until not GetTheName;
Result := TName;
end;
function ResetCDColor(r, g, b: byte): TColor;
begin
if r <= 0 then
r := 1;
if g <= 0 then
g := 1;
if b <= 0 then
b := 1;
Result := RGB(r, g, b);
end;
function GetAColor(Color: TColor; Rate: byte): TColor;
var
r, g, b: byte;
begin
r := GetRValue(ColorToRGB(Color));
g := GetGValue(ColorToRGB(Color));
b := GetBValue(ColorToRGB(Color));
r := r * Rate div 100;
g := g * Rate div 100;
b := b * Rate div 100;
Result := ResetCDColor(r, g, b);
end;
function GetUColor(Color: TColor; Rate: byte): TColor;
var
r, g, b: byte;
begin
r := GetRValue(ColorToRGB(Color));
g := GetGValue(ColorToRGB(Color));
b := GetBValue(ColorToRGB(Color));
r := r * 100 div Rate;
g := g * 100 div Rate;
b := b * 100 div Rate;
Result := ResetCDColor(r, g, b);
end;
procedure GradientFill(Clr1, Clr2: TColor; Canvas: TCanvas);
var
ColorFrom: array[0..2] of byte;
ColorDiff: array[0..2] of integer;
DrawBand: TRect;
I: integer;
R, G, B: byte;
begin
ColorFrom[0] := GetRValue(ColorToRGB(Clr1));
ColorFrom[1] := GetGValue(ColorToRGB(Clr1));
ColorFrom[2] := GetBValue(ColorToRGB(Clr1));
ColorDiff[0] := GetRValue(ColorToRGB(Clr2)) - ColorFrom[0];
ColorDiff[1] := GetGValue(ColorToRGB(Clr2)) - ColorFrom[1];
ColorDiff[2] := GetBValue(ColorToRGB(Clr2)) - ColorFrom[2];
Canvas.Pen.Style := psSolid;
Canvas.Pen.Mode := pmCopy;
DrawBand.Left := 0;
DrawBand.Right := Canvas.Width;
for I := 0 to $ff do
begin
DrawBand.Top := MulDiv(I, Canvas.Height, $100);
DrawBand.Bottom := MulDiv(I + 1, Canvas.Height, $100);
R := ColorFrom[0] + MulDiv(I, ColorDiff[0], $ff);
G := ColorFrom[1] + MulDiv(I, ColorDiff[1], $ff);
B := ColorFrom[2] + MulDiv(I, ColorDiff[2], $ff);
Canvas.Brush.Color := RGB(R, G, B);
Canvas.FillRect(DrawBand);
end;
end;
procedure GradientFillRect(Clr1, Clr2: TColor; Canvas: TFPCustomCanvas; lRect: TRect);
var
ColorFrom: array[0..2] of byte;
ColorDiff: array[0..2] of integer;
DrawBand: TRect;
I: integer;
R, G, B: byte;
begin
ColorFrom[0] := GetRValue(ColorToRGB(Clr1));
ColorFrom[1] := GetGValue(ColorToRGB(Clr1));
ColorFrom[2] := GetBValue(ColorToRGB(Clr1));
ColorDiff[0] := GetRValue(ColorToRGB(Clr2)) - ColorFrom[0];
ColorDiff[1] := GetGValue(ColorToRGB(Clr2)) - ColorFrom[1];
ColorDiff[2] := GetBValue(ColorToRGB(Clr2)) - ColorFrom[2];
Canvas.Pen.Style := psSolid;
Canvas.Brush.Style := bsSolid;
Canvas.Pen.Mode := pmCopy;
DrawBand.Left := lRect.Left;
DrawBand.Right := lRect.Right;
for I := 0 to $ff do
begin
DrawBand.Top := lRect.Top + MulDiv(I, lRect.Bottom, $100);
DrawBand.Bottom := lRect.Top + MulDiv(I + 1, lRect.Bottom, $100);
R := ColorFrom[0] + MulDiv(I, ColorDiff[0], $ff);
G := ColorFrom[1] + MulDiv(I, ColorDiff[1], $ff);
B := ColorFrom[2] + MulDiv(I, ColorDiff[2], $ff);
Canvas.Brush.FPColor := TColorToFPColor(ColorToRGB(RGB(R, G, B)));
Canvas.Pen.FPColor := TColorToFPColor(ColorToRGB(RGB(R, G, B)));
Canvas.Rectangle(DrawBand);
end;
end;
procedure GradCenterFill(Canvas: TFPCustomCanvas; aRect: TRect;
Clr1, Clr2: TColor; rate: float);
var
lRect: TRect;
begin
lRect.Left := aRect.Left;
lRect.Top := aRect.Top;
lRect.Right := aRect.Left + Ceil(rate * (aRect.Right - aRect.Left));
lRect.Bottom := aRect.Bottom;
GradFill(Canvas, lRect, Clr1, Clr2);
lRect.Left := aRect.Left + Ceil(rate * (aRect.Right - aRect.Left));
lRect.Top := aRect.Top;
lRect.Right := aRect.Right;
lRect.Bottom := aRect.Bottom;
GradFill(Canvas, lRect, Clr2, Clr1);
end;
procedure GradFill(Canvas: TFPCustomCanvas; aRect: TRect; Clr1, Clr2: TColor);
var
ColorFrom: array[0..2] of byte;
ColorDiff: array[0..2] of integer;
I: integer;
R, G, B: byte;
RBand: TRect;
begin
ColorFrom[0] := GetRValue(ColorToRGB(Clr1));
ColorFrom[1] := GetGValue(ColorToRGB(Clr1));
ColorFrom[2] := GetBValue(ColorToRGB(Clr1));
ColorDiff[0] := GetRValue(ColorToRGB(Clr2)) - ColorFrom[0];
ColorDiff[1] := GetGValue(ColorToRGB(Clr2)) - ColorFrom[1];
ColorDiff[2] := GetBValue(ColorToRGB(Clr2)) - ColorFrom[2];
Canvas.Pen.Style := psSolid;
Canvas.Pen.Mode := pmCopy;
RBand.Bottom := aRect.Bottom;
RBand.Top := aRect.Top;
for I := 0 to $ff do
begin
RBand.Left := aRect.Left + MulDiv(I, aRect.Right - aRect.Left, $100);
RBand.Right := aRect.Left + MulDiv(I + 1, aRect.Right - aRect.Left, $100);
R := ColorFrom[0] + MulDiv(I, ColorDiff[0], $ff);
G := ColorFrom[1] + MulDiv(I, ColorDiff[1], $ff);
B := ColorFrom[2] + MulDiv(I, ColorDiff[2], $ff);
Canvas.Brush.FPColor := TColorToFPColor(ColorToRGB(RGB(R, G, B)));
Canvas.Pen.FPColor := TColorToFPColor(ColorToRGB(RGB(R, G, B)));
Canvas.RecTangle(RBand);
end;
end;
function GetNomalColor(a: byte): byte;
begin
Result := a;
if a < 1 then
a := 1;
if a > 255 then
a := 255;
end;
procedure FPImgCloneRect(IntfImg1, IntfImg2: TLazIntfImage; lRect: TRect; Fast: boolean);
var
FadeStep, px, py: integer;
Row1, Row2: PRGBTripleArray;
begin
for FadeStep := 1 to 32 do
begin
for py := lRect.Top to lRect.Bottom - 1 do
begin
if fast then
begin
Row1 := IntfImg1.GetDataLineStart(py);
Row2 := IntfImg2.GetDataLineStart(py);
end;
for px := lRect.Left to lRect.Right - 1 do
begin
if fast then
begin
Row2^[px].rgbtRed := Row1^[px].rgbtRed;
Row2^[px].rgbtGreen := Row1^[px].rgbtGreen;
Row2^[px].rgbtBlue := Row1^[px].rgbtBlue;
end
else
IntfImg2.Colors[px, py] := IntfImg1.Colors[px, py];
end;
end;
end;
end;
procedure DrawAndroidButton(Canvas: TCanvas; Color: TColor);
const
vedge = 12;
rr = 3;
var
i, xx, yy: integer;
c2: TColor;
r, g, b, r1, g1, b1: byte;
begin
//Canvas.Brush.Color := clWhite;
//Canvas.FillRect(0, 0, Canvas.Width, Canvas.Height);
Canvas.Brush.Color := Color;
Canvas.Pen.Color := Color;
r1 := GetRValue(Color);
g1 := GetGValue(Color);
b1 := GetBValue(Color);
for yy := 0 to Canvas.Height do
begin
{ if yy < vedge then
begin
r := GetNomalColor(r1 - (vedge - yy) * rr);
g := GetNomalColor(g1 - (vedge - yy) * rr);
b := GetNomalColor(b1 - (vedge - yy) * rr);
c2 := RGB(r, g, b);
Canvas.Pen.Color := c2;
end
else }
if yy > Canvas.Height - vedge then
begin
r := GetNomalColor(r1 - (yy - Canvas.Height + vedge) * rr);
g := GetNomalColor(g1 - (yy - Canvas.Height + vedge) * rr);
b := GetNomalColor(b1 - (yy - Canvas.Height + vedge) * rr);
c2 := RGB(r, g, b);
Canvas.Pen.Color := c2;
end
else
Canvas.Pen.Color := Color;
if yy < 4 then
Canvas.Line(4 - yy, yy, Canvas.Width - 4 + yy, yy)
else
if yy > Canvas.Height - 5 then
Canvas.Line(4 - Canvas.Height + yy, yy, Canvas.Width - yy - 4 + Canvas.Height, yy)
else
Canvas.Line(0, yy, Canvas.Width, yy);
end;
end;
procedure DrawXPTaskbarButton(Canvas: TCanvas; Color: TColor);
var
aColor: TColor;
begin
aColor := GetUColor(Color, 96);
with Canvas do
begin
Brush.Color := Color;
Brush.Style := bsSolid;
FillRect(0, 0, Width, Height);
Pen.Color := aColor;
RecTangle(0, 0, Width, Height);
Pen.Color := GetAColor(aColor, 86);
RoundRect(0, 0, Width, Canvas.Height, 8, 8);
// Pen.Color := aColor;
// RecTangle(0, 6, Width, Height);
Pen.Color := GetAColor(aColor, 86);
Line(0, 3, 0, Height - 3);
Line(Width, 3, Width, Height - 3);
Line(3, Height - 1, Width - 3, Height - 1);
Line(2, Height - 2, Width - 2, Height - 2);
Pen.Color := GetAColor(aColor, 93);
Line(1, Height - 4, Width - 1, Height - 4);
Pen.Color := GetAColor(aColor, 91);
Line(1, Height - 3, Width - 1, Height - 3);
Pen.Color := GetAColor(aColor, 88);
Line(Width - 2, 4, Width - 2, Height - 3);
//Pen.Color := GetAColor(aColor, 94);
//Line(2, 2, 6, 2);
end;
end;
procedure FastAntiAliasPicture(orig_bmp, dest_bmp: TBitmap);
var
x, y, cx, cy: integer;
totr, totg, totb: integer;
Row1, Row2, Row3, DestRow: PRGBTripleArray;
i: integer;
IntfImg1, IntfImg2: TLazIntfImage;
ImgHandle, ImgMaskHandle: HBitmap;
FadeStep: integer;
px, py: integer;
CurColor: TFPColor;
TmpBmp: TBitmap;
begin
if (orig_bmp = nil) or (dest_bmp = nil) then
Exit;
TmpBmp := TBitmap.Create;
TmpBmp.PixelFormat := pf24bit;
IntfImg1 := TLazIntfImage.Create(0, 0);
IntfImg1.LoadFromBitmap(orig_bmp.Handle, orig_bmp.MaskHandle);
IntfImg2 := TLazIntfImage.Create(0, 0);
IntfImg2.LoadFromBitmap(dest_bmp.Handle, dest_bmp.MaskHandle);
// For each row
for y := 0 to dest_bmp.Height - 1 do
begin
// We compute samples of 3 x 3 pixels
cy := y * 3;
// Get pointers to actual, previous and next rows in supersampled bitmap
Row1 := IntfImg1.GetDataLineStart(cy);
Row2 := IntfImg1.GetDataLineStart(cy + 1);
Row3 := IntfImg1.GetDataLineStart(cy + 2);
// Get a pointer to destination row in output bitmap
DestRow := IntfImg2.GetDataLineStart(y);
// For each column...
for x := 0 to dest_bmp.Width - 1 do
begin
// We compute samples of 3 x 3 pixels
cx := 3 * x;
// Initialize result color
totr := 0;
totg := 0;
totb := 0;
// For each pixel in sample
for i := 0 to 2 do
begin
// New red value
totr := totr + Row1^[cx + i].rgbtRed + Row2^[cx + i].rgbtRed +
Row3^[cx + i].rgbtRed;
// New green value
totg := totg + Row1^[cx + i].rgbtGreen + Row2^[cx + i].rgbtGreen +
Row3^[cx + i].rgbtGreen;
// New blue value
totb := totb + Row1^[cx + i].rgbtBlue + Row2^[cx + i].rgbtBlue +
Row3^[cx + i].rgbtBlue;
end;
// Set output pixel colors
DestRow^[x].rgbtRed := totr div 9;
DestRow^[x].rgbtGreen := totg div 9;
DestRow^[x].rgbtBlue := totb div 9;
end;
end;
IntfImg2.CreateBitmaps(ImgHandle, ImgMaskHandle, False);
TmpBmp.Handle := ImgHandle;
TmpBmp.MaskHandle := ImgMaskHandle;
dest_bmp.Empty;
dest_bmp.Assign(TmpBmp);
IntfImg1.Free;
IntfImg2.Free;
TmpBmp.Free;
end;
end.