It is currently 23 May 2024, 14:35
   
Text Size

Card Contributions

Moderators: ubeefx, beholder, melvin, ShawnieBoy, Lodici, CCGHQ Admins

Re: Card Contributions

Postby frank » 31 Mar 2014, 22:03

truth to be told, java and me, we stopped being friends some 11 years ago and it's not coming back that easily ;) at least I have an faint understanding what the code does...

didn't know I could test them myself - that's great. will do. thanks
frank
 
Posts: 46
Joined: 24 Mar 2014, 00:59
Has thanked: 8 times
Been thanked: 2 times

Re: Card Contributions

Postby ShawnieBoy » 31 Mar 2014, 22:53

No problem! - Glad to be able to help. I'm not really a Java person myself, but thankfully a lot of the coding has been done so that it reads really well.

If you're testing new scripts, launch the Magarena-debug.bat file, it will run through all the cards abilities before you get into the game (will take a little longer to launch), so you won't need to put the card into a deck, then try a duel before it (potentially) crashes. The crash log will give you some pointers on where errors might be.

OK, now for Mistblade Shinobi:

Here we encounter a 'May' choice - bouncing a creature isn't mandatory, unlike Throat Slitter. MagicEvent only allows one 'choice' entry, but we've actually got two choices here - one 'May' choice and one 'Target' choice (do you want to bounce something, and if so, what?).

For cards that require only one simple yes/no may choice, say Rhox
Code: Select all
new MagicMayChoice()
is all you'd need to get that decision.

To allow Mistblade Shinobi's choices, it's May choice is it's Target choice (You may return target creature)
Code: Select all
new MagicMayChoice(
    MagicTargetChoice.TARGET_CREATURE_YOUR_OPPONENT_CONTROLS
)
The string that gives the description of the effect, normally lets the player know what the choice was (the blue text in brackets), and whose choice is was:

Code: Select all
"PN may\$ return target creature defending player controls to its owner's hand."
PN will get replaced in the code by the Players Name (You've seen this before when it's not worked correctly), and the 'may\$' will have the result of the choice after it.

When we get to the executeEvent(), we only want to do anything if the choice was 'yes', this is easily found with
Code: Select all
if (event.isYes()){

}
With anything in the curly brackets occurring if it is.

Adding this to what you've got, we have the finished product: :D
Code: Select all
name=Mistblade Shinobi
url=http://magiccards.info/query?q=!mistblade%20shinobi
image=http://mtgimage.com/card/mistblade%20shinobi.jpg
value=4.267
rarity=C
type=Creature
subtype=Human,Ninja
cost={2}{U}
pt=1/1
ability=ninjutsu {U}
timing=main
requires_groovy_code
Code: Select all
[
    new MagicWhenDamageIsDealtTrigger() {
        @Override
        public MagicEvent executeTrigger(final MagicGame game,final MagicPermanent permanent,final MagicDamage damage) {
            return (damage.getSource() == permanent &&
                damage.getTarget().isPlayer() &&
                damage.isCombat()) ?
                new MagicEvent(
                    permanent,
                    new MagicMayChoice(
                        MagicTargetChoice.TARGET_CREATURE_YOUR_OPPONENT_CONTROLS
                    ),
                    MagicBounceTargetPicker.create(),
                    this,
                    "PN may\$ return target creature defending player controls to its owner's hand."
                ):
                MagicEvent.NONE;
        }

        @Override
        public void executeEvent(final MagicGame game, final MagicEvent event) {
            if (event.isYes()) {
                event.processTargetPermanent(game, {
                    final MagicPermanent creature ->
                    game.doAction(new MagicRemoveFromPlayAction(creature,MagicLocationType.OwnersHand));
                });
            }
        }
    }
]
Practically spot on otherwise :D

