TetrisGameState SetCurrentPiece(PieceInstance currentPiece, bool autoSolidify)
        {
            if (ValidPosition(currentPiece, Grid))
                return new TetrisGameState(PieceGenerator, Rows, Points, currentPiece, NextPiece, Grid);

            if (autoSolidify)
                return SolidifyCurrentPiece(Grid);

            return this;
        }
 static bool ValidPosition(PieceInstance livePiece, Color[,] grid)
 {
     var shape = livePiece.Shape.Data;
     for (int l = 0; l < 4; l++)
     {
         int checkY = livePiece.Position.Y + l - 1;
         for (int c = 0; c < 4; c++)
         {
             int checkX = livePiece.Position.X + c - 2;
             if (checkY < 0)
                 continue;
             if (shape[l, c] && (checkX < 0 || checkX >= 10 || checkY < 0 || checkY >= 20 || grid[checkY, checkX] != Color.Transparent))
                 return false;
         }
     }
     return true;
 }
 public TetrisGameState Tick()
 {
     var nextPiece = new PieceInstance(CurrentPiece.Piece, CurrentPiece.Rotation,
         new Point(CurrentPiece.Position.X, CurrentPiece.Position.Y + 1));
     return SetCurrentPiece(nextPiece, true);
 }
 public TetrisGameState RotateCounterClockwise()
 {
     var nextRotation = (CurrentPiece.Rotation + 1) % CurrentPiece.Piece.Shapes.Length;
     var nextPiece = new PieceInstance(CurrentPiece.Piece, nextRotation, CurrentPiece.Position);
     return SetCurrentPiece(nextPiece, false);
 }
 public TetrisGameState MoveRight()
 {
     var nextPiece = new PieceInstance(CurrentPiece.Piece, CurrentPiece.Rotation,
         new Point(CurrentPiece.Position.X + 1, CurrentPiece.Position.Y));
     return SetCurrentPiece(nextPiece, false);
 }
 public TetrisGameState(IPieceGenerator generator, int rows, int points, PieceInstance current, Piece next, Color[,] grid)
 {
     PieceGenerator = generator;
     Level = rows / 10;
     Rows = rows;
     Points = points;
     CurrentPiece = current;
     NextPiece = next;
     Grid = grid;
     IsFinished = !ValidPosition(current, grid);
 }