diff --git a/src/Battle.Logic/CharacterCover/Cover.cs b/src/Battle.Logic/CharacterCover/Cover.cs index c758ea88..71a906a1 100644 --- a/src/Battle.Logic/CharacterCover/Cover.cs +++ b/src/Battle.Logic/CharacterCover/Cover.cs @@ -200,19 +200,19 @@ private static List FindAdjacentCover(Vector3 currentLocation, int widt } //Get possible tiles, within constraints of map, including only square titles from current position (not diagonally) - if (validTiles[Convert.ToInt32(currentLocation.X), Convert.ToInt32(zMax)] == CoverType.FullCover) + if (validTiles[Convert.ToInt32(currentLocation.X), zMax] == CoverType.FullCover || validTiles[Convert.ToInt32(currentLocation.X), zMax] == CoverType.HalfCover) { result.Add(new Vector3(currentLocation.X, 0f, zMax)); } - if (validTiles[Convert.ToInt32(xMax), Convert.ToInt32(currentLocation.Z)] == CoverType.FullCover) + if (validTiles[xMax, Convert.ToInt32(currentLocation.Z)] == CoverType.FullCover || validTiles[xMax, Convert.ToInt32(currentLocation.Z)] == CoverType.HalfCover) { result.Add(new Vector3(xMax, 0f, currentLocation.Z)); } - if (validTiles[Convert.ToInt32(currentLocation.X), Convert.ToInt32(zMin)] == CoverType.FullCover) + if (validTiles[Convert.ToInt32(currentLocation.X), zMin] == CoverType.FullCover|| validTiles[Convert.ToInt32(currentLocation.X), zMin] == CoverType.HalfCover) { result.Add(new Vector3(currentLocation.X, 0f, zMin)); } - if (validTiles[Convert.ToInt32(xMin), Convert.ToInt32(currentLocation.Z)] == CoverType.FullCover) + if (validTiles[xMin, Convert.ToInt32(currentLocation.Z)] == CoverType.FullCover|| validTiles[xMin, Convert.ToInt32(currentLocation.Z)] == CoverType.HalfCover) { result.Add(new Vector3(xMin, 0f, currentLocation.Z)); } diff --git a/src/Battle.Logic/CharacterCover/CoverType.cs b/src/Battle.Logic/CharacterCover/CoverType.cs index 1b482654..5dbb54a5 100644 --- a/src/Battle.Logic/CharacterCover/CoverType.cs +++ b/src/Battle.Logic/CharacterCover/CoverType.cs @@ -2,7 +2,7 @@ { public static class CoverType { - public const string FullCover = "■"; + public const string FullCover = "■"; public const string HalfCover = "▪"; public const string NoCover = "□"; //▫ diff --git a/src/Battle.Logic/Characters/Experience.cs b/src/Battle.Logic/Characters/Experience.cs new file mode 100644 index 00000000..365214f7 --- /dev/null +++ b/src/Battle.Logic/Characters/Experience.cs @@ -0,0 +1,102 @@ +namespace Battle.Logic.Characters +{ + public static class Experience + { + //Experience + // 0xp for miss + // 10xp for hit + // 100xp for kill + + //Rank Enemy Unknown + //1. Rookie 0 + //2. Squaddie 100 + //3. Corporal 500 + //4. Sergeant 1000 + //5. Lieutenant 1500 + //6. Captain 2000 + //7. Major 2500 + //8. Colonel 3000 + private const int Level2ExperienceNeeded = 100; + private const int Level3ExperienceNeeded = 500; + private const int Level4ExperienceNeeded = 1000; + private const int Level5ExperienceNeeded = 1500; + private const int Level6ExperienceNeeded = 2000; + private const int Level7ExperienceNeeded = 2500; + private const int Level8ExperienceNeeded = 3000; + + private const int SuccessfulAction = 10; + private const int KillXP = 100; + + public static int GetExperience(bool successfulAction, bool successfulKill = false) + { + //hit + if (successfulAction == true) + { + if (successfulKill == true) + { + return KillXP; + } + else + { + return SuccessfulAction; + } + } + else + { + return 0; + } + } + + public static bool CheckIfReadyToLevelUp(int level, int experience) + { + bool result = false; + switch (level) + { + case 1: + if (experience >= Level2ExperienceNeeded) + { + result = true; + } + break; + case 2: + if (experience >= Level3ExperienceNeeded) + { + result = true; + } + break; + case 3: + if (experience >= Level4ExperienceNeeded) + { + result = true; + } + break; + case 4: + if (experience >= Level5ExperienceNeeded) + { + result = true; + } + break; + case 5: + if (experience >= Level6ExperienceNeeded) + { + result = true; + } + break; + case 6: + if (experience >= Level7ExperienceNeeded) + { + result = true; + } + break; + case 7: + if (experience >= Level8ExperienceNeeded) + { + result = true; + } + break; + + } + return result; + } + } +} diff --git a/src/Battle.Logic/Encounters/Encounter.cs b/src/Battle.Logic/Encounters/Encounter.cs index 7b536251..60d534b2 100644 --- a/src/Battle.Logic/Encounters/Encounter.cs +++ b/src/Battle.Logic/Encounters/Encounter.cs @@ -51,7 +51,7 @@ public static EncounterResult AttackCharacterWithAreaOfEffect(Character sourceCh List area = FieldOfViewAreaEffectCalculator.GetAreaOfEffect(map, throwingTargetLocation, weapon.AreaEffectRadius); foreach (Vector3 item in area) { - if (map[(int)item.X, (int)item.Z] == CoverType.FullCover) + if (map[(int)item.X, (int)item.Z] == CoverType.FullCover || map[(int)item.X, (int)item.Z] == CoverType.HalfCover) { map[(int)item.X, (int)item.Z] = ""; log.Add("Cover removed from " + item.ToString()); diff --git a/src/Battle.Logic/Encounters/Experience.cs b/src/Battle.Logic/Encounters/Experience.cs deleted file mode 100644 index fdf6dde3..00000000 --- a/src/Battle.Logic/Encounters/Experience.cs +++ /dev/null @@ -1,65 +0,0 @@ -namespace Battle.Logic.Encounters -{ - public static class Experience - { - //Experience - // 10xp for hit - // 0xp for miss (TODO: consider this - is this fair? Don't you still learn when you fail?) - // 100xp for kill - - //Rank Enemy Unknown - //Squaddie 100 - //Corporal 500 - //Sergeant 1000 - //Lieutenant 1500 - //Captain 2000 - //Major 2500 - //Colonel 3000 - private const int Level1ExperienceUp = 100; - //private const int Level2ExperienceUp = 500; - //private const int Level3ExperienceUp = 1000; - //private const int Level4ExperienceUp = 1500; - //private const int Level5ExperienceUp = 2000; - //private const int Level6ExperienceUp = 2500; - //private const int Level7ExperienceUp = 3000; - - private const int SuccessfulAction = 10; - private const int KillXP = 100; - - public static int GetExperience(bool successfulAction, bool successfulKill = false) - { - //hit - if (successfulAction == true) - { - if (successfulKill == true) - { - return KillXP; - } - else - { - return SuccessfulAction; - } - } - else - { - return 0; - } - } - - public static bool CheckIfReadyToLevelUp(int level, int experience) - { - bool result = false; - switch (level) - { - case 1: - if (experience >= Level1ExperienceUp) - { - result= true; - } - break; - - } - return result; - } - } -} diff --git a/src/Battle.Logic/FieldOfView/FieldOfViewCalculator.cs b/src/Battle.Logic/FieldOfView/FieldOfViewCalculator.cs index cb9341e1..43c289f5 100644 --- a/src/Battle.Logic/FieldOfView/FieldOfViewCalculator.cs +++ b/src/Battle.Logic/FieldOfView/FieldOfViewCalculator.cs @@ -1,4 +1,5 @@ -using System; +using Battle.Logic.CharacterCover; +using System; using System.Collections.Generic; using System.Linq; using System.Numerics; @@ -70,7 +71,7 @@ public static List GetFieldOfView(string[,] map, Vector3 location, int currentLength += lineSegment; Vector3 fovItem = singleLineCheck[i]; //If we find an object, stop adding tiles - if (map[(int)fovItem.X, (int)fovItem.Z] != "") + if (map[(int)fovItem.X, (int)fovItem.Z] == CoverType.FullCover) { break; } diff --git a/src/Battle.Logic/Map/MapItem.cs b/src/Battle.Logic/Map/MapItem.cs new file mode 100644 index 00000000..a7157d18 --- /dev/null +++ b/src/Battle.Logic/Map/MapItem.cs @@ -0,0 +1,10 @@ +namespace Battle.Logic.Map +{ + public class MapItem + { + public string Name { get; set; } + public int HitPoints { get; set; } + public bool IsBurnable { get; set; } + public bool IsExplosive { get; set; } + } +} diff --git a/src/Battle.Tests/Characters/CharacterExperienceTests.cs b/src/Battle.Tests/Characters/CharacterExperienceTests.cs new file mode 100644 index 00000000..23092d4c --- /dev/null +++ b/src/Battle.Tests/Characters/CharacterExperienceTests.cs @@ -0,0 +1,134 @@ +using Battle.Logic.AbilitiesAndEffects; +using Battle.Logic.Characters; +using Microsoft.VisualStudio.TestTools.UnitTesting; +using System.Collections.Generic; +using System.Numerics; + +namespace Battle.Tests.Characters +{ + [TestClass] + [TestCategory("L0")] + public class CharacterExperienceTests + { + [TestMethod] + public void CharacterFredLevel1To2XPTest() + { + //Arrange + Character fred = CharacterPool.CreateFredHero(); + fred.Experience = 100; + fred.Level = 1; + + //Act + bool readyToLevelUp = Experience.CheckIfReadyToLevelUp(fred.Level, fred.Experience); + + //Assert + Assert.AreEqual(true, readyToLevelUp); + } + + [TestMethod] + public void CharacterFredLevel2To3XPTest() + { + //Arrange + Character fred = CharacterPool.CreateFredHero(); + fred.Experience = 500; + fred.Level = 2; + + //Act + bool readyToLevelUp = Experience.CheckIfReadyToLevelUp(fred.Level, fred.Experience); + + //Assert + Assert.AreEqual(true, readyToLevelUp); + } + + [TestMethod] + public void CharacterFredLevel3To4XPTest() + { + //Arrange + Character fred = CharacterPool.CreateFredHero(); + fred.Experience = 1000; + fred.Level = 3; + + //Act + bool readyToLevelUp = Experience.CheckIfReadyToLevelUp(fred.Level, fred.Experience); + + //Assert + Assert.AreEqual(true, readyToLevelUp); + } + + [TestMethod] + public void CharacterFredLevel4To5XPTest() + { + //Arrange + Character fred = CharacterPool.CreateFredHero(); + fred.Experience = 1500; + fred.Level = 4; + + //Act + bool readyToLevelUp = Experience.CheckIfReadyToLevelUp(fred.Level, fred.Experience); + + //Assert + Assert.AreEqual(true, readyToLevelUp); + } + + [TestMethod] + public void CharacterFredLevel5To6XPTest() + { + //Arrange + Character fred = CharacterPool.CreateFredHero(); + fred.Experience = 2000; + fred.Level = 5; + + //Act + bool readyToLevelUp = Experience.CheckIfReadyToLevelUp(fred.Level, fred.Experience); + + //Assert + Assert.AreEqual(true, readyToLevelUp); + } + + [TestMethod] + public void CharacterFredLevel6To7XPTest() + { + //Arrange + Character fred = CharacterPool.CreateFredHero(); + fred.Experience = 2500; + fred.Level = 6; + + //Act + bool readyToLevelUp = Experience.CheckIfReadyToLevelUp(fred.Level, fred.Experience); + + //Assert + Assert.AreEqual(true, readyToLevelUp); + } + + [TestMethod] + public void CharacterFredLevel7To8XPFailTest() + { + //Arrange + Character fred = CharacterPool.CreateFredHero(); + fred.Experience = 3000-1; + fred.Level = 7; + + //Act + bool readyToLevelUp = Experience.CheckIfReadyToLevelUp(fred.Level, fred.Experience); + + //Assert + Assert.AreEqual(false, readyToLevelUp); + } + + [TestMethod] + public void CharacterFredLevel7To8XPTest() + { + //Arrange + Character fred = CharacterPool.CreateFredHero(); + fred.Experience = 3000; + fred.Level = 7; + + //Act + bool readyToLevelUp = Experience.CheckIfReadyToLevelUp(fred.Level, fred.Experience); + + //Assert + Assert.AreEqual(true, readyToLevelUp); + } + + } +} diff --git a/src/Battle.Tests/FieldOfView/CharacterFieldOfViewTests.cs b/src/Battle.Tests/FieldOfView/CharacterFieldOfViewTests.cs index 54028e7d..7b2c7aa8 100644 --- a/src/Battle.Tests/FieldOfView/CharacterFieldOfViewTests.cs +++ b/src/Battle.Tests/FieldOfView/CharacterFieldOfViewTests.cs @@ -301,6 +301,41 @@ public void JeffCannotSeeFredTest() Assert.AreEqual(mapResult, mapString); } + [TestMethod] + public void JeffCanSeeFredTest() + { + //Arrange + Character fred = CharacterPool.CreateFredHero(); + Character jeff = CharacterPool.CreateJeffBaddie(); + string[,] map = MapUtility.InitializeMap(10, 10); + map[7, 7] = CoverType.HalfCover; + map[8, 7] = CoverType.FullCover; + map[9, 7] = CoverType.FullCover; + Team teamGood = new(); + teamGood.Characters.Add(fred); + + //Act + string mapString = jeff.GetCharactersInViewMapString(map, new List { teamGood }); + List characters = jeff.GetCharactersInView(map, new List { teamGood }); + + //Assert + Assert.IsTrue(characters != null); + Assert.AreEqual(1, characters.Count); + string mapResult = @" +o o o o o o o o o o +o o o o o o o o P o +o o o o o o o ▪ ■ ■ +o o o o o o o o □ □ +o o o o o o o □ □ □ +o o o o o o o □ □ □ +o o o o o o □ □ □ □ +o o o o o o □ □ □ □ +o o o o o □ □ □ □ □ +P o o o o □ □ □ □ □ +"; + Assert.AreEqual(mapResult, mapString); + } + [TestMethod] public void FredShouldSeeJeffInCoverTest() {