Search code examples
delphicanvasrounded-corners

Delphi 7 - How to fill a rounded rectangle with brush?


I am trying to use Canvas to paint a Dialog-like form. I can put rounded borders in it and a rounded rectangle as a header/title. I want to fill only the title with brush.

see form here

However, I'm struggling to fill this title. When using FillRect all Form is repainted. Tried to search here, so if I missed, just point me where to go. Otherwise, how can I do it? Using Delphi 7, OnPaint event.

procedure TCustomDialog.FormPaint(Sender: TObject);
var
  Rect: TRect;
  BorderColor: TColor;
  BrushColor: TColor;
begin
  // Rect for Form's borders;
  Rect.Left := 0;
  Rect.Top := 0;
  Rect.Right  := ClientWidth;
  Rect.Bottom := ClientHeight;

  BorderColor := HtmlToTColor('#ffffff');
  BrushColor := HtmlToTColor('#ffffff');

  // Here I set the colors of Canvas.Pen (border) and Canvas.Brush (Filling),
  // similar to Bootstrap themes/classes (Default, Success, Warning, Danger);
  case DialogType of
    dtInformation:
    begin
      BorderColor := HtmlToTColor(Header_Color_Pen_Information);
      BrushColor := HtmlToTColor(Header_Color_Brush_Information);
    end;

    dtSuccess:
    begin
      BorderColor := HtmlToTColor(Header_Color_Pen_Success);
      BrushColor := HtmlToTColor(Header_Color_Brush_Success);
    end;

    dtWarning:
    begin
      BorderColor := HtmlToTColor(Header_Color_Pen_Warning);
      BrushColor := HtmlToTColor(Header_Color_Brush_Warning);
    end;

    dtError:
    begin
      BorderColor := HtmlToTColor(Header_Color_Pen_Error);
      BrushColor := HtmlToTColor(Header_Color_Brush_Error);
    end;
  end;

  with Canvas do
  begin
    Pen.Color := BorderColor;
    Pen.Width := Form_Pen_Width;

    // Draw rounded borders for Form;
    RoundRect(1, 1, Rect.Right - 1, Rect.Bottom - 1, Form_Border_Radius - 1, Form_Border_Radius - 1);

    // Rect for Dialog's Header;
    Rect.Left := Component_Gutter;
    Rect.Top := Component_Gutter;
    Rect.Right  := ClientWidth - Component_Gutter;
    Rect.Bottom := Form_Header_Height;

    RoundRect(Component_Gutter, Component_Gutter, ClientWidth - Component_Gutter, Form_Header_Height,
  Form_Border_Radius - 2, Form_Border_Radius - 2);

    Brush.Color := BrushColor;
    FillRect(Rect);
  end;
end;

Solution

  • When you prepare to draw the rounded rectangle, define Brush.Color to have the color you want the rectangle to be filled with, before drawing.

    The Documentation for Delphi 7 says:

    Rectangle
    Draws a rectangle on the canvas with its upper left corner at the point (X1, Y1) and its lower right corner at the point (X2, Y2). Use Rectangle to draw a box using Pen and fill it using Brush.

    RoundRect
    Draws a rectangle with rounded corners on the canvas.

    From Delphi XE7 doc:

    Use RoundRect to draw a rounded rectangle using Pen and fill it with Brush.

    So, you need to define the colors for Pen and Brush before you call RoundRect()

    The last block of your code should be in line with

      with Canvas do
      begin
        Pen.Color := BorderColor;
        Pen.Width := Form_Pen_Width;
        Brush.Color := BrushColor; // Add this line to control which fill color the form will have
    
        // Draw rounded borders for Form;
        RoundRect(1, 1, Rect.Right - 1, Rect.Bottom - 1, Form_Border_Radius - 1, Form_Border_Radius - 1);
    
        // Rect for Dialog's Header;
        Rect.Left := Component_Gutter;
        Rect.Top := Component_Gutter;
        Rect.Right  := ClientWidth - Component_Gutter;
        Rect.Bottom := Form_Header_Height;
    
        Brush.Color := clYellow;  // This line defines the fill color of the "header"
        RoundRect(Component_Gutter, Component_Gutter, ClientWidth - Component_Gutter, Form_Header_Height, Form_Border_Radius - 2, Form_Border_Radius - 2);
    
        Brush.Color := BrushColor; // Resets the brush color to the same as the form has
    //    FillRect(Rect); Remove this line, as it overdraws the "header" incl. its border
      end;
    

    And a sample image:

    enter image description here