Mage: C19 - Commander 2019 Set Card Implementation Tracking

Created on 2 Aug 2019  路  19Comments  路  Source: magefree/mage

Mark cards you're working on in the second post of this issue.
If you can't check things off, leave a comment instead.
Once the card is committed, check off the card here to show that it's finished.
Don't worry about adding new spoilers to this list, it's generated by a script.

All Sets

Unimplemented Cards

Click to expand

tracking set

All 19 comments

No other tasks currently

Created pull request for Empowered Autogenerator

  • [x] Rayami, First of the Fallen - Rayami doesn't exile creatures - Rayami's exile ability doesnt work (mininine, 2019-09-10 06:44:03) Rayami's exile part doesnt work most of the time, the only time i worked was when he also died (mininine, 2019-09-10 07:04:59)

  • [x] Gift of Doom - does literally nothing btw... you untransform it and it immediately dies (reddit);

  • [x] Gift of Doom (from Commander 2019) seems to be bugged. Once you've sacrificed your creature as a cost it doesn't resolve or ask you a target for the enchantment and it goes directly in the graveyard (forum).

  • [x] Sevinne, the Chronoclasm

java.lang.IndexOutOfBoundsException: Index: 0, Size: 0
        at java.util.ArrayList.rangeCheck(ArrayList.java:657)
        at java.util.ArrayList.get(ArrayList.java:433)
        at mage.abilities.common.SpellCastControllerTriggeredAbility.checkTrigger(SpellCastControllerTriggeredAbility.java:70)
        at mage.cards.s.SevinneTheChronoclasmTriggeredAbility.checkTrigger(SevinneTheChronoclasm.java:66)
        at mage.abilities.TriggeredAbilities.checkTrigger(TriggeredAbilities.java:94)
        at mage.abilities.TriggeredAbilities.checkTriggers(TriggeredAbilities.java:51)
        at mage.game.GameState.handleEvent(GameState.java:705)
        at mage.game.GameImpl.fireEvent(GameImpl.java:2597)
        at mage.players.PlayerImpl.cast(PlayerImpl.java:1131)
        at mage.players.PlayerImpl.activateAbility(PlayerImpl.java:1346)
        at mage.player.human.HumanPlayer.activateAbility(HumanPlayer.java:1685)
        at mage.player.human.HumanPlayer.activateAbility(HumanPlayer.java:1699)
        at mage.player.human.HumanPlayer.priority(HumanPlayer.java:956)
        at mage.game.GameImpl.playPriority(GameImpl.java:1248)
        at mage.game.turn.Step.priority(Step.java:61)
        at mage.game.turn.Phase.playStep(Phase.java:184)
        at mage.game.turn.Phase.play(Phase.java:89)
        at mage.game.turn.Turn.play(Turn.java:126)
        at mage.game.GameImpl.playTurn(GameImpl.java:850)
        at mage.game.GameImpl.play(GameImpl.java:759)
        at mage.game.GameImpl.start(GameImpl.java:723)
        at mage.server.game.GameWorker.call(GameWorker.java:34)
        at java.util.concurrent.FutureTask.run(FutureTask.java:266)
        at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
        at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
        at java.lang.Thread.run(Thread.java:748)
  • [x] Elsha of the Infinite
