From 5c70e41b76b4d8c64f048b3ee7b5b45f064551ac Mon Sep 17 00:00:00 2001 From: Kurt Date: Sun, 7 May 2023 13:34:47 -0700 Subject: [PATCH] Devirtualize GetMatchingSlots --- PKHeX.Core/Legality/Areas/EncounterArea.cs | 10 ---- PKHeX.Core/Legality/Areas/EncounterArea1.cs | 2 +- PKHeX.Core/Legality/Areas/EncounterArea2.cs | 2 +- PKHeX.Core/Legality/Areas/EncounterArea3.cs | 2 +- PKHeX.Core/Legality/Areas/EncounterArea3XD.cs | 2 +- PKHeX.Core/Legality/Areas/EncounterArea4.cs | 2 +- PKHeX.Core/Legality/Areas/EncounterArea5.cs | 2 +- PKHeX.Core/Legality/Areas/EncounterArea6AO.cs | 2 +- PKHeX.Core/Legality/Areas/EncounterArea6XY.cs | 2 +- PKHeX.Core/Legality/Areas/EncounterArea7.cs | 2 +- PKHeX.Core/Legality/Areas/EncounterArea7b.cs | 2 +- PKHeX.Core/Legality/Areas/EncounterArea7g.cs | 8 +-- PKHeX.Core/Legality/Areas/EncounterArea8.cs | 2 +- PKHeX.Core/Legality/Areas/EncounterArea8a.cs | 2 +- PKHeX.Core/Legality/Areas/EncounterArea8b.cs | 2 +- PKHeX.Core/Legality/Areas/EncounterArea8g.cs | 2 +- PKHeX.Core/Legality/Areas/EncounterArea9.cs | 2 +- .../ByGeneration/EncounterGenerator6.cs | 57 ++++++++++++------- 18 files changed, 55 insertions(+), 50 deletions(-) diff --git a/PKHeX.Core/Legality/Areas/EncounterArea.cs b/PKHeX.Core/Legality/Areas/EncounterArea.cs index dd31359d4..a041396be 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea.cs @@ -1,5 +1,3 @@ -using System.Collections.Generic; - namespace PKHeX.Core; /// @@ -10,14 +8,6 @@ public abstract record EncounterArea(GameVersion Version) : IVersion public int Location { get; protected init; } public SlotType Type { get; protected init; } - /// - /// Gets the slots contained in the area that match the provided data. - /// - /// Pokémon Data - /// Evolution lineage - /// Enumerable list of encounters - public abstract IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain); - /// /// Checks if the provided met location ID matches the parameters for the area. /// diff --git a/PKHeX.Core/Legality/Areas/EncounterArea1.cs b/PKHeX.Core/Legality/Areas/EncounterArea1.cs index 4245787ed..5021c8997 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea1.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea1.cs @@ -43,7 +43,7 @@ private EncounterArea1(ReadOnlySpan data, GameVersion game) : base(game) Slots = slots; } - public override IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) + public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) { (bool useCatchRate, byte rate) = pk is PK1 pk1 ? (true, pk1.Catch_Rate) : (false, (byte)0); foreach (var slot in Slots) diff --git a/PKHeX.Core/Legality/Areas/EncounterArea2.cs b/PKHeX.Core/Legality/Areas/EncounterArea2.cs index bc15f2981..589c4bf45 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea2.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea2.cs @@ -66,7 +66,7 @@ private EncounterSlot2[] ReadSlots(ReadOnlySpan data, int count) return slots; } - public override IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) + public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) { if (pk is not ICaughtData2 {CaughtData: not 0} pk2) return GetSlotsFuzzy(chain); diff --git a/PKHeX.Core/Legality/Areas/EncounterArea3.cs b/PKHeX.Core/Legality/Areas/EncounterArea3.cs index f84b5568c..779981382 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea3.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea3.cs @@ -110,7 +110,7 @@ private EncounterSlot3Swarm ReadSwarmSlot(ReadOnlySpan entry) return new EncounterSlot3Swarm(this, species, min, max, slotNum, moves); } - public override IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) + public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) { if (pk.Format != 3) // Met Location and Met Level are changed on PK3->PK4 return GetSlotsFuzzy(chain); diff --git a/PKHeX.Core/Legality/Areas/EncounterArea3XD.cs b/PKHeX.Core/Legality/Areas/EncounterArea3XD.cs index 49c53e28a..882fcdb69 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea3XD.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea3XD.cs @@ -23,7 +23,7 @@ public EncounterArea3XD(int loc, ushort s0, byte l0, ushort s1, byte l1, ushort }; } - public override IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) + public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) { if (pk.Format != 3) // Met Location and Met Level are changed on PK3->PK4 return GetSlotsFuzzy(chain); diff --git a/PKHeX.Core/Legality/Areas/EncounterArea4.cs b/PKHeX.Core/Legality/Areas/EncounterArea4.cs index a22aee1ed..758ca38d6 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea4.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea4.cs @@ -62,7 +62,7 @@ private EncounterSlot4 ReadRegularSlot(ReadOnlySpan entry) return new EncounterSlot4(this, species, form, min, max, slotNum, mpi, mpc, sti, stc); } - public override IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) + public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) { if (pk.Format != 4) // Met Location and Met Level are changed on PK4->PK5 return GetSlotsFuzzy(chain); diff --git a/PKHeX.Core/Legality/Areas/EncounterArea5.cs b/PKHeX.Core/Legality/Areas/EncounterArea5.cs index 31c0a668d..b16dc9a54 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea5.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea5.cs @@ -53,7 +53,7 @@ private EncounterSlot5 ReadSlot(ReadOnlySpan entry) return new EncounterSlot5(this, species, form, min, max); } - public override IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) + public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) { foreach (var slot in Slots) { diff --git a/PKHeX.Core/Legality/Areas/EncounterArea6AO.cs b/PKHeX.Core/Legality/Areas/EncounterArea6AO.cs index d43f00b57..d7eec4204 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea6AO.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea6AO.cs @@ -57,7 +57,7 @@ private EncounterSlot6AO ReadSlot(ReadOnlySpan entry) private const int FluteBoostMax = 4; // Black Flute increases levels. private const int DexNavBoost = 30; // Maximum DexNav chain - public override IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) + public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) { foreach (var slot in Slots) { diff --git a/PKHeX.Core/Legality/Areas/EncounterArea6XY.cs b/PKHeX.Core/Legality/Areas/EncounterArea6XY.cs index 3a0d53bae..29affb0df 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea6XY.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea6XY.cs @@ -105,7 +105,7 @@ private EncounterSlot6XY[] ReadSlots(ReadOnlySpan data) return slots; } - public override IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) + public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) { foreach (var slot in Slots) { diff --git a/PKHeX.Core/Legality/Areas/EncounterArea7.cs b/PKHeX.Core/Legality/Areas/EncounterArea7.cs index 469307a1a..85fcc149e 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea7.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea7.cs @@ -53,7 +53,7 @@ private EncounterSlot7 ReadSlot(ReadOnlySpan entry) return new EncounterSlot7(this, species, form, min, max); } - public override IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) + public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) { foreach (var slot in Slots) { diff --git a/PKHeX.Core/Legality/Areas/EncounterArea7b.cs b/PKHeX.Core/Legality/Areas/EncounterArea7b.cs index 59d62336e..b5649e0e9 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea7b.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea7b.cs @@ -52,7 +52,7 @@ private EncounterSlot7b ReadSlot(ReadOnlySpan entry) private const int CatchComboBonus = 1; - public override IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) + public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) { foreach (var slot in Slots) { diff --git a/PKHeX.Core/Legality/Areas/EncounterArea7g.cs b/PKHeX.Core/Legality/Areas/EncounterArea7g.cs index 1a82342f9..d7e317800 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea7g.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea7g.cs @@ -66,11 +66,8 @@ private static EncounterSlot7GO ReadSlot(ReadOnlySpan entry, EncounterArea return new EncounterSlot7GO(area, species, form, start, end, shiny, gender, type); } - public override IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) + public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) { - // Find the first chain that has slots defined. - // Since it is possible to evolve before transferring, we only need the highest evolution species possible. - // PoGoEncTool has already extrapolated the evolutions to separate encounters! var sf = Array.Find(chain, z => z.Species == Species && z.Form == Form); if (sf == default) return Array.Empty(); @@ -80,6 +77,9 @@ public override IEnumerable GetMatchingSlots(PKM pk, EvoCriter public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria evo) { + // Find the first chain that has slots defined. + // Since it is possible to evolve before transferring, we only need the highest evolution species possible. + // PoGoEncTool has already extrapolated the evolutions to separate encounters! var stamp = EncounterSlotGO.GetTimeStamp(pk.Met_Year + 2000, pk.Met_Month, pk.Met_Day); var met = Math.Max(evo.LevelMin, pk.Met_Level); EncounterSlot7GO? deferredIV = null; diff --git a/PKHeX.Core/Legality/Areas/EncounterArea8.cs b/PKHeX.Core/Legality/Areas/EncounterArea8.cs index e6b53e8e3..9fc80199c 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea8.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea8.cs @@ -38,7 +38,7 @@ public override bool IsMatchLocation(int location) return Array.IndexOf(others, (byte)location) != -1; } - public override IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) + public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) { var metLocation = pk.Met_Location; // wild area gets boosted up to level 60 post-game diff --git a/PKHeX.Core/Legality/Areas/EncounterArea8a.cs b/PKHeX.Core/Legality/Areas/EncounterArea8a.cs index bdb291864..e9d960962 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea8a.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea8a.cs @@ -18,7 +18,7 @@ public override bool IsMatchLocation(int location) return Array.IndexOf(Locations, (byte)location) != -1; } - public override IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) => GetMatches(chain, pk.Met_Level); + public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) => GetMatches(chain, pk.Met_Level); private IEnumerable GetMatches(EvoCriteria[] chain, int metLevel) { diff --git a/PKHeX.Core/Legality/Areas/EncounterArea8b.cs b/PKHeX.Core/Legality/Areas/EncounterArea8b.cs index ffd0046c3..d1f8f8210 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea8b.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea8b.cs @@ -79,7 +79,7 @@ private bool CanCrossoverTo(int location) return false; } - public override IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) + public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) { foreach (var slot in Slots) { diff --git a/PKHeX.Core/Legality/Areas/EncounterArea8g.cs b/PKHeX.Core/Legality/Areas/EncounterArea8g.cs index 33bded4a4..ee5ffa0ce 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea8g.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea8g.cs @@ -66,7 +66,7 @@ private static EncounterSlot8GO ReadSlot(ReadOnlySpan entry, EncounterArea return new EncounterSlot8GO(area, species, form, start, end, shiny, gender, type, format); } - public override IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) + public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) { // Find the first chain that has slots defined. // Since it is possible to evolve before transferring, we only need the highest evolution species possible. diff --git a/PKHeX.Core/Legality/Areas/EncounterArea9.cs b/PKHeX.Core/Legality/Areas/EncounterArea9.cs index f13a8ebc9..7e6cf60a7 100644 --- a/PKHeX.Core/Legality/Areas/EncounterArea9.cs +++ b/PKHeX.Core/Legality/Areas/EncounterArea9.cs @@ -49,7 +49,7 @@ private EncounterSlot9[] ReadSlots(ReadOnlySpan areaData) return result; } - public override IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) + public IEnumerable GetMatchingSlots(PKM pk, EvoCriteria[] chain) { var lvl = pk.Met_Level; foreach (var slot in Slots) diff --git a/PKHeX.Core/Legality/Encounters/Generator/ByGeneration/EncounterGenerator6.cs b/PKHeX.Core/Legality/Encounters/Generator/ByGeneration/EncounterGenerator6.cs index 56f04465e..4351a8163 100644 --- a/PKHeX.Core/Legality/Encounters/Generator/ByGeneration/EncounterGenerator6.cs +++ b/PKHeX.Core/Legality/Encounters/Generator/ByGeneration/EncounterGenerator6.cs @@ -222,21 +222,45 @@ public IEnumerable GetEncounters(PKM pk, EvoCriteria[] chain, Le if (CanBeWildEncounter(pk)) { var location = pk.Met_Location; - var areas = GetAreas(game); - foreach (var area in areas) + if (game is GameVersion.X or GameVersion.Y) { - if (!area.IsMatchLocation(location)) - continue; - - var slots = area.GetMatchingSlots(pk, chain); - foreach (var slot in slots) + var areas = game == GameVersion.X ? Encounters6XY.SlotsX : Encounters6XY.SlotsY; + foreach (var area in areas) { - var match = slot.GetMatchRating(pk); - switch (match) + if (!area.IsMatchLocation(location)) + continue; + + var slots = area.GetMatchingSlots(pk, chain); + foreach (var slot in slots) { - case Match: yield return slot; yielded = true; break; - case Deferred: deferred ??= slot; break; - case PartialMatch: partial ??= slot; break; + var match = slot.GetMatchRating(pk); + switch (match) + { + case Match: yield return slot; yielded = true; break; + case Deferred: deferred ??= slot; break; + case PartialMatch: partial ??= slot; break; + } + } + } + } + else if (game is GameVersion.AS or GameVersion.OR) + { + var areas = game == GameVersion.AS ? Encounters6AO.SlotsA : Encounters6AO.SlotsO; + foreach (var area in areas) + { + if (!area.IsMatchLocation(location)) + continue; + + var slots = area.GetMatchingSlots(pk, chain); + foreach (var slot in slots) + { + var match = slot.GetMatchRating(pk); + switch (match) + { + case Match: yield return slot; yielded = true; break; + case Deferred: deferred ??= slot; break; + case PartialMatch: partial ??= slot; break; + } } } } @@ -282,15 +306,6 @@ public IEnumerable GetEncounters(PKM pk, EvoCriteria[] chain, Le _ => throw new ArgumentOutOfRangeException(nameof(gameSource), gameSource, null), }; - private static EncounterArea[] GetAreas(GameVersion gameSource) => gameSource switch - { - GameVersion.X => Encounters6XY.SlotsX, - GameVersion.Y => Encounters6XY.SlotsY, - GameVersion.AS => Encounters6AO.SlotsA, - GameVersion.OR => Encounters6AO.SlotsO, - _ => throw new ArgumentOutOfRangeException(nameof(gameSource), gameSource, null), - }; - private static EncounterTrade6[] GetTrades(GameVersion gameSource) => gameSource switch { GameVersion.X => Encounters6XY.TradeGift_XY,