Sierpinski Carpet

This demonstration is based on our Lazarus version of the fractal. See that page for the theory of the recursion involved and for the original reference of the solution written in C.

Demonstration

If the demo does not work in your current browser, try another such as Chrome. If you see no display at school, the security system might have blocked it. You can try instead this direct link to the program running on its own page.

SierpinskiCarpet.html

Smart Pascal Code of Form

unit Form1;

interface

uses 
  SmartCL.System, SmartCL.Graphics, SmartCL.Components, SmartCL.Forms, 
  SmartCL.Fonts, SmartCL.Borders, SmartCL.Application,
  SmartCL.Controls.PaintBox, SmartCL.Controls.ComboBox,
  SmartCL.Controls.Label;

type
  TForm1 = class(TW3Form)
    procedure cboBackColourChanged(Sender: TObject);
    procedure cboSquareColourChanged(Sender: TObject);
  private
    {$I 'Form1:intf'}
    BackgroundColour, SquareColour : string;
  protected
    procedure InitializeObject; override;
    procedure Sierpinski;
    function PixelToBeFilled (x, y, Width, Height : integer) : Boolean;
  end;

implementation


procedure TForm1.cboSquareColourChanged(Sender: TObject);
begin
  case cboSquareColour.SelectedIndex of
    0: SquareColour := 'red';
    1: SquareColour := 'green';
    2: SquareColour := 'blue';
  end;
  Sierpinski;
end;

procedure TForm1.cboBackColourChanged(Sender: TObject);
begin
  case cboBackColour.SelectedIndex of
    0: BackgroundColour := 'rgb(251, 250, 208)';
    1: BackgroundColour := 'orange';
    2: BackgroundColour := 'white';
  end;
  Sierpinski;
end;

procedure TForm1.InitializeObject;
begin
  inherited;
  {$I 'Form1:impl'}
  BackgroundColour := 'rgb(251, 250, 208)';
  SquareColour := 'red';

  cboSquareColour.Add('Red');
  cboSquareColour.Add('Green');
  cboSquareColour.Add('Blue');

  cboBackColour.Add('Pale yellow');
  cboBackColour.Add('Orange');
  cboBackColour.Add('White');

  w3Label2.Font.Size := 16;
end;

function TForm1.PixelToBeFilled(x, y, Width, Height : integer) : Boolean;
var
  x2, y2 : integer;
begin
  // First stopping condition
  if x < 1  then
    result := False
  else
    begin
      // If the grid was split in 9 parts, what part(x2,y2) would x,y fit into?
      x2 := (x * 3) DIV Width; // an integer from 0..2 inclusive
      y2 := (y * 3) DIV Height; // an integer from 0..2 inclusive
      // Second stopping condition
      // if in the centre square, it should be filled.
      if (x2 = 1) and (y2 = 1) then
        result := True
      else
        begin
          // General case
          {Offset x and y so it becomes bounded by 0 .. width DIV 3 and
          0.. height DIV 3 and prepares for recursive call.}
          x := x - (x2 * Width) DIV 3;
          y := y - (y2 * Height) DIV 3;
          // Recursive call
          Result := PixelToBeFilled(x, y, Width DIV 3, Height DIV 3);
        end;
    end;
end;

procedure TForm1.Sierpinski;
begin
  pb.Canvas.FillStyle := BackgroundColour;
  pb.Canvas.FillRectF(0, 0, pb.Width, pb.Height);
  pb.Canvas.FillStyle := SquareColour;
  // Draw carpet
  for var CountX := 1 to pb.Width do
    for var CountY := 1 to pb.Height do
      if PixelToBeFilled (CountX, CountY, pb.Width, pb.Height) then
        pb.Canvas.FillRectF(CountX, CountY, 1, 1);
end;
 
initialization
  Forms.RegisterForm({$I %FILE%}, TForm1);
end.    

XML Code of Form

<SMART>
  <Form version="2" subversion="2">
    <Created>2017-06-01T09:32:48.293</Created>
    <Modified>2017-06-27T17:48:29.665</Modified>
    <object type="TW3Form">
      <Caption>W3Form</Caption>
      <Name>Form1</Name>
      <object type="TW3PaintBox">
        <Width>729</Width>
        <Top>96</Top>
        <Left>24</Left>
        <Height>729</Height>
        <Color>16513751</Color>
        <Name>pb</Name>
      </object>
      <object type="TW3Label">
        <Caption>Select square colour:</Caption>
        <Width>152</Width>
        <Top>48</Top>
        <Left>32</Left>
        <Height>32</Height>
        <Name>W3Label1</Name>
        <object type="TW3Label">
          <Caption>Select square colour:</Caption>
          <Width>152</Width>
          <Top>56</Top>
          <Left>40</Left>
          <Height>32</Height>
          <Name>W3Label3</Name>
        </object>
      </object>
      <object type="TW3Label">
        <Caption>Sierpinski Carpet</Caption>
        <Width>183</Width>
        <Top>8</Top>
        <Left>312</Left>
        <Height>40</Height>
        <BorderRadius>0</BorderRadius>
        <Name>W3Label2</Name>
      </object>
      <object type="TW3ComboBox">
        <Width>128</Width>
        <Top>48</Top>
        <Left>176</Left>
        <Height>32</Height>
        <Name>cboSquareColour</Name>
        <OnChanged>cboSquareColourChanged</OnChanged>
      </object>
      <object type="TW3Label">
        <Caption>Select background colour:</Caption>
        <Width>176</Width>
        <Top>48</Top>
        <Left>449</Left>
        <Height>32</Height>
        <Name>W3Label4</Name>
      </object>
      <object type="TW3ComboBox">
        <Width>128</Width>
        <Top>48</Top>
        <Left>621</Left>
        <Height>32</Height>
        <Name>cboBackColour</Name>
        <OnChanged>cboBackColourChanged</OnChanged>
      </object>
    </object>
  </Form>
</SMART>

Programming - a skill for life!

Using a PaintBox to display Sierpinski curves