java.lang.NullPointerException
    at mage.cards.e.ElshaOfTheInfinitePredicate.apply(ElshaOfTheInfinite.java:82)
    at mage.cards.e.ElshaOfTheInfinitePredicate.apply(ElshaOfTheInfinite.java:76)
    at mage.filter.predicate.Predicates$AndPredicate.lambda$apply$0(Predicates.java:145)
    at java.util.stream.MatchOps$1MatchSink.accept(MatchOps.java:90)
    at java.util.ArrayList$ArrayListSpliterator.tryAdvance(ArrayList.java:1359)
    at java.util.stream.ReferencePipeline.forEachWithCancel(ReferencePipeline.java:126)
    at java.util.stream.AbstractPipeline.copyIntoWithCancel(AbstractPipeline.java:498)
    at java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:485)
    at java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:471)
    at java.util.stream.MatchOps$MatchOp.evaluateSequential(MatchOps.java:230)
    at java.util.stream.MatchOps$MatchOp.evaluateSequential(MatchOps.java:196)
    at java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)
    at java.util.stream.ReferencePipeline.allMatch(ReferencePipeline.java:454)
    at mage.filter.predicate.Predicates$AndPredicate.apply(Predicates.java:145)
    at mage.filter.FilterImpl.match(FilterImpl.java:38)
    at mage.filter.FilterCard.match(FilterCard.java:51)
    at mage.abilities.effects.common.continuous.PlayTheTopCardEffect.applies(PlayTheTopCardEffect.java:55)
    at mage.abilities.effects.ContinuousEffects.asThough(ContinuousEffects.java:522)
    at mage.players.PlayerImpl.getPlayable(PlayerImpl.java:3178)
    at mage.players.PlayerImpl.getPlayableObjects(PlayerImpl.java:3288)
    at mage.server.game.GameSessionPlayer.getGameView(GameSessionPlayer.java:192)
    at mage.server.game.GameSessionWatcher.lambda$update$0(GameSessionWatcher.java:54)
    at java.util.Optional.ifPresent(Optional.java:159)
    at mage.server.game.GameSessionWatcher.update(GameSessionWatcher.java:54)
    at mage.server.game.GameController.updateGame(GameController.java:732)
    at mage.server.game.GameController.lambda$init$3aa0d15c$1(GameController.java:119)
    at mage.game.events.EventDispatcher.fireEvent(EventDispatcher.java:30)
    at mage.game.events.TableEventSource.fireTableEvent(TableEventSource.java:41)
    at mage.game.GameImpl.fireUpdatePlayersEvent(GameImpl.java:2340)
    at mage.server.game.GameWorker.call(GameWorker.java:35)
  • [x] Leadership Vacuum
java.lang.UnsupportedOperationException: to ZoneCOMMAND not supported yet
    at mage.players.PlayerImpl.moveCards(PlayerImpl.java:3735)
    at mage.players.PlayerImpl.moveCards(PlayerImpl.java:3650)
    at mage.cards.l.LeadershipVacuumEffect.apply(LeadershipVacuum.java:74)
    at mage.abilities.AbilityImpl.resolveMode(AbilityImpl.java:176)
    at mage.abilities.AbilityImpl.resolve(AbilityImpl.java:166)
    at mage.game.stack.Spell.resolve(Spell.java:217)
    at mage.game.GameImpl.resolve(GameImpl.java:1319)
    at mage.game.GameImpl.playPriority(GameImpl.java:1269)
    at mage.game.turn.Step.priority(Step.java:61)
    at mage.game.turn.Phase.playStep(Phase.java:184)
    at mage.game.turn.Phase.play(Phase.java:89)
    at mage.game.turn.Turn.play(Turn.java:126)
    at mage.game.GameImpl.playTurn(GameImpl.java:850)
    at mage.game.GameImpl.play(GameImpl.java:759)
    at mage.game.GameImpl.start(GameImpl.java:723)
    at mage.server.game.GameWorker.call(GameWorker.java:34)

Multiple exception errors added after latest release 38v0

oh joy, looks like I've got my work cut out for me

@theelk801 do you plan to fix exception errors above?

I do, I just haven't gotten to them yet.

Hi, what is the current state of this?

So I got "K'rrik, Son of Yawgmoth" semi-working? You can pay Phyrexian for him, he has lifelink, he gets +1/+1 counters when you cast black spells, and he lets you pay Phyrexian for your other black costs, both in spells and abilities.

The problem is my solution is probably a bit hacky. As a result, you can still pay Phyrexian for black costs even after he leaves the battlefield.

Should I commit my changes anyway so someone else can see what I might be doing wrong?

i think i am almost done with Aeon Engine, but i have an issue, details here:
https://www.slightlymagic.net/forum/viewtopic.php?f=70&t=29099
any idea what might be causing this?
perhaps my change to the pass turn mechanic?

