3
votes

This question looks very simple, with VCL this is works fine (Image is TImage on VCL):

procedure TFormMain.btnDrawBackgroundClick(Sender: TObject);
var
  theme: HTHEME;
begin
  theme := OpenThemeData(0, 'TASKDIALOG');
  if theme <> 0 then
  try
    DrawThemeBackground(theme,
                        Image.Canvas.Handle,
                        TDLG_SECONDARYPANEL,
                        0,
                        Image.ClientRect,
                        nil);
  finally
    CloseThemeData(theme);
  end;
end;

Question: what I should change to get the same effect with FMX (on Windows)

1

1 Answers

4
votes

Based on this answer you simply can't do that.

The problem is that with Firemonkey, you only have a single device context for the form and not one for each component. When a component needs to be redrawn, it gets passed the forms canvas but with clipping and co-ordinates mapped to the components location.

But there is always some workaround and you can try something like this.

procedure TFormMain.btnDrawBackgroundClick(Sender: TObject);
var
  lTheme : HTHEME;
  lStream : TMemoryStream;
  lBitmap : Vcl.Graphics.TBitmap;
begin
  lTheme := OpenThemeData(0, 'TASKDIALOG');
  if lTheme <> 0 then
  try
    lBitmap := Vcl.Graphics.TBitmap.Create;
    try
      lBitmap.Width := Round(Image.Width);
      lBitmap.Height := Round(Image.Height);
      DrawThemeBackground(lTheme, lBitmap.Canvas.Handle, TDLG_SECONDARYPANEL, 0, 
                          Rect(0, 0, lBitmap.Width, lBitmap.Height), nil);
      lStream := TMemoryStream.Create;
      try
        lBitmap.SaveToStream(lStream);
        Image.Bitmap.LoadFromStream(lStream);
      finally
        lStream.Free;
      end;
    finally
      lBitmap.Free;
    end;
  finally
    CloseThemeData(lTheme);
  end;
end;