But for some bad news...
Skullsnatcher has multiple targets, something we can't quite do yet. Devour works as it's not targeted (You sacrifice x creatures). But I like your logic in trying to get it to work, even with multiple triggers. I tend to veer away from any 'up to' or 'any number of' cards.
It's a shame, but he can go and live in the 'incomplete' folder for the time being, so your work isn't in vain :)
User avatar
ShawnieBoy
Programmer
 
Posts: 601
Joined: 02 Apr 2012, 22:42
Location: UK
Has thanked: 80 times
Been thanked: 50 times

Re: Card Contributions

Postby frank » 31 Mar 2014, 23:14

I was testing the card myself... missed the may choice and it crashed due to naming a variable permanent and calling it creature later... the crash log is quite informative: told me exactly what I was doing wrong. liked that.

okay, that was fun the time being, maybe more later ;)
frank
 
Posts: 46
Joined: 24 Mar 2014, 00:59
Has thanked: 8 times
Been thanked: 2 times

Re: Card Contributions

Postby frank » 01 Apr 2014, 05:37

got one more, however incomplete/faulty.
I can play a few turns, than crash and burn...

edit: found the mistake. now it's working like a charm. and in near mint condition, too ;)

edit2: I'd certainly like to try Shuriken next. Do we have some means to unattach equips?

Higure, the Still Wind
Code: Select all
name=Higure, the Still Wind
url=http://magiccards.info/query?q=!higure,%20the%20still%20wind
image=http://mtgimage.com/card/higure,%20the%20still%20wind.jpg
value=3.900
rarity=R
type=Creature
subtype=Human,Ninja
cost={3}{U}{U}
pt=3/1
ability=ninjutsu {2}{U}{U}
timing=main
requires_groovy_code
groovy
Code: Select all
def NINJA_FILTER=new MagicPermanentFilterImpl() {
        public boolean accept(final MagicGame game,final MagicPlayer player,final MagicPermanent target) {
            return target.isCreature() && target.hasSubType(MagicSubType.Ninja);
        }
    };
def TARGET_NINJA = new MagicTargetChoice(
    NINJA_FILTER,
    "target ninja"
)

def NINJA_CARD_FROM_LIBRARY = new MagicCardFilterImpl() {
    public boolean accept(final MagicGame game,final MagicPlayer player,final MagicCard target) {
        return target.hasSubType(MagicSubType.Ninja);
    }
    public boolean acceptType(final MagicTargetType targetType) {
        return targetType == MagicTargetType.Library;
    }
};

def A_NINJA_CARD_FROM_LIBRARY = new MagicTargetChoice(
    NINJA_CARD_FROM_LIBRARY,
    "a ninja card"
)

[
    new MagicPermanentActivation(
        new MagicActivationHints(MagicTiming.Attack),
        "Unblockable"
    ) {

        @Override
        public Iterable<MagicEvent> getCostEvent(final MagicPermanent source) {
            return [
            new MagicPayManaCostEvent(source,"{2}")
            ];
        }

        @Override
        public MagicEvent getPermanentEvent(final MagicPermanent source,final MagicPayedCost payedCost) {
            return new MagicEvent(
                source,
                TARGET_NINJA,
                MagicUnblockableTargetPicker.create(),
                this,
                "Target Ninja\$ is unblockable this turn."
            );
        }

        @Override
        public void executeEvent(final MagicGame game, final MagicEvent event) {
            event.processTargetPermanent(game, {
                final MagicPermanent creature ->
                game.doAction(new MagicGainAbilityAction(creature,MagicAbility.Unblockable));
            });
        }
    },
    new MagicWhenDamageIsDealtTrigger() {
        @Override
        public MagicEvent executeTrigger(final MagicGame game,final MagicPermanent permanent,final MagicDamage damage) {
            return (damage.getSource() == permanent &&
                damage.getTarget().isPlayer() &&
                damage.isCombat()) ?
                new MagicEvent(
                permanent,
                new MagicMayChoice(),
                this,
                "PN may search his or her library for a ninja card, reveals it, puts it into PN's Hand, and shuffles PN's library."
                ):
                MagicEvent.NONE;
        }

        @Override
        public void executeEvent(final MagicGame game, final MagicEvent event) {
            if (event.isYes()) {
                game.addEvent(new MagicSearchIntoHandEvent(
                event,
                A_NINJA_CARD_FROM_LIBRARY
            ));
            }
        }
    }
]