@algeee nope, that's not full implementation. You've got idea, but there are many places to fix.

  1. Changeable data like turn order must be stored in GameState, not Game object (rollback replaces GameState objects and don't change Game). AI simulates/plays multiple actions before choose (that's the reason of your bug maybe -- Game object changed in one of the simulated turns).
  1. XMage copy objects all around -- you must check your Game/GameState object and ensure about new field copy in one/many constructors (search another field to find copy code in class).

  2. You must replace uses of getNext() to getNext(game). Same for getPrevious().
    shot_191121_142224

  3. Moreover some code with getNext uses:

    • physical left/right, independent from turn order (Aminatou, the Fateshifter -- Choose left or right. ...controlled by the next player in the chosen direction)
    • logical left/right, depends on turn order (Kynaios and Tiro of Meletis -- Starting with you, each player may put...).
  4. That's why all getNext() and getNext(game) calls can be replaced with getNext(Game game, boolean dependsOnTurnOrder)

  5. After search and replace that code you can find possible use cases to test (like game cards, effects or other situations).

oh well, i should have known, couldn't be that easy xD
i got my initial idea from Fateshifter, but it didn't come to my mind to use GameState to store the turn order state, which would also make sense terminology wise.
but i think i am at least some steps closer, storing turnOrder in GameState fixed my issue, the card appears to be working correctly now.
It enters tapped, and if i tap it, it get's exiled and turn order is reversed.
I also did all the other changes you suggested.

However, the card only works when i actually test this in a match, i can't get the test class to work, apparently the ability is not activated.. the ability string i pass does match what i see ingame for the ability. do i have to escape some characters?

test class is attached as text file.

the error i get:
(Exile PlayerA) Card counts are not equal (Aeon Engine expected: <1> but was: <0>
the card also doesn't get tapped or turn order altered, so something must be wrong with the activateAbility call.

AeonEngineTest.txt

@algeee

  1. You must use multiplayer tests, not two player (CardTestMultiPlayerBase instead CardTestPlayerBase). In two player game turn order is unaffected;
  2. You don't need to call full ability text -- just enter start of the text. You can find available abilities by command: showAvaileableAbilities("before", 1, PhaseStep.PRECOMBAT_MAIN, playerA);. If you changed ability/card text then you must delete all cards.h2.mv.db files (Mage.Tests\db for tests and other folders for client/server) to re-create database.
  3. Use extra test commands:

    • setStrictChooseMode(true); before execute -- if you missing choose command then test will raise error (in non strict mode AI will play that command, e.g. random);

    • assertAllCommandsUsed(); after execute -- ensure that all your test commands was used (if you calls ability and game do not allows it then that's command will be unused and that's check will raise error).

  4. There are many real time checks like checkPermanentCount -- it's useful for big tests with multiple commands (you can check conditions after every step);
  5. Look at CommandersCastTest.java as test example.

i should test if the reverse turnorder is actually applied by checking if the turn is passed to the correct opponent...

also, i found that using abilities seems impossible in test past turn 1.

if i use showAvaileableAbilities("T1 before", 1, PhaseStep.PRECOMBAT_MAIN, playerA);
it shows the abilities i should be able to use at that point,
if i use showAvaileableAbilities("T3 before", 3, PhaseStep.PRECOMBAT_MAIN, playerA);
it shows nothing, and there definetly should be something... that occurs for any turn other than 1.
is that by design or another bug i introduced :S

@algeee check turn order correction by casting any spell card and check life after that (player can't cast spell on wrong turn) -- as example: Agonizing Syphon.

showAvaileableAbilities works fine -- it's uses on player priority as all other test commands. If you can't see your ability in list then there are something wrong with commands before (you call it in wrong turn/step, card is not on the battlefield, no mana, tapped, no targets and etc -- or ability's code is broken).

also added assertActivePlayer for good measure.
and now my abilities also work past turn 1, no idea why though.
ok, so the card passed all tests, but the project compiles with errors, because another test failed -.-
2 errors in PlayerLeavesGameTest, apparently a continuous effects is being removed too early after it's controller leaves.
can't find anything related to my changes in these tests, and no other error's occured,
so i doubt its related - should i ignore and commit?

You must test multi turn cases, not only one.

Some rare tests fails by random -- run it multiple times to check. If all fine then clone repository and make pull request from it to xmage. If something wrong then you can add extra commits/changes to it.

well i can't yet figure out what's causing these errors.
i started from scratch, changing things step by step and now i end up with even more errors. not sure if somehow related to the latest changes i pulled... a fresh clone will build just fine, so something is broken.
too tired right now. will have to do more digging, hopefully i can get this over with by the end of this week, this is eating up my time... i guess i know why noone wanted to pick this up xD

Was this page helpful?
0 / 5 - 0 ratings