From 7e93bcfb61d5fcdfc13e61e4dc78d49936b613d7 Mon Sep 17 00:00:00 2001 From: Kurt Date: Thu, 29 Oct 2020 19:11:03 -0700 Subject: [PATCH] Handle contest ribbon deadlock scenario Contest Star needs all 5 ribbons; all 5 ribbons require contest star. Incrementally adding will fail on the last ribbon. Try setting both at the end. When removing ribbons, attempt to remove the pair first, as the incremental removal will fail each time (contest star last). #3061 --- .../Editing/Applicators/RibbonApplicator.cs | 32 +++++++++++++++++-- 1 file changed, 29 insertions(+), 3 deletions(-) diff --git a/PKHeX.Core/Editing/Applicators/RibbonApplicator.cs b/PKHeX.Core/Editing/Applicators/RibbonApplicator.cs index 97aa620c9..6c47f4519 100644 --- a/PKHeX.Core/Editing/Applicators/RibbonApplicator.cs +++ b/PKHeX.Core/Editing/Applicators/RibbonApplicator.cs @@ -90,6 +90,10 @@ private static IReadOnlyList SetAllValidRibbons(IList allRibbons // Repeat the operation until no more ribbons are set. } + // Ribbon Deadlock + if (pk is IRibbonSetCommon6 c6) + InvertDeadlockContest(c6, la, true); + return valid; } @@ -121,6 +125,10 @@ private static IReadOnlyList RemoveAllValidRibbons(IList allRibb var la = new LegalityAnalysis(pk); var valid = new List(); + // Ribbon Deadlock + if (pk is IRibbonSetCommon6 c6) + InvertDeadlockContest(c6, la, false); + while (TryRemoveAllRibbons(pk, la, allRibbons, valid) != 0) { // Repeat the operation until no more ribbons are set. @@ -182,13 +190,17 @@ private static int TryRemoveAllRibbons(PKM pk, LegalityAnalysis la, IList z.Valid); + return UpdateIsValid(la); } private static bool TryApplyRibbon(PKM pk, LegalityAnalysis la, string rib) { SetRibbonValue(pk, rib, 1); + return UpdateIsValid(la); + } + + private static bool UpdateIsValid(LegalityAnalysis la) + { LegalityAnalysis.Ribbon.Verify(la); return la.Results.All(z => z.Valid); } @@ -211,5 +223,19 @@ private static void SetRibbonValue(PKM pk, string rib, int value) break; } } + + private static void InvertDeadlockContest(IRibbonSetCommon6 c6, LegalityAnalysis la, bool desiredState) + { + // RibbonContestStar depends on having all contest ribbons, and having RibbonContestStar requires all. + // Since the above logic sets individual ribbons, we must try setting this deadlock pair manually. + if (c6.RibbonMasterToughness == desiredState || c6.RibbonContestStar == desiredState) + return; + + la.ResetParse(); + c6.RibbonMasterToughness = c6.RibbonContestStar = desiredState; + bool result = UpdateIsValid(la); + if (!result) + c6.RibbonMasterToughness = c6.RibbonContestStar = !desiredState; + } } -} \ No newline at end of file +}