frank
 
Posts: 46
Joined: 24 Mar 2014, 00:59
Has thanked: 8 times
Been thanked: 2 times

Re: Card Contributions

Postby melvin » 01 Apr 2014, 07:53

frank wrote:I'd certainly like to try Shuriken next. Do we have some means to unattach equips?
The current method for unattaching a permanent is to attach it to MagicPermanent.NONE. Will look into creating a more intuitive unattach action for next release.

Thank for the new cards, and ShawnieBoy for helping to add the earlier ones to the project.

The easiest way for us to integrate your submission is using firemind.ch. Recommended to create an account on firemind.ch (for us to attribute the card to you) and submitting the cards via http://www.firemind.ch/card_script_submissions/new when you get them working. Try using firemind.ch for Higure, the Still Wind.
User avatar
melvin
AI Programmer
 
Posts: 1062
Joined: 21 Mar 2010, 12:26
Location: Singapore
Has thanked: 36 times
Been thanked: 459 times

Re: Card Contributions

Postby frank » 02 Apr 2014, 11:51

I hate to ask, but could somebody please help me again?

I tried Benthicore. This is how far I got:
Code: Select all
name=Benthicore
url=http://magiccards.info/query?q=%21benthicore
image=http://mtgimage.com/card/benthicore.jpg
value=3.095
rarity=U
type=Creature
subtype=Elemental
cost={6}{U}
pt=5/5
timing=main
requires_groovy_code
groovy:
Code: Select all
def UNTAPPED_MERFOLK_YOU_CONTROL=new MagicPermanentFilterImpl(){
        public boolean accept(final MagicGame game,final MagicPlayer player,final MagicPermanent target)
        {
            return target.isCreature() && target.hasSubType(MagicSubType.Merfolk) && !target.isTapped() && !target.isOpponent(player);
        }
    };
def AN_UNTAPPED_MERFOLK_YOU_CONTROL = new MagicTargetChoice(UNTAPPED_MERFOLK_YOU_CONTROL,"an untapped merfolk creature you control");

[
    new MagicWhenComesIntoPlayTrigger()
    {
        @Override
        public MagicEvent executeTrigger(final MagicGame game,final MagicPermanent permanent, final MagicPayedCost payedCost)
        {
            return new MagicEvent(permanent,this,"PN puts two 1/1 blue Merfolk Wizard creature token onto the battlefield.");
        }
        @Override
        public void executeEvent(final MagicGame game, final MagicEvent event)
        {
            game.doAction(new MagicPlayTokenAction(event.getPlayer(),TokenCardDefinitions.get("1/1 blue Merfolk Wizard creature token")));
            game.doAction(new MagicPlayTokenAction(event.getPlayer(),TokenCardDefinitions.get("1/1 blue Merfolk Wizard creature token")));
        }
    },
   
   
   
    new MagicPermanentActivation(new MagicActivationHints(MagicTiming.Removal),"Untap")
    {

        @Override
        public Iterable<MagicEvent> getCostEvent(final MagicPermanent source)
        {
            return [new MagicTapPermanentEvent(source, AN_UNTAPPED_MERFOLK_YOU_CONTROL),new MagicTapPermanentEvent(source, AN_UNTAPPED_MERFOLK_YOU_CONTROL)];
        }

        @Override
        public MagicEvent getPermanentEvent(final MagicPermanent source, final MagicPayedCost payedCost)
        {
           
            return new MagicEvent(source,this,"Untap SN. SN gains shroud until end of turn.");
        }

        @Override
        public void executeEvent(final MagicGame game, final MagicEvent event) {
            event.processTargetPermanent(game, {
                final MagicPermanent creature ->
                game.doAction(new MagicUntapAction(creature));
                game.doAction(new MagicGainAbilityAction(creature,MagicAbility.Shroud));
            });
        }
    }
]
Now, the game starts drama-free but after a few turns it breaks. crash.log shows:

Exception from controller.runGame: Unable to find target
java.lang.RuntimeException: Unable to find target
at magic.model.event.MagicEvent.getTarget(MagicEvent.java:434)
at magic.model.event.MagicEvent.getLegalTarget(MagicEvent.java:505)
at magic.model.event.MagicEvent.processTargetPermanent(MagicEvent.java:544)
at Benthicore$3.executeEvent(Benthicore.groovy:42)
at magic.model.event.MagicEvent.executeEvent(MagicEvent.java:618)
at magic.model.MagicGame.executeEvent(MagicGame.java:752)
at magic.model.stack.MagicItemOnStack.resolve(MagicItemOnStack.java:120)
at magic.model.action.MagicStackResolveAction.doAction(MagicStackResolveAction.java:13)
at magic.model.MagicGame.doAction(MagicGame.java:532)
at magic.model.phase.MagicPhase.executePhase(MagicPhase.java:43)
at magic.model.MagicGame.executePhase(MagicGame.java:431)
at magic.ai.MCTSAI.getNextChoices(MCTSAI.java:426)
at magic.ai.MCTSAI.randomPlay(MCTSAI.java:397)
at magic.ai.MCTSAI.access$000(MCTSAI.java:66)
at magic.ai.MCTSAI$1.run(MCTSAI.java:186)
at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:471)
at java.util.concurrent.FutureTask.run(FutureTask.java:262)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:615)
at java.lang.Thread.run(Thread.java:744)


What I'm missing here?
frank
 
Posts: 46
Joined: 24 Mar 2014, 00:59
Has thanked: 8 times
Been thanked: 2 times

Re: Card Contributions

Postby melvin » 02 Apr 2014, 14:29

1) The second ability's executeEvent shouldn't be using processTargetPermanet as there is no target. The Untap and Gain action should be applied to event.getPermanent(). See executeEvent of Ghost_Hounds.groovy as an example.

2) A more subtle problem is that the second ability needs an activation condition so that it can only be activated when the player has at least two untapped merfolks. The game is not smart enough to deduce this condition, it will allow the ability to be activated when there is one untapped merfolk, but later it would get stuck paying the cost. See Eater_of_Hope.groovy for an example.
User avatar
melvin
AI Programmer
 
Posts: 1062
Joined: 21 Mar 2010, 12:26
Location: Singapore
Has thanked: 36 times
Been thanked: 459 times

Re: Card Contributions

Postby frank » 02 Apr 2014, 14:49

Meanwhile I was working on Bringer of the Black Dawn. Good news: that one works, but still I ran into something I need to know:
Code: Select all
def CARD_FROM_LIBRARY = new MagicCardFilterImpl() {
    public boolean accept(final MagicGame game,final MagicPlayer player,final MagicCard target) {
        return true;
    }
    public boolean acceptType(final MagicTargetType targetType) {
        return targetType == MagicTargetType.Library;
    }
};

