Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Draw text on image

I'm trying to draw text on image using the below code :

procedure TfMain.TextToImage(const AText: string; const AImage: TImage);
begin
  if NOT Assigned(AImage) then Exit;    
  AImage.Canvas.BeginScene;
  AImage.Canvas.Font.Size    := 18;
  AImage.Canvas.Font.Family  := 'Arial';
  AImage.Canvas.Fill.Color   := TAlphaColorRec.Dodgerblue;
  AImage.Canvas.Font.Style   := [TFontStyle.fsbold];
  AImage.Canvas.FillText( AImage.AbsoluteRect,
                          AText,
                          False,
                          1,
                          [TFillTextFlag.RightToLeft],
                          TTextAlign.taCenter,
                          TTextAlign.taCenter);
  AImage.Canvas.EndScene;
end;

Q: Why the above procedure works on Windows but not in android ?

like image 883
RepeatUntil Avatar asked Mar 12 '26 23:03

RepeatUntil


1 Answers

Try to draw directly on the TBitmap of the timage instead of the Canvas of the TImage.

You need also to create a bitmap of your image before you try to access it:

AImage.Bitmap := TBitmap.Create(Round(AImage.Width), Round(AImage.Height));

So the correct code will be something like this:

procedure TfMain.TextToImage(const AText: string; const AImage: TImage);
begin
  if NOT Assigned(AImage) then Exit;
  AImage.Bitmap := TBitmap.Create(Round(AImage.Width), Round(AImage.Height));
  AImage.Bitmap.Canvas.BeginScene;
  try
    //....
    // Use AImage.Bitmap.Canvas as needed
    AImage.Bitmap.Canvas.FillText( AImage.AbsoluteRect,
                            AText,
                            False,
                            1,
                            [],
                            TTextAlign.Center,
                            TTextAlign.Center);
  finally
    AImage.Bitmap.Canvas.EndScene;
  end;
end;

From the TImage.Paint event code you will see:

procedure TImage.Paint;
var
  R: TRectF;
begin
  if (csDesigning in ComponentState) and not Locked and not FInPaintTo then
  begin
    R := LocalRect;
    InflateRect(R, -0.5, -0.5);
    Canvas.DrawDashRect(R, 0, 0, AllCorners, AbsoluteOpacity, $A0909090);
  end;

  UpdateCurrentBitmap;
  if FCurrentBitmap <> nil then
    DrawBitmap(Canvas, LocalRect, FCurrentBitmap, AbsoluteOpacity);
end;

So no matter what you will paint on the canvas, on the next repaint it will draw again the full bitmap erasing what you already done.

If you don't want to touch the bitmap than you need to override the OnPaint event of theTImage and call function TextToImage(const AText: string; const AImage: TImage);


Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!