private bool OnlyMovePlayer(Player sender, Vector2 Distance) { if (Distance.X == 0) { if (Distance.Y > 0) { if (Current.PlayerCanMove(sender, Direction.Down)) { sender.MovePlayer(Direction.Down); return true; } } else { if (Current.PlayerCanMove(sender, Direction.Up)) { sender.MovePlayer(Direction.Up); return true; } } return false; } else if (Distance.Y == 0) { if (Distance.X > 0) { if (Current.PlayerCanMove(sender, Direction.Right)) { sender.MovePlayer(Direction.Right); return true; } } else { if (Current.PlayerCanMove(sender, Direction.Left)) { sender.MovePlayer(Direction.Left); return true; } } return false; } if (Distance.X > 0) { if (Current.PlayerCanMove(sender, Direction.Right)) { sender.MovePlayer(Direction.Right); return true; } } else if (Distance.X < 0) { if (Current.PlayerCanMove(sender, Direction.Left)) { sender.MovePlayer(Direction.Left); return true; } } if (Distance.Y > 0) { if (Current.PlayerCanMove(sender, Direction.Down)) { sender.MovePlayer(Direction.Down); return true; } } else if (Distance.Y < 0) { if (Current.PlayerCanMove(sender, Direction.Up)) { sender.MovePlayer(Direction.Up); return true; } } return false; }
/// <summary> /// If possible moves a row and then the player in a direction. /// </summary> /// <returns>Returns true if player was able to move.</returns> private bool TryShiftRowAndMove(Player sender, Direction dir) { if (dir == Direction.Left || dir == Direction.Right) { if (Current.CanShift((int)sender.Position.Y) && Current.PlayerCanMove(sender, dir)) { Current.ShiftRow((int)sender.Position.Y, dir); sender.MovePlayer(dir); return true; } } else { if (Current.CanShift((int)sender.Position.X) && Current.PlayerCanMove(sender, dir)) { Current.ShiftRow((int)sender.Position.X, dir); sender.MovePlayer(dir); return true; } } return false; }
private bool LastMove(Player sender, Direction dir) { if (Current.PlayerCanMove(sender, dir)) { sender.MovePlayer(dir); return true; } else if (TryRotateSelf(sender, dir)) { sender.MovePlayer(dir); return true; } else { Current.Rotate((int)sender.Position.X, (int)sender.Position.Y, Rotate.Right); return true; } }
/// <summary> /// Execute when players X or Y location is alligned with the Chest. /// </summary> private void HandleZeroDistance(Player sender, Vector2 Distance, Direction dir) { if (Current.PlayerCanMove(sender, dir)) { // Player can move, try to block another player. ExecuteCounter(sender, dir); // Execute counter move. sender.MovePlayer(dir); // Move self in direction. return; } // Try rotating self to see if you can move after. Current.Rotate((int)sender.Position.X, (int)sender.Position.Y, Rotate.Right); if (Current.PlayerCanMove(sender, dir)) { sender.MovePlayer(dir); return; } Current.Rotate((int)sender.Position.X, (int)sender.Position.Y, Rotate.Left, 2); if (Current.PlayerCanMove(sender, dir)) { sender.MovePlayer(dir); return; } Current.Rotate((int)sender.Position.X, (int)sender.Position.Y, Rotate.Right, 1, true); // Rotating self not usefull, reset rotation. // Move not possible. Rotate adjacent and check again. RotateAdjacent(sender, Distance); // If player can move after rotating , move player. if (Current.PlayerCanMove(sender, dir)) sender.MovePlayer(dir); }
private bool HandleSameBlock(Player sender, Vector2 Distance) { if (OnlyMovePlayer(sender, Distance)) return true; if (Distance.X > 0) { if (TryRotateSelf(sender, Direction.Right) || TryRotate(sender, Direction.Right)) { sender.MovePlayer(Direction.Right); return true; } } else if (Distance.X < 0) { if (TryRotateSelf(sender, Direction.Left) || TryRotate(sender, Direction.Left)) { sender.MovePlayer(Direction.Left); return true; } } if (Distance.Y > 0) { if (TryRotateSelf(sender, Direction.Down) || TryRotate(sender, Direction.Down)) { sender.MovePlayer(Direction.Down); return true; } } else if (Distance.Y < 0) { if (TryRotateSelf(sender, Direction.Up) || TryRotate(sender, Direction.Up)) { sender.MovePlayer(Direction.Up); return true; } } return false; }
/// <summary> /// Execute when player is within a 1 block radius of chest. /// </summary> private void HandleLastMove(Player sender, Vector2 Distance) { // State where player is in proximity of chest if (Distance.X == 0) { if (Distance.Y > 0) LastMove(sender, Direction.Down); else LastMove(sender, Direction.Up); return; } else if (Distance.Y == 0) { if (Distance.X > 0) LastMove(sender, Direction.Right); else LastMove(sender, Direction.Left); return; } if (Distance.X == 1 && Distance.Y == 1) { // Player is Left and above of chest. if (Current.PlayerCanMoveOut(sender, Direction.Right)) { Current.ShiftRow((int)sender.Position.X, Direction.Down); sender.MovePlayer(Direction.Right); } else if (Current.PlayerCanMoveOut(sender, Direction.Down)) { Current.ShiftRow((int)sender.Position.Y, Direction.Right); sender.MovePlayer(Direction.Down); } else Current.ShiftRow((int)sender.Position.X, Direction.Down); } else if (Distance.X == -1 && Distance.Y == 1) { // Player is right and above chest. if (Current.PlayerCanMoveOut(sender, Direction.Left)) { Current.ShiftRow((int)sender.Position.X, Direction.Down); sender.MovePlayer(Direction.Left); } else if (Current.PlayerCanMoveOut(sender, Direction.Down)) { Current.ShiftRow((int)sender.Position.Y, Direction.Left); sender.MovePlayer(Direction.Down); } else Current.ShiftRow((int)sender.Position.X, Direction.Down); } else if (Distance.X == 1 && Distance.Y == -1) { // Player is left and below the chest. if (Current.PlayerCanMoveOut(sender, Direction.Right)) { Current.ShiftRow((int)sender.Position.X, Direction.Up); sender.MovePlayer(Direction.Right); } else if (Current.PlayerCanMoveOut(sender, Direction.Up)) { Current.ShiftRow((int)sender.Position.Y, Direction.Right); sender.MovePlayer(Direction.Up); } else Current.ShiftRow((int)sender.Position.X, Direction.Up); } else if (Distance.X == -1 && Distance.Y == -1) { // Player is right and below the chest. if (Current.PlayerCanMoveOut(sender, Direction.Left)) { Current.ShiftRow((int)sender.Position.X, Direction.Up); sender.MovePlayer(Direction.Left); } else if (Current.PlayerCanMoveOut(sender, Direction.Up)) { Current.ShiftRow((int)sender.Position.Y, Direction.Left); sender.MovePlayer(Direction.Up); } else Current.ShiftRow((int)sender.Position.X, Direction.Up); } }
private void ExecuteBestMove(Player sender, Vector2 Distance, bool SecondBest = false) { // Handle player being inline with the Chest. #region New Method : HandleZeroDistance // <<<<< if (SecondBest) if (HandleSameBlock(sender, Distance)) return; if (Distance.X == 0) { if (Distance.Y > 0) // Player has to move Down. HandleZeroDistance(sender, Distance, Direction.Down); else // Player has to move Up. HandleZeroDistance(sender, Distance, Direction.Up); return; } else if (Distance.Y == 0) { if (Distance.X > 0) // Player has to move Right. HandleZeroDistance(sender, Distance, Direction.Right); else // Player has to move Left. HandleZeroDistance(sender, Distance, Direction.Left); return; } if (Distance.X == 1 && Distance.Y == 1) { HandleLastMove(sender, Distance); return; } #endregion if (Distance.X > 0) { if (Distance.X != 1) { if (TryShiftRowAndMove(sender, Direction.Right)) return; if (SecondBest) { if (Current.PlayerCanMove(sender, Direction.Right)) { ExecuteCounter(sender, Direction.Right); sender.MovePlayer(Direction.Right); return; } else if (Current.CanShift((int)sender.Position.Y)) { // If second best, only move a row. Player can't move. Current.ShiftRow((int)sender.Position.Y, Direction.Right); return; } } } } else if (Distance.X < 0) { if (Distance.X != -1) { if (TryShiftRowAndMove(sender, Direction.Left)) return; if (SecondBest) { if (Current.PlayerCanMove(sender, Direction.Left)) { ExecuteCounter(sender, Direction.Left); sender.MovePlayer(Direction.Left); return; } else if (Current.CanShift((int)sender.Position.Y)) { Current.ShiftRow((int)sender.Position.Y, Direction.Left); return; } } } } if (Distance.Y > 0) { if (Distance.Y != 1) { if (TryShiftRowAndMove(sender, Direction.Down)) return; if (SecondBest) if (Current.PlayerCanMove(sender, Direction.Down)) { ExecuteCounter(sender, Direction.Down); sender.MovePlayer(Direction.Down); return; } else if (Current.CanShift((int)sender.Position.X)) { Current.ShiftRow((int)sender.Position.X, Direction.Down); return; } } } else if (Distance.Y < 0) { if (Distance.Y != 1) { if (TryShiftRowAndMove(sender, Direction.Up)) return; if (SecondBest) if (Current.PlayerCanMove(sender, Direction.Up)) { ExecuteCounter(sender, Direction.Up); sender.MovePlayer(Direction.Up); return; } else if (Current.CanShift((int)sender.Position.X)) { Current.ShiftRow((int)sender.Position.X, Direction.Up); return; } } } if (SecondBest) { // Worst possible move. Only obstruct other player. if (!RotateAdjacent(sender, Distance)) ExecuteCounter(sender); return; // Later implementation ? : // Annoy other player if you can move. // else rotate nearby and move. // else only rotate. } ExecuteBestMove(sender, Distance, true); }