def A_CARD_FROM_LIBRARY = new MagicTargetChoice(
    CARD_FROM_LIBRARY,
    "a card"
);
[
    new MagicAtUpkeepTrigger() {
        @Override
        public MagicEvent executeTrigger(final MagicGame game,final MagicPermanent permanent,final MagicPlayer upkeepPlayer) {
            return (permanent.isController(upkeepPlayer)) ?
                new MagicEvent(
                    permanent,
                    new MagicMayChoice(),
                    this,
                    "PN may\$ pay 2 Life to search his or her library for a card, then shuffle his or her library and put that card on top of it."
                ):
                MagicEvent.NONE;
        }
        @Override
        public void executeEvent(final MagicGame game, final MagicEvent event) {
            if (event.isYes()){
                game.addEvent(new MagicPayLifeEvent(event.getPermanent(), 2));
                game.addEvent(new MagicSearchOntoLibraryEvent(event,A_CARD_FROM_LIBRARY));
            }
        }
    }
]
I didn't find a MagicPayLifeChoice, just a MagicPayManaChoice - so I couldn't get the "paying life"-action upfront. The actual loss of life occurs when you put that card on top of your library - is that problematic concerning the timing?

I just posted it on firemind nevertheless... will look into your suggestions now. Thanks for spoon-feeding me. ;)


edit: that did the trick, thanks again - posted to firemind.
frank
 
Posts: 46
Joined: 24 Mar 2014, 00:59
Has thanked: 8 times
Been thanked: 2 times

Re: Card Contributions

Postby ShawnieBoy » 02 Apr 2014, 17:56

The payment timing should be fine - it's how the Ravnica shock lands are coded as well. There's no real timing gap between paying and searching. It's worded that way so it prevents you from paying multiple amounts of life.

Thanks for the submissions! Keep them coming - Although do remember to log in on firemind.ch, they're being submitted as Guest ;)
User avatar
ShawnieBoy
Programmer
 
Posts: 601
Joined: 02 Apr 2012, 22:42
Location: UK
Has thanked: 80 times
Been thanked: 50 times

Re: Card Contributions

Postby frank » 02 Apr 2014, 18:02

right, wasn't logged in. I see it now. Bringer of the Red Dawn was mine, too... ;)

There's is but one thing, that keeps me wondering: as by the rules, you can't pay 2 life, if you don't have 2 life. The way I did it you are asked the May-Option and the paylife action occurs later, what happens if you have exactly 1 life left?

edit: I give up on Shuriken - for now.
proved to difficult for me, sorry.
frank
 
Posts: 46
Joined: 24 Mar 2014, 00:59
Has thanked: 8 times
Been thanked: 2 times

Re: Card Contributions

Postby frank » 03 Apr 2014, 21:07

I'm terribly sorry. I submitted two cards which weren't working properly. Didn'T get the color as they should. As soon as I discovered it, I fixed it and tried to re-submit them, but firemind wouldn't let me. So here the correct code:

Genju of the Cedars:
Code: Select all
name=Genju of the Cedars
url=http://magiccards.info/query?q=%21genju%20of%20the%20cedars
image=http://mtgimage.com/card/genju%20of%20the%20cedars.jpg
value=4.115
rarity=U
type=Enchantment
subtype=Aura
cost={G}
enchant=pump,pos forest
timing=enchantment
requires_groovy_code
groovy:
Code: Select all
def PT = new MagicStatic(MagicLayer.SetPT, MagicStatic.UntilEOT) {
    @Override
    public void modPowerToughness(final MagicPermanent source,final MagicPermanent permanent,final MagicPowerToughness pt) {
        pt.set(4,4);
    }
};
def ST = new MagicStatic(MagicLayer.Type, MagicStatic.UntilEOT) {
    @Override
    public int getTypeFlags(final MagicPermanent permanent,final int flags) {
        return flags | MagicType.Creature.getMask();
    }
    @Override
    public void modTypeFlags(final MagicPermanent permanent, final Set<MagicType> flags) {   
        flags.add(MagicType.Creature);
    }
    @Override
    public void modSubTypeFlags(final MagicPermanent permanent, final Set<MagicSubType> flags) {
        flags.add(MagicSubType.Spirit);
    }
};
def LC = new MagicStatic(MagicLayer.Color, MagicStatic.UntilEOT) {
    @Override
    public int getColorFlags(final MagicPermanent permanent,final int flags) {
        return MagicColor.Green.getMask();
    }
};
[
    new MagicPermanentActivation(
        [
            new MagicArtificialCondition(
                MagicConditionFactory.ManaCost("{3}")
            )
        ],
        new MagicActivationHints(MagicTiming.Animate),
        "Animate"
    ) {

        @Override
        public Iterable<MagicEvent> getCostEvent(final MagicPermanent source) {
            return [new MagicPayManaCostEvent(source,"{2}")];
        }

        @Override
        public MagicEvent getPermanentEvent(final MagicPermanent source,final MagicPayedCost payedCost) {
            return new MagicEvent(
                source.getEnchantedPermanent(),
                this,
                "SN becomes a 4/4 green Spirit creature until end of turn." +
                "It's still a land."
            );
        }

        @Override
        public void executeEvent(final MagicGame game, final MagicEvent event) {
            game.doAction(new MagicBecomesCreatureAction(event.getPermanent(),PT,ST,LC));
        }
    },
    new MagicWhenOtherDiesTrigger() {
        @Override
        public MagicEvent executeTrigger(
                final MagicGame game,
                final MagicPermanent permanent,
                final MagicPermanent died) {
            return (permanent.getEnchantedPermanent() == died) ?
                new MagicEvent(
                    permanent,
                    permanent.getCard(),
                    this,
                    "Return RN to its owner's hand."
                ):
                MagicEvent.NONE;
        }
        @Override
        public void executeEvent(final MagicGame game, final MagicEvent event) {
            final MagicCard card = event.getRefCard();
            if (card.isInGraveyard()) {
                game.doAction(new MagicRemoveCardAction(card,MagicLocationType.Graveyard));
                game.doAction(new MagicMoveCardAction(card,MagicLocationType.Graveyard,MagicLocationType.OwnersHand));
            }
        }
    }
]
Genju of the Falls:
Code: Select all
name=Genju of the Falls
url=http://magiccards.info/query?q=%21genju%20of%20the%20falls
image=http://mtgimage.com/card/genju%20of%20the%20falls.jpg
value=4.221
rarity=U
type=Enchantment
subtype=Aura
cost={U}
enchant=pump,pos island
timing=enchantment
requires_groovy_code
groovy:
Code: Select all
def PT = new MagicStatic(MagicLayer.SetPT, MagicStatic.UntilEOT) {
    @Override
    public void modPowerToughness(final MagicPermanent source,final MagicPermanent permanent,final MagicPowerToughness pt) {
        pt.set(3,2);
    }
};
def AB = new MagicStatic(MagicLayer.Ability, MagicStatic.UntilEOT) {
    @Override
    public void modAbilityFlags(final MagicPermanent source,final MagicPermanent permanent,final Set<MagicAbility> flags) {
        permanent.addAbility(MagicAbility.Flying, flags);
    }
};
def ST = new MagicStatic(MagicLayer.Type, MagicStatic.UntilEOT) {
    @Override
    public int getTypeFlags(final MagicPermanent permanent,final int flags) {
        return flags | MagicType.Creature.getMask();
    }
    @Override
    public void modTypeFlags(final MagicPermanent permanent, final Set<MagicType> flags) {   
        flags.add(MagicType.Creature);
    }
    @Override
    public void modSubTypeFlags(final MagicPermanent permanent, final Set<MagicSubType> flags) {
        flags.add(MagicSubType.Spirit);
    }
};
def LC = new MagicStatic(MagicLayer.Color, MagicStatic.UntilEOT) {
    @Override
    public int getColorFlags(final MagicPermanent permanent,final int flags) {
        return MagicColor.Blue.getMask();
    }
};
[
    new MagicPermanentActivation(
        [
            new MagicArtificialCondition(
                MagicConditionFactory.ManaCost("{3}")
            )
        ],
        new MagicActivationHints(MagicTiming.Animate),
        "Animate"
    ) {

        @Override
        public Iterable<MagicEvent> getCostEvent(final MagicPermanent source) {
            return [new MagicPayManaCostEvent(source,"{2}")];
        }

        @Override
        public MagicEvent getPermanentEvent(final MagicPermanent source,final MagicPayedCost payedCost) {
            return new MagicEvent(
                source.getEnchantedPermanent(),
                this,
                "SN becomes a 3/2 blue Spirit creature with flying until end of turn." +
                "It's still a land."
            );
        }

        @Override
        public void executeEvent(final MagicGame game, final MagicEvent event) {
            game.doAction(new MagicBecomesCreatureAction(event.getPermanent(),PT,AB,ST,LC));
        }
    },
    new MagicWhenOtherDiesTrigger() {
        @Override
        public MagicEvent executeTrigger(
                final MagicGame game,
                final MagicPermanent permanent,
                final MagicPermanent died) {
            return (permanent.getEnchantedPermanent() == died) ?
                new MagicEvent(
                    permanent,
                    permanent.getCard(),
                    this,
                    "Return RN to its owner's hand."
                ):
                MagicEvent.NONE;
        }
        @Override
        public void executeEvent(final MagicGame game, final MagicEvent event) {
            final MagicCard card = event.getRefCard();
            if (card.isInGraveyard()) {
                game.doAction(new MagicRemoveCardAction(card,MagicLocationType.Graveyard));
                game.doAction(new MagicMoveCardAction(card,MagicLocationType.Graveyard,MagicLocationType.OwnersHand));
            }
        }
    }
]
frank
 
