Beispiel #1
0
        /// <summary>
        ///     Move a <see cref="Tetrimino" /> towards a <see cref="MoveDirection" /> if permits.
        ///     The <see cref="Tetrimino" /> will not be changed if the operation fails.
        /// </summary>
        /// <param name="collisionChecker">
        ///     A <see cref="Func{Block, Boolean}" /> which returns true.
        ///     when the block will collide
        /// </param>
        /// <param name="direction">Direction to move</param>
        /// <returns>Whether the <see cref="TryMove(MoveDirection, Func{Block, bool})" /> step succeeds</returns>
        public bool TryMove(MoveDirection direction, Func <Block, bool> collisionChecker)
        {
            var position = Position;

            if (direction == MoveDirection.Down)
            {
                var row = position.Y + 1;
                position = new Position(position.X, row);
            }
            else
            {
                var delta  = direction == MoveDirection.Right ? 1 : -1;
                var column = position.X + delta;
                position = new Position(column, position.Y);
            }

            var newBlocks = GeneratorHelper.CreateOffsetBlocks(Kind, position, FacingDirection);

            if (newBlocks.Any(collisionChecker))
            {
                return(false);
            }
            GeneratorHelper.MapAtomicNumberForNewBlocks(Blocks, newBlocks);

            Position = position;
            Blocks   = newBlocks;
            return(true);
        }
Beispiel #2
0
 protected Tetrimino(TetriminoKind kind, Position position, Position firstBlockPosition,
                     Direction facingDirection)
 {
     Kind               = kind;
     Position           = position;
     FacingDirection    = facingDirection;
     FirstBlockPosition = firstBlockPosition;
     Blocks             = GeneratorHelper.CreateOffsetBlocks(kind, Position, facingDirection);
 }
Beispiel #3
0
        /// <summary>
        ///     Rotate a <see cref="Tetrimino" /> towards a <see cref="RotationDirection" /> if permits.
        ///     The <see cref="Tetrimino" /> will not be changed if the operation fails.
        /// </summary>
        /// <param name="collisionChecker">
        ///     A <see cref="Func{Block, Boolean}" /> which returns true when the block will
        ///     collide
        /// </param>
        /// <param name="rotationDirection">Direction to rotate</param>
        /// <returns>Whether the <see cref="TryRotate" /> step succeeds</returns>
        public bool TryRotate(RotationDirection rotationDirection, Func <Block, bool> collisionChecker)
        {
            var count     = Enum.GetValues(typeof(Direction)).Length;
            var delta     = rotationDirection == RotationDirection.Right ? 1 : -1;
            var direction = (int)FacingDirection + delta;

            if (direction < 0)
            {
                direction += count;
            }

            if (direction >= count)
            {
                direction %= count;
            }

            var adjustPattern = Kind == TetriminoKind.Linear
                ? new[] { 0, 1, -1, 2, -2 }
                : new[] { 0, 1, -1 };

            foreach (var adjust in adjustPattern)
            {
                var newPos    = new Position(Position.X + adjust, Position.Y);
                var newBlocks = GeneratorHelper.CreateOffsetBlocks(Kind, newPos, (Direction)direction);

                if (!newBlocks.Any(collisionChecker))
                {
                    GeneratorHelper.MapAtomicNumberForNewBlocks(Blocks, newBlocks);

                    FacingDirection = (Direction)direction;
                    Position        = newPos;
                    Blocks          = newBlocks;
                    return(true);
                }
            }

            return(false);
        }