In Delphi 10.2. using Firemonkey for a Windows 10 desktop application I would like distort the image of a TImage according to a wave function (or a Perlin Noise function or a similar function).
On the creation of the application's main form I first calculate the wave (or noise) data and keep it in a 3 dimensional array var WaveData: array[0..MaxNumOfFunctionValues-1, 0..BitmapWidth-1, 0..BitmapHeight-1] of Integer.
On a TTimer.OnTimer event I initiate the drawing of the distortion by calling the following procedure:
procedure DrawWaveDistortion;
var
SourceBitmap, TargetBitmap: TBitmap;
SourceBitmapData, TargetBitmapData: TBitmapData;
MapAccessOk: Boolean;
BMWidth, BMHeight: Integer;
ix, iy: Integer;
Shift: Integer;
Shiftedix, Shiftediy: Integer;
Color: TAlphaColor;
begin
SourceBitmap:=Image1.Bitmap;
BMWidth:=SourceBitmap.Width;
BMHeight:=SourceBitmap.Height;
TargetBitmap:=TBitmap.Create(BMWidth, BMHeight);
try
MapAccessOk:=SourceBitmap.Map(TMapAccess.Read, SourceBitmapData);
try
if MapAccessOk then
begin
MapAccessOk:=TargetBitmap.Map(TMapAccess.Write, TargetBitmapData);
try
if MapAccessOk then
begin
for ix := 0 to BMWidth-1 do
begin
for iy := 0 to BMHeight-1 do
begin
Shift:=WaveData[StepCounter, ix, iy];
Shiftedix:=EnsureRange(ix+Shift, 0, BMWidth-1);
Shiftediy:=EnsureRange(iy+Shift, 0, BMHeight-1);
Color:=SourceBitmapData.GetPixel(Shiftedix, Shiftediy);
TargetBitmapData.SetPixel(ix, iy, Color);
end;
end;
end;
finally
TargetBitmap.Unmap(TargetBitmapData);
end;
end;
finally
SourceBitmap.Unmap(SourceBitmapData);
end;
Image1.Bitmap.Assign(TargetBitmap);
Inc(StepCounter);
if StepCounter>=MaxNumOfFunctionValues then
begin
StepCounter:=0;
end;
finally
FTargetBitmap.Free;
end;
end;
I use 32 ms for the TTimer.Interval.
This works fine and animates the TImage with some sort of water wave effect. However it is to slow, the number of frames per second is low and so I do get a jerky animation (specially when I try to add some other effects).
What can I try to do to improve the performance and increase the number of frames per second?