Posts: 46
Joined: 24 Mar 2014, 00:59
Has thanked: 8 times
Been thanked: 2 times

Re: Card Contributions

Postby melvin » 04 Apr 2014, 01:39

No worries, it happens all the time. Perhaps we should make the card scripts more like a wiki page.

I've made the fixed you suggested plus some other ones (there isn't a modTypeFlags method) in https://code.google.com/p/magarena/sour ... 057aac81e8
User avatar
melvin
AI Programmer
 
Posts: 1062
Joined: 21 Mar 2010, 12:26
Location: Singapore
Has thanked: 36 times
Been thanked: 459 times

Re: Card Contributions

Postby frank » 04 Apr 2014, 10:23

but there is a modSubTypeFlag method. I assumed it would work... but couldn't get MagicType.Legendary onto that land enchanted by Genju of the Realms, so used the code from Blinkmoth Nexus. Thanks for cleaning it up.

say, is there a way to find out if a creature did damage to a player this turn?
I was trying to implement Spear of Heliod yesterday, but didn't find anything useful in the class definitions.
frank
 
Posts: 46
Joined: 24 Mar 2014, 00:59
Has thanked: 8 times
Been thanked: 2 times

Re: Card Contributions

Postby ShawnieBoy » 04 Apr 2014, 20:58

There's a playerState flag WasDealtDamage, that is used by effects such as Bloodlust. But that's as close as it gets.
I'm not sure if it would later be possible to add variables to that, to show and list the sources of damage.
User avatar
ShawnieBoy
Programmer
 
Posts: 601
Joined: 02 Apr 2012, 22:42
Location: UK
Has thanked: 80 times
Been thanked: 50 times

Re: Card Contributions

Postby frank » 04 Apr 2014, 23:26

and the other way round? flag the creature boolean hasDealtDamageToPlayerThisTurn(MagicPlayer player){...}
frank
 
Posts: 46
Joined: 24 Mar 2014, 00:59
Has thanked: 8 times
Been thanked: 2 times

PreviousNext

Return to Magarena

Who is online

Users browsing this forum: No registered users and 4 guests


Who is online

In total there are 4 users online :: 0 registered, 0 hidden and 4 guests (based on users active over the past 10 minutes)
Most users ever online was 4143 on 23 Jan 2024, 08:21

Users browsing this forum: No registered users and 4 guests

Login Form