Changeset 17


Ignore:
Timestamp:
Oct 5, 2019, 12:17:17 PM (5 years ago)
Author:
chronos
Message:
  • Modified: Tiles matrix moved to separate class called TBoard.
Location:
trunk
Files:
4 edited

Legend:

Unmodified
Added
Removed
  • trunk/Forms/UFormMain.pas

    r12 r17  
    5959      40: MovedCount := Core.Game.MoveAll(drDown);
    6060    end;
    61     if MovedCount > 0 then Core.Game.FillRandomCell;
    62     if not Core.Game.CanMove and (Core.Game.GetEmptyCellsCount = 0) then
     61    if MovedCount > 0 then Core.Game.FillRandomTile;
     62    if not Core.Game.CanMove and (Core.Game.Board.GetEmptyTilesCount = 0) then
    6363      Core.Game.GameOver;
    64     if (not Core.Game.Won) and (Core.Game.GetHighestCellValue >= 2048) then
     64    if (not Core.Game.Won) and (Core.Game.Board.GetHighestTileValue >= 2048) then
    6565      Core.Game.Win;
    6666  end;
  • trunk/Forms/UFormNew.pas

    r15 r17  
    4545procedure TFormNew.Load(Game: TGame);
    4646begin
    47   ComboBoxSize.ItemIndex := Game.Size.X - 3;
     47  ComboBoxSize.ItemIndex := Game.Board.Size.X - 3;
    4848end;
    4949
    5050procedure TFormNew.Save(Game: TGame);
    5151begin
    52   Game.Size := Point(3 + ComboBoxSize.ItemIndex, 3 + ComboBoxSize.ItemIndex);
     52  Game.Board.Size := Point(3 + ComboBoxSize.ItemIndex, 3 + ComboBoxSize.ItemIndex);
    5353end;
    5454
  • trunk/UCore.pas

    r13 r17  
    5353  Randomize;
    5454  Game := TGame.Create;
    55   Game.Size := Point(4, 4);
     55  Game.Board.Size := Point(4, 4);
    5656  Game.OnChange := GameChange;
    5757  LoadConfig;
     
    116116
    117117    Game.TopScore := ReadIntegerWithDefault('TopScore', 0);
    118     Game.Size := Point(ReadIntegerWithDefault('SizeX', 4), ReadIntegerWithDefault('SizeY', 4));
     118    Game.Board.Size := Point(ReadIntegerWithDefault('SizeX', 4), ReadIntegerWithDefault('SizeY', 4));
    119119    Game.AnimationDuration := ReadIntegerWithDefault('AnimationDuration', 30);
    120120    if ValueExists('LanguageCode') then
     
    133133
    134134    WriteInteger('TopScore', Game.TopScore);
    135     WriteInteger('SizeX', Game.Size.X);
    136     WriteInteger('SizeY', Game.Size.Y);
     135    WriteInteger('SizeX', Game.Board.Size.X);
     136    WriteInteger('SizeY', Game.Board.Size.Y);
    137137    WriteInteger('AnimationDuration', Game.AnimationDuration);
    138138    if Assigned(Translator1.Language) and (Translator1.Language.Code <> '') then
  • trunk/UGame.pas

    r16 r17  
    1111type
    1212
    13   { TCell }
    14 
    15   TCell = class
     13  { TTile }
     14
     15  TTile = class
    1616    Value: Integer;
    1717    NewValue: Integer;
     
    1919    Moving: Boolean;
    2020    Shift: TPoint;
    21     procedure Assign(Source: TCell);
    22   end;
    23 
    24   TCells = class(TFPGObjectList<TCell>)
     21    procedure Assign(Source: TTile);
     22  end;
     23
     24  TTiles = class(TFPGObjectList<TTile>)
     25  end;
     26
     27  { TBoard }
     28
     29  TBoard = class
     30  private
     31    FSize: TPoint;
     32    procedure SetSize(AValue: TPoint);
     33  public
     34    Tiles: array of array of TTile;
     35    procedure Assign(Source: TBoard);
     36    procedure Clear;
     37    procedure ClearMerged;
     38    function GetHighestTileValue: Integer;
     39    function GetEmptyTilesCount: Integer;
     40    procedure GetEmptyTiles(EmptyTiles: TTiles);
     41    destructor Destroy; override;
     42    property Size: TPoint read FSize write SetSize;
    2543  end;
    2644
     
    3553    FRunning: Boolean;
    3654    FScore: Integer;
    37     FSize: TPoint;
    38     function GetCellColor(Value: Integer): TColor;
     55    function GetTileColor(Value: Integer): TColor;
    3956    procedure SetScore(AValue: Integer);
    40     procedure SetSize(AValue: TPoint);
    41     procedure GetEmptyCells(EmptyCells: TCells);
    4257    procedure DoChange;
    43     procedure ClearMerged;
    44     procedure RenderCell(Canvas: TCanvas; Cell: TCell; CellRect: TRect);
     58    procedure RenderTile(Canvas: TCanvas; Tile: TTile; TileRect: TRect);
    4559  public
    46     Cells: array of array of TCell;
     60    Board: TBoard;
    4761    TopScore: Integer;
    4862    AnimationDuration: Integer;
     
    5064    procedure GameOver;
    5165    procedure Win;
    52     function FillRandomCell: Integer;
     66    function FillRandomTile: Integer;
    5367    function CanMove: Boolean;
    54     function GetEmptyCellsCount: Integer;
    55     function GetHighestCellValue: Integer;
    5668    procedure Assign(Source: TGame);
    5769    procedure New;
    58     procedure Clear;
    5970    procedure Render(Canvas: TCanvas; CanvasSize: TPoint);
    6071    function MoveAll(Direction: TDirection): Integer;
    61     procedure MoveCell(SourceCell, TargetCell: TCell);
     72    procedure MoveTile(SourceTile, TargetTile: TTile);
    6273    function IsValidPos(Pos: TPoint): Boolean;
    6374    constructor Create;
    6475    destructor Destroy; override;
    6576    property Score: Integer read FScore write SetScore;
    66     property Size: TPoint read FSize write SetSize;
    6777    property Running: Boolean read FRunning write FRunning;
    6878    property OnChange: TNotifyEvent read FOnChange write FOnChange;
     
    8595implementation
    8696
    87 { TCell }
    88 
    89 procedure TCell.Assign(Source: TCell);
    90 begin
    91   Value := Source.Value;
    92   Merged := Source.Merged;
    93 end;
    94 
    95 { TGame }
    96 
    97 procedure TGame.SetSize(AValue: TPoint);
     97{ TBoard }
     98
     99procedure TBoard.SetSize(AValue: TPoint);
    98100var
    99101  X, Y: Integer;
     
    102104  for Y := 0 to FSize.Y - 1 do
    103105    for X := 0 to FSize.X - 1 do
    104       Cells[Y, X].Free;
     106      Tiles[Y, X].Free;
    105107  FSize := AValue;
    106   SetLength(Cells, FSize.Y, FSize.X);
     108  SetLength(Tiles, FSize.Y, FSize.X);
    107109  for Y := 0 to FSize.Y - 1 do
    108110    for X := 0 to FSize.X - 1 do
    109       Cells[Y, X] := TCell.Create;
    110 end;
    111 
    112 procedure TGame.GetEmptyCells(EmptyCells: TCells);
    113 var
    114   X, Y: Integer;
    115 begin
    116   EmptyCells.Clear;
     111      Tiles[Y, X] := TTile.Create;
     112end;
     113
     114procedure TBoard.Assign(Source: TBoard);
     115var
     116  X, Y: Integer;
     117begin
     118  Size := Source.Size;
    117119  for Y := 0 to Size.Y - 1 do
    118120    for X := 0 to Size.X - 1 do
    119       if Cells[Y, X].Value = 0 then
    120         EmptyCells.Add(Cells[Y, X]);
    121 end;
    122 
    123 procedure TGame.DoChange;
    124 begin
    125   if Assigned(FOnChange) then FOnChange(Self);
    126 end;
    127 
    128 procedure TGame.ClearMerged;
    129 var
    130   X, Y: Integer;
    131 begin
     121      Tiles[Y, X].Assign(Source.Tiles[Y, X]);
     122end;
     123
     124procedure TBoard.GetEmptyTiles(EmptyTiles: TTiles);
     125var
     126  X, Y: Integer;
     127begin
     128  EmptyTiles.Clear;
    132129  for Y := 0 to Size.Y - 1 do
    133130    for X := 0 to Size.X - 1 do
    134       Cells[Y, X].Merged := False;
     131      if Tiles[Y, X].Value = 0 then
     132        EmptyTiles.Add(Tiles[Y, X]);
     133end;
     134
     135destructor TBoard.Destroy;
     136begin
     137  Size := Point(0, 0);
     138  inherited Destroy;
     139end;
     140
     141procedure TBoard.ClearMerged;
     142var
     143  X, Y: Integer;
     144begin
     145  for Y := 0 to Size.Y - 1 do
     146    for X := 0 to Size.X - 1 do
     147      Tiles[Y, X].Merged := False;
     148end;
     149
     150function TBoard.GetEmptyTilesCount: Integer;
     151var
     152  X, Y: Integer;
     153begin
     154  Result := 0;
     155  for Y := 0 to Size.Y - 1 do
     156    for X := 0 to Size.X - 1 do
     157      if Tiles[Y, X].Value = 0 then
     158        Inc(Result);
     159end;
     160
     161function TBoard.GetHighestTileValue: Integer;
     162var
     163  X, Y: Integer;
     164begin
     165  Result := 0;
     166  for Y := 0 to Size.Y - 1 do
     167    for X := 0 to Size.X - 1 do
     168      if Result < Tiles[Y, X].Value then Result := Tiles[Y, X].Value;
     169end;
     170
     171procedure TBoard.Clear;
     172var
     173  X, Y: Integer;
     174begin
     175  for Y := 0 to Size.Y - 1 do
     176    for X := 0 to Size.X - 1 do
     177      Tiles[Y, X].Value := 0;
     178end;
     179
     180
     181{ TTile }
     182
     183procedure TTile.Assign(Source: TTile);
     184begin
     185  Value := Source.Value;
     186  Merged := Source.Merged;
     187end;
     188
     189{ TGame }
     190
     191procedure TGame.DoChange;
     192begin
     193  if Assigned(FOnChange) then FOnChange(Self);
    135194end;
    136195
     
    152211end;
    153212
    154 function TGame.FillRandomCell: Integer;
    155 var
    156   EmptyCells: TCells;
     213function TGame.FillRandomTile: Integer;
     214var
     215  EmptyTiles: TTiles;
    157216begin
    158217  Result := 0;
    159   EmptyCells := TCells.Create(False);
    160   GetEmptyCells(EmptyCells);
    161   if EmptyCells.Count > 0 then begin
    162     EmptyCells[Random(EmptyCells.Count)].Value := 2;
     218  EmptyTiles := TTiles.Create(False);
     219  Board.GetEmptyTiles(EmptyTiles);
     220  if EmptyTiles.Count > 0 then begin
     221    EmptyTiles[Random(EmptyTiles.Count)].Value := 2;
    163222    Result := 1;
    164223  end;
    165   EmptyCells.Free;
     224  EmptyTiles.Free;
    166225end;
    167226
     
    187246end;
    188247
    189 function TGame.GetEmptyCellsCount: Integer;
    190 var
    191   X, Y: Integer;
    192 begin
    193   Result := 0;
    194   for Y := 0 to Size.Y - 1 do
    195     for X := 0 to Size.X - 1 do
    196       if Cells[Y, X].Value = 0 then
    197         Inc(Result);
    198 end;
    199 
    200 function TGame.GetHighestCellValue: Integer;
    201 var
    202   X, Y: Integer;
    203 begin
    204   Result := 0;
    205   for Y := 0 to Size.Y - 1 do
    206     for X := 0 to Size.X - 1 do
    207       if Result < Cells[Y, X].Value then Result := Cells[Y, X].Value;
    208 end;
    209 
    210248procedure TGame.Assign(Source: TGame);
    211249var
     
    216254  AnimationDuration := Source.AnimationDuration;
    217255  Won := Source.Won;
    218   Size := Source.Size;
    219   for Y := 0 to Size.Y - 1 do
    220     for X := 0 to Size.X - 1 do
    221       Cells[Y, X].Assign(Source.Cells[Y, X]);
     256  Board.Assign(Source.Board);
    222257end;
    223258
     
    226261  I: Integer;
    227262begin
    228   Clear;
     263  Board.Clear;
    229264  Score := 0;
    230265  Won := False;
    231266  Running := True;
    232   for I := 0 to 1 do FillRandomCell;
     267  for I := 0 to 1 do FillRandomTile;
    233268  DoChange;
    234269end;
    235270
    236 procedure TGame.Clear;
    237 var
    238   X, Y: Integer;
    239 begin
    240   for Y := 0 to Size.Y - 1 do
    241     for X := 0 to Size.X - 1 do
    242       Cells[Y, X].Value := 0;
    243 end;
    244 
    245271procedure TGame.Render(Canvas: TCanvas; CanvasSize: TPoint);
    246272var
    247273  X, Y: Integer;
    248   CellSize: TPoint;
     274  TileSize: TPoint;
    249275  ValueStr: string;
    250276  Frame: TRect;
    251   CellRect: TRect;
     277  TileRect: TRect;
    252278  TopBarHeight: Integer;
    253   CellMargin: Integer;
     279  TileMargin: Integer;
    254280begin
    255281  TopBarHeight := ScaleY(24, 96);
    256   CellMargin := Round(CanvasSize.X / Size.X * 0.02);
     282  TileMargin := Round(CanvasSize.X / Board.Size.X * 0.02);
    257283  Canvas.Brush.Style := bsSolid;
    258284  Canvas.Brush.Color := clBlack;
     
    272298  // So dimensions are provided by CanvasSize parameter.
    273299  Frame := Rect(2, TopBarHeight, CanvasSize.X - 2, CanvasSize.Y - 2);
    274   CellSize := Point(Frame.Width div Size.X, Frame.Height div Size.Y);
    275   if CellSize.X < CellSize.Y then CellSize.Y := CellSize.X;
    276   if CellSize.Y < CellSize.X then CellSize.X := CellSize.Y;
    277   Frame := Rect(Frame.Width div 2 - (Size.X * CellSize.X) div 2,
    278     Frame.Top + Frame.Height div 2 - (Size.Y * CellSize.Y) div 2,
    279     Frame.Width div 2 + (Size.X * CellSize.X) div 2,
    280     Frame.Top + Frame.Height div 2 + (Size.Y * CellSize.Y) div 2);
     300  TileSize := Point(Frame.Width div Board.Size.X, Frame.Height div Board.Size.Y);
     301  if TileSize.X < TileSize.Y then TileSize.Y := TileSize.X;
     302  if TileSize.Y < TileSize.X then TileSize.X := TileSize.Y;
     303  Frame := Rect(Frame.Width div 2 - (Board.Size.X * TileSize.X) div 2,
     304    Frame.Top + Frame.Height div 2 - (Board.Size.Y * TileSize.Y) div 2,
     305    Frame.Width div 2 + (Board.Size.X * TileSize.X) div 2,
     306    Frame.Top + Frame.Height div 2 + (Board.Size.Y * TileSize.Y) div 2);
    281307
    282308  Canvas.Brush.Style := bsSolid;
     
    286312  Canvas.Font.Color := clBlack;
    287313
    288   // Draw static cells
    289   for Y := 0 to Size.Y - 1 do
    290     for X := 0 to Size.X - 1 do begin
    291       if Cells[Y, X].Moving then Canvas.Brush.Color := GetCellColor(0)
    292         else Canvas.Brush.Color := GetCellColor(Cells[Y, X].Value);
     314  // Draw static tiles
     315  for Y := 0 to Board.Size.Y - 1 do
     316    for X := 0 to Board.Size.X - 1 do begin
     317      if Board.Tiles[Y, X].Moving then Canvas.Brush.Color := GetTileColor(0)
     318        else Canvas.Brush.Color := GetTileColor(Board.Tiles[Y, X].Value);
    293319      Canvas.Brush.Style := bsSolid;
    294       CellRect := Bounds(
    295         Frame.Left + X * CellSize.X + CellMargin,
    296         Frame.Top + Y * CellSize.Y + CellMargin,
    297         CellSize.X - 2 * CellMargin, CellSize.Y - 2 * CellMargin);
    298       RenderCell(Canvas, Cells[Y, X], CellRect);
    299     end;
    300 
    301   // Draw moving cells
    302   for Y := 0 to Size.Y - 1 do
    303     for X := 0 to Size.X - 1 do
    304     if Cells[Y, X].Moving then begin
    305       Canvas.Brush.Color := GetCellColor(Cells[Y, X].Value);
     320      TileRect := Bounds(
     321        Frame.Left + X * TileSize.X + TileMargin,
     322        Frame.Top + Y * TileSize.Y + TileMargin,
     323        TileSize.X - 2 * TileMargin, TileSize.Y - 2 * TileMargin);
     324      RenderTile(Canvas, Board.Tiles[Y, X], TileRect);
     325    end;
     326
     327  // Draw moving Tiles
     328  for Y := 0 to Board.Size.Y - 1 do
     329    for X := 0 to Board.Size.X - 1 do
     330    if Board.Tiles[Y, X].Moving then begin
     331      Canvas.Brush.Color := GetTileColor(Board.Tiles[Y, X].Value);
    306332      Canvas.Brush.Style := bsSolid;
    307       CellRect := Bounds(
    308         Frame.Left + X * CellSize.X + Trunc(Cells[Y, X].Shift.X / 100 * CellSize.X + CellMargin),
    309         Frame.Top + Y * CellSize.Y + Trunc(Cells[Y, X].Shift.Y / 100 * CellSize.Y + CellMargin),
    310         CellSize.X - 2 * CellMargin, CellSize.Y - 2 * CellMargin);
    311       RenderCell(Canvas, Cells[Y, X], CellRect);
    312     end;
    313 end;
    314 
    315 procedure TGame.RenderCell(Canvas: TCanvas; Cell: TCell; CellRect: TRect);
     333      TileRect := Bounds(
     334        Frame.Left + X * TileSize.X + Trunc(Board.Tiles[Y, X].Shift.X / 100 * TileSize.X + TileMargin),
     335        Frame.Top + Y * TileSize.Y + Trunc(Board.Tiles[Y, X].Shift.Y / 100 * TileSize.Y + TileMargin),
     336        TileSize.X - 2 * TileMargin, TileSize.Y - 2 * TileMargin);
     337      RenderTile(Canvas, Board.Tiles[Y, X], TileRect);
     338    end;
     339end;
     340
     341procedure TGame.RenderTile(Canvas: TCanvas; Tile: TTile; TileRect: TRect);
    316342var
    317343  ValueStr: string;
    318344  TextSize: TSize;
    319345begin
    320   Canvas.FillRect(CellRect);
    321   if Cell.Value <> 0 then begin
    322     ValueStr := IntToStr(Cell.Value);
     346  Canvas.FillRect(TileRect);
     347  if Tile.Value <> 0 then begin
     348    ValueStr := IntToStr(Tile.Value);
    323349    Canvas.Brush.Style := bsClear;
    324     Canvas.Font.Height := Trunc(CellRect.Height * 0.7);
     350    Canvas.Font.Height := Trunc(TileRect.Height * 0.7);
    325351    TextSize := Canvas.TextExtent(ValueStr);
    326     if TextSize.Width > CellRect.Width then
    327       Canvas.Font.Height := Trunc(Canvas.Font.Height / TextSize.Width * CellRect.Width);
     352    if TextSize.Width > TileRect.Width then
     353      Canvas.Font.Height := Trunc(Canvas.Font.Height / TextSize.Width * TileRect.Width);
    328354    TextSize := Canvas.TextExtent(ValueStr);
    329     Canvas.TextOut(CellRect.Left + CellRect.Width div 2 - TextSize.Width div 2,
    330       CellRect.Top + CellRect.Height div 2 - TextSize.Height div 2, ValueStr);
     355    Canvas.TextOut(TileRect.Left + TileRect.Width div 2 - TextSize.Width div 2,
     356      TileRect.Top + TileRect.Height div 2 - TextSize.Height div 2, ValueStr);
    331357  end;
    332358end;
     
    355381    drLeft: begin
    356382      StartPoint := Point(1, 0);
    357       AreaSize := Point(Size.X - 2, Size.Y - 1);
     383      AreaSize := Point(Board.Size.X - 2, Board.Size.Y - 1);
    358384      Increment := Point(1, 1);
    359385      MoveDirection := Point(-1, 0);
     
    361387    drUp: begin
    362388      StartPoint := Point(0, 1);
    363       AreaSize := Point(Size.X - 1, Size.Y - 2);
     389      AreaSize := Point(Board.Size.X - 1, Board.Size.Y - 2);
    364390      Increment := Point(1, 1);
    365391      MoveDirection := Point(0, -1);
    366392    end;
    367393    drRight: begin
    368       StartPoint := Point(Size.X - 2, 0);
    369       AreaSize := Point(Size.X - 2, Size.Y - 1);
     394      StartPoint := Point(Board.Size.X - 2, 0);
     395      AreaSize := Point(Board.Size.X - 2, Board.Size.Y - 1);
    370396      Increment := Point(-1, 1);
    371397      MoveDirection := Point(1, 0);
    372398    end;
    373399    drDown: begin
    374       StartPoint := Point(0, Size.Y - 2);
    375       AreaSize := Point(Size.X - 1, Size.Y - 2);
     400      StartPoint := Point(0, Board.Size.Y - 2);
     401      AreaSize := Point(Board.Size.X - 1, Board.Size.Y - 2);
    376402      Increment := Point(1, -1);
    377403      MoveDirection := Point(0, 1);
     
    379405  end;
    380406  MovedCount := 0;
    381   ClearMerged;
    382   for I := 0 to Max(Size.X, Size.Y) - 1 do begin
     407  Board.ClearMerged;
     408  for I := 0 to Max(Board.Size.X, Board.Size.Y) - 1 do begin
    383409    PI.Y := 0;
    384     for Y := 0 to Size.Y - 1 do
    385       for X := 0 to Size.X - 1 do begin
    386         Cells[Y, X].NewValue := Cells[Y, X].Value;
    387         Cells[Y, X].Moving := False;
     410    for Y := 0 to Board.Size.Y - 1 do
     411      for X := 0 to Board.Size.X - 1 do begin
     412        Board.Tiles[Y, X].NewValue := Board.Tiles[Y, X].Value;
     413        Board.Tiles[Y, X].Moving := False;
    388414      end;
    389415
     
    395421        PNew.Y := P.Y + DirectionDiff[Direction].Y;
    396422        if IsValidPos(PNew) then begin
    397           if (Cells[P.Y, P.X].NewValue <> 0) then begin
    398             if (Cells[PNew.Y, PNew.X].NewValue = 0) then begin
    399               Cells[P.Y, P.X].Moving := True;
    400               Cells[PNew.Y, PNew.X].NewValue := Cells[P.Y, P.X].NewValue;
    401               Cells[PNew.Y, PNew.X].Merged := Cells[P.Y, P.X].Merged;
    402               Cells[P.Y, P.X].NewValue := 0;
    403               Cells[P.Y, P.X].Merged := False;
     423          if (Board.Tiles[P.Y, P.X].NewValue <> 0) then begin
     424            if (Board.Tiles[PNew.Y, PNew.X].NewValue = 0) then begin
     425              Board.Tiles[P.Y, P.X].Moving := True;
     426              Board.Tiles[PNew.Y, PNew.X].NewValue := Board.Tiles[P.Y, P.X].NewValue;
     427              Board.Tiles[PNew.Y, PNew.X].Merged := Board.Tiles[P.Y, P.X].Merged;
     428              Board.Tiles[P.Y, P.X].NewValue := 0;
     429              Board.Tiles[P.Y, P.X].Merged := False;
    404430              Inc(MovedCount);
    405431            end else
    406             if (not Cells[P.Y, P.X].Merged) and (not Cells[PNew.Y, PNew.X].Merged) and
    407             (Cells[PNew.Y, PNew.X].NewValue = Cells[P.Y, P.X].NewValue) then begin
    408               Cells[P.Y, P.X].Moving := True;
    409               Cells[PNew.Y, PNew.X].NewValue := Cells[PNew.Y, PNew.X].NewValue + Cells[P.Y, P.X].NewValue;
    410               Cells[PNew.Y, PNew.X].Merged := True;
    411               Cells[P.Y, P.X].NewValue := 0;
    412               Cells[P.Y, P.X].Merged := False;
     432            if (not Board.Tiles[P.Y, P.X].Merged) and (not Board.Tiles[PNew.Y, PNew.X].Merged) and
     433            (Board.Tiles[PNew.Y, PNew.X].NewValue = Board.Tiles[P.Y, P.X].NewValue) then begin
     434              Board.Tiles[P.Y, P.X].Moving := True;
     435              Board.Tiles[PNew.Y, PNew.X].NewValue := Board.Tiles[PNew.Y, PNew.X].NewValue + Board.Tiles[P.Y, P.X].NewValue;
     436              Board.Tiles[PNew.Y, PNew.X].Merged := True;
     437              Board.Tiles[P.Y, P.X].NewValue := 0;
     438              Board.Tiles[P.Y, P.X].Merged := False;
    413439              Inc(MovedCount);
    414               Score := Score + Cells[PNew.Y, PNew.X].NewValue;
     440              Score := Score + Board.Tiles[PNew.Y, PNew.X].NewValue;
    415441            end;
    416442          end;
     
    425451    end;
    426452
    427     // Animate cell move
     453    // Animate tiles move
    428454    StartTime := Now;
    429     EndTime := StartTime + AnimationDuration / 300 * OneSecond / Size.X;
     455    EndTime := StartTime + AnimationDuration / 300 * OneSecond / Max(Board.Size.X, Board.Size.Y);
    430456    if AnimationDuration > 0 then
    431457    repeat
     
    433459      Part := (Time - StartTime) / (EndTime - StartTime);
    434460      if Part > 1 then Part := 1;
    435       for Y := 0 to Size.Y - 1 do
    436         for X := 0 to Size.X - 1 do begin
    437           if Cells[Y, X].Moving then
    438             Cells[Y, X].Shift := Point(Trunc(Part * MoveDirection.X * 100),
     461      for Y := 0 to Board.Size.Y - 1 do
     462        for X := 0 to Board.Size.X - 1 do begin
     463          if Board.Tiles[Y, X].Moving then
     464            Board.Tiles[Y, X].Shift := Point(Trunc(Part * MoveDirection.X * 100),
    439465              Trunc(Part * MoveDirection.Y * 100));
    440466        end;
     
    444470    until Time > EndTime;
    445471
    446     // Set final cell values
    447     for Y := 0 to Size.Y - 1 do
    448       for X := 0 to Size.X - 1 do begin
    449         Cells[Y, X].Shift := Point(0, 0);
    450         Cells[Y, X].Moving := False;
    451         Cells[Y, X].Value := Cells[Y, X].NewValue;
     472    // Set final tiles values
     473    for Y := 0 to Board.Size.Y - 1 do
     474      for X := 0 to Board.Size.X - 1 do begin
     475        Board.Tiles[Y, X].Shift := Point(0, 0);
     476        Board.Tiles[Y, X].Moving := False;
     477        Board.Tiles[Y, X].Value := Board.Tiles[Y, X].NewValue;
    452478      end;
    453479    DoChange;
     
    457483end;
    458484
    459 procedure TGame.MoveCell(SourceCell, TargetCell: TCell);
    460 begin
    461   TargetCell.Value := SourceCell.Value;
    462   SourceCell.Value := 0;
    463   TargetCell.Merged := SourceCell.Merged;
    464   SourceCell.Merged := False;
     485procedure TGame.MoveTile(SourceTile, TargetTile: TTile);
     486begin
     487  TargetTile.Value := SourceTile.Value;
     488  SourceTile.Value := 0;
     489  TargetTile.Merged := SourceTile.Merged;
     490  SourceTile.Merged := False;
    465491end;
    466492
    467493function TGame.IsValidPos(Pos: TPoint): Boolean;
    468494begin
    469   Result := (Pos.X >= 0) and (Pos.X < FSize.X) and
    470     (Pos.Y >= 0) and (Pos.Y < FSize.Y);
     495  Result := (Pos.X >= 0) and (Pos.X < Board.Size.X) and
     496    (Pos.Y >= 0) and (Pos.Y < Board.Size.Y);
    471497end;
    472498
     
    474500begin
    475501  AnimationDuration := 30;
     502  Board := TBoard.Create;
    476503end;
    477504
    478505destructor TGame.Destroy;
    479506begin
    480   Size := Point(0, 0);
     507  FreeAndNil(Board);
    481508  inherited;
    482509end;
    483510
    484 function TGame.GetCellColor(Value: Integer): TColor;
     511function TGame.GetTileColor(Value: Integer): TColor;
    485512begin
    486513  case Value of
Note: See TracChangeset for help on using the changeset viewer.