diff --git a/projects/mtg/bin/Res/sets/10E/_cards.dat b/projects/mtg/bin/Res/sets/10E/_cards.dat index 67d41b913..195392805 100644 --- a/projects/mtg/bin/Res/sets/10E/_cards.dat +++ b/projects/mtg/bin/Res/sets/10E/_cards.dat @@ -2,7 +2,7 @@ text=Target creature gets -1/-1 until end of turn. Draw a card. target=creature auto=-1/-1 -auto=draw:1 +auto=draw:1 controller id=135206 name=Afflict rarity=C diff --git a/projects/mtg/bin/Res/sets/10E/todo.dat b/projects/mtg/bin/Res/sets/10E/todo.dat index 2d2d061b8..0a3f2777d 100644 --- a/projects/mtg/bin/Res/sets/10E/todo.dat +++ b/projects/mtg/bin/Res/sets/10E/todo.dat @@ -104,7 +104,7 @@ toughness=3 text={X}{W}, {T}: Ballista Squad deals X damage to target attacking or blocking creature. id=129477 name=Ballista Squad -auto={X}{W}{T}:damage:x target(creature[attacking,blocking]) +auto={X}{W}{T}:damage:x target(creature[attacking;blocking]) rarity=U color=White type=Creature diff --git a/projects/mtg/bin/Res/sets/ARB/_cards.dat b/projects/mtg/bin/Res/sets/ARB/_cards.dat index 00f03b1ff..f6e084b07 100644 --- a/projects/mtg/bin/Res/sets/ARB/_cards.dat +++ b/projects/mtg/bin/Res/sets/ARB/_cards.dat @@ -265,6 +265,7 @@ id=179614 name=Morbid Bloom target=creature|graveyard auto=moveto(exile) +auto=token(Saproling,Creature Saproling,1/1,green)*t rarity=U mana={4}{B}{G} type=Sorcery diff --git a/projects/mtg/bin/Res/sets/ICE/_cards.dat b/projects/mtg/bin/Res/sets/ICE/_cards.dat index 8254b0cf8..cc9964642 100644 --- a/projects/mtg/bin/Res/sets/ICE/_cards.dat +++ b/projects/mtg/bin/Res/sets/ICE/_cards.dat @@ -1490,6 +1490,7 @@ text=Destroy target Wall. It can't be regenerated. Word of Blasting deals damage id=2660 target=Wall auto=bury +auto=damage:manacost targetcontroller name=Word of Blasting rarity=U mana={1}{R} diff --git a/projects/mtg/bin/Res/sets/INV/_cards.dat b/projects/mtg/bin/Res/sets/INV/_cards.dat index 193eabaff..f3587cfce 100644 --- a/projects/mtg/bin/Res/sets/INV/_cards.dat +++ b/projects/mtg/bin/Res/sets/INV/_cards.dat @@ -125,6 +125,8 @@ toughness=5 text=Destroy target artifact. It can't be regenerated. Put X 1/1 green Saproling creature tokens onto the battlefield, where X is its converted mana cost. id=23195 target=artifact +auto=bury +auto=token(Saproling,Creature Saproling,1/1,green)*manacost name=Artifact Mutation rarity=R type=Instant diff --git a/projects/mtg/bin/Res/sets/LEG/_cards.dat b/projects/mtg/bin/Res/sets/LEG/_cards.dat index 831476a22..8ea1d65f2 100644 --- a/projects/mtg/bin/Res/sets/LEG/_cards.dat +++ b/projects/mtg/bin/Res/sets/LEG/_cards.dat @@ -285,6 +285,8 @@ text=Destroy target artifact. You gain life equal to its converted mana cost. id=1607 target=artifact name=Divine Offering +auto=destroy +auto=life:manacost controller rarity=C type=Instant mana={1}{W} diff --git a/projects/mtg/bin/Res/sets/ODY/_cards.dat b/projects/mtg/bin/Res/sets/ODY/_cards.dat index 40dd44580..c79e9a935 100644 --- a/projects/mtg/bin/Res/sets/ODY/_cards.dat +++ b/projects/mtg/bin/Res/sets/ODY/_cards.dat @@ -30,7 +30,7 @@ id=29740 name=Afflict target=Creature auto=-1/-1 -auto=draw:1 +auto=draw:1 controller rarity=C mana={2}{B} type=Instant diff --git a/projects/mtg/bin/Res/sets/RV/_cards.dat b/projects/mtg/bin/Res/sets/RV/_cards.dat index f116dfc90..e9a3bc5ac 100644 --- a/projects/mtg/bin/Res/sets/RV/_cards.dat +++ b/projects/mtg/bin/Res/sets/RV/_cards.dat @@ -436,6 +436,7 @@ subtype=Aura text=Destroy target artifact. It can't be regenerated. That artifact's controller gains life equal to its converted mana cost. target=artifact auto=bury +auto=life:manacost targetcontroller id=1240 name=Crumble rarity=U @@ -656,6 +657,8 @@ subtype=Aura [/card] [card] text=Earthquake deals X damage to each creature without flying and each player. +auto=damage:X all(player) +auto=damage:X all(creature[-flying]) id=1289 name=Earthquake rarity=R @@ -1052,6 +1055,8 @@ id=1251 name=Hurricane rarity=U mana={X}{G} +auto=damage:X all(player) +auto=damage:X all(creature[flying]) type=Sorcery [/card] [card] diff --git a/projects/mtg/bin/Res/test/_tests.txt b/projects/mtg/bin/Res/test/_tests.txt index 6abfd747c..0d5ff3570 100644 --- a/projects/mtg/bin/Res/test/_tests.txt +++ b/projects/mtg/bin/Res/test/_tests.txt @@ -116,6 +116,7 @@ counterspell3.txt counterspell4.txt creature_bond.txt crimson_kobolds.txt +crumble.txt crystal_rod_i172.txt dauntless_escort.txt dauthi_embrace.txt @@ -170,6 +171,7 @@ harpoon_sniper.txt hellfire.txt howl_from_beyond.txt howl_of_the_night_pack.txt +hurricane.txt hyalopterous_lemure.txt hymn_of_rebirth.txt hypnotic_specter.txt diff --git a/projects/mtg/bin/Res/test/crumble.txt b/projects/mtg/bin/Res/test/crumble.txt new file mode 100644 index 000000000..38f120b09 --- /dev/null +++ b/projects/mtg/bin/Res/test/crumble.txt @@ -0,0 +1,19 @@ +#Test Crumble life +[INIT] +FIRSTMAIN +[PLAYER1] +hand:crumble +manapool:{G} +[PLAYER2] +inplay:colossus of Sardia +[DO] +crumble +colossus of sardia +[ASSERT] +FIRSTMAIN +[PLAYER1] +graveyard:crumble +[PLAYER2] +graveyard:colossus of sardia +life:29 +[END] \ No newline at end of file diff --git a/projects/mtg/bin/Res/test/hurricane.txt b/projects/mtg/bin/Res/test/hurricane.txt new file mode 100644 index 000000000..8aabae80e --- /dev/null +++ b/projects/mtg/bin/Res/test/hurricane.txt @@ -0,0 +1,21 @@ +#Test Hurricane +[INIT] +FIRSTMAIN +[PLAYER1] +hand:hurricane +inplay:grizzly bears,air elemental +manapool:{4}{G} +[PLAYER2] +inplay:serra angel +[DO] +hurricane +[ASSERT] +FIRSTMAIN +[PLAYER1] +life:16 +inplay:grizzly bears +graveyard:air elemental,hurricane +[PLAYER2] +graveyard:serra angel +life:16 +[END] \ No newline at end of file diff --git a/projects/mtg/include/AllAbilities.h b/projects/mtg/include/AllAbilities.h index 26bada041..518ddd830 100644 --- a/projects/mtg/include/AllAbilities.h +++ b/projects/mtg/include/AllAbilities.h @@ -182,9 +182,9 @@ public: return 1; } - ~ TrDamaged (){ + ~TrDamaged (){ SAFE_DELETE(tc); - SAFE_DELETE(fromTc); + SAFE_DELETE(fromTc); } TrDamaged * clone() const{ @@ -502,8 +502,8 @@ class AADrawer:public ActivatedAbilityTP{ /*Gives life to target controller*/ class AALifer:public ActivatedAbilityTP{ public: - int life; - AALifer(int _id, MTGCardInstance * card, Targetable * _target, int life, ManaCost * _cost = NULL, int _tap = 0, int who = TargetChooser::UNSET):ActivatedAbilityTP(_id, card,_target,_cost,_tap,who),life(life){ + WParsedInt *life; + AALifer(int _id, MTGCardInstance * card, Targetable * _target, WParsedInt * life, ManaCost * _cost = NULL, int _tap = 0, int who = TargetChooser::UNSET):ActivatedAbilityTP(_id, card,_target,_cost,_tap,who),life(life){ } int resolve(){ @@ -512,7 +512,7 @@ class AALifer:public ActivatedAbilityTP{ if (_target->type_as_damageable == DAMAGEABLE_MTGCARDINSTANCE){ _target = ((MTGCardInstance *)_target)->controller(); } - _target->life+=life; + _target->life+=life->getValue(); } return 1; } @@ -523,10 +523,15 @@ class AALifer:public ActivatedAbilityTP{ AALifer * clone() const{ AALifer * a = NEW AALifer(*this); + a->life = NEW WParsedInt(*(a->life)); a->isClone = 1; return a; } + ~AALifer(){ + SAFE_DELETE(life); + } + }; @@ -1767,15 +1772,15 @@ class AForeach:public ListMaintainerAbility{ class AADamager:public ActivatedAbilityTP{ public: - int damage; -AADamager(int _id, MTGCardInstance * _source, Targetable * _target, int _damage = 0, ManaCost * _cost=NULL, int doTap = 0, int who = TargetChooser::UNSET):ActivatedAbilityTP(_id,_source,_target,_cost,doTap,who),damage(_damage){ + WParsedInt * damage; +AADamager(int _id, MTGCardInstance * _source, Targetable * _target, WParsedInt * damage, ManaCost * _cost=NULL, int doTap = 0, int who = TargetChooser::UNSET):ActivatedAbilityTP(_id,_source,_target,_cost,doTap,who),damage(damage){ aType = MTGAbility::DAMAGER; } int resolve(){ if(target){ Damageable * _target = (Damageable *) getTarget(); - game->mLayers->stackLayer()->addDamage(source,_target, damage); + game->mLayers->stackLayer()->addDamage(source,_target, damage->getValue()); game->mLayers->stackLayer()->resolve(); return 1; } @@ -1786,21 +1791,25 @@ AADamager(int _id, MTGCardInstance * _source, Targetable * _target, int _damage return "Damage"; } - AADamager * clone() const{ AADamager * a = NEW AADamager(*this); + a->damage = NEW WParsedInt(*(a->damage)); a->isClone = 1; return a; } + ~AADamager(){ + SAFE_DELETE(damage); + } + }; /* Standard Damager, can choose a NEW target each time the price is paid */ class TADamager:public TargetAbility{ public: - int damage; - TADamager(int id, MTGCardInstance * card, ManaCost * _cost, int _damage, TargetChooser * _tc = NULL, int _tap = 0):TargetAbility(id,card, _tc, _cost,0,_tap),damage(_damage){ + + TADamager(int id, MTGCardInstance * card, ManaCost * _cost, WParsedInt * damage, TargetChooser * _tc = NULL, int _tap = 0):TargetAbility(id,card, _tc, _cost,0,_tap){ if (!tc) tc = NEW DamageableTargetChooser(card); ability = NEW AADamager(id,card,NULL,damage); } diff --git a/projects/mtg/include/MTGDefinitions.h b/projects/mtg/include/MTGDefinitions.h index 5f4557cf6..a886475b0 100644 --- a/projects/mtg/include/MTGDefinitions.h +++ b/projects/mtg/include/MTGDefinitions.h @@ -101,8 +101,9 @@ class Constants INTIMIDATE = 43, DEATHTOUCH = 44, HORSEMANSHIP = 45, + CANTREGENERATE = 46, - NB_BASIC_ABILITIES = 46, + NB_BASIC_ABILITIES = 47, RARITY_M = 'M', diff --git a/projects/mtg/src/AIPlayer.cpp b/projects/mtg/src/AIPlayer.cpp index bcbfedb28..3c11acd41 100644 --- a/projects/mtg/src/AIPlayer.cpp +++ b/projects/mtg/src/AIPlayer.cpp @@ -178,10 +178,10 @@ int AIAction::getEfficiency(){ AADamager * aad = (AADamager *) a; if ( p == target->controller()){ efficiency = 0; - }else if (aad->damage >= target->toughness){ + }else if (aad->damage->getValue() >= target->toughness){ efficiency = 100; }else if (target->toughness){ - efficiency = (50 * aad->damage) / target->toughness; + efficiency = (50 * aad->damage->getValue()) / target->toughness; }else{ efficiency = 0; } diff --git a/projects/mtg/src/MTGAbility.cpp b/projects/mtg/src/MTGAbility.cpp index 8a837a433..9d92bad72 100644 --- a/projects/mtg/src/MTGAbility.cpp +++ b/projects/mtg/src/MTGAbility.cpp @@ -489,16 +489,16 @@ MTGAbility * AbilityFactory::parseMagicLine(string s, int id, Spell * spell, MTG unsigned int start = s.find(":",found); if (start == string::npos) start = s.find(" ",found); unsigned int end = s.find(" ",start); - int damage; + string d; if (end != string::npos){ - damage = atoi(s.substr(start+1,end-start-1).c_str()); + d = s.substr(start+1,end-start-1); }else{ - damage = atoi(s.substr(start+1).c_str()); + d = s.substr(start+1); } - - Damageable * d = NULL; - if (spell) d = spell->getNextDamageableTarget(); - MTGAbility * a = NEW AADamager(id,card,d, damage, NULL, 0, who); + WParsedInt * damage = NEW WParsedInt(d,spell,card); + Damageable * t = NULL; + if (spell) t = spell->getNextDamageableTarget(); + MTGAbility * a = NEW AADamager(id,card,t, damage, NULL, 0, who); a->oneShot = 1; return a; } @@ -509,15 +509,15 @@ MTGAbility * AbilityFactory::parseMagicLine(string s, int id, Spell * spell, MTG if (found != string::npos){ unsigned int start = found+4; unsigned int end = s.find(" ",start); - int life; + string life_s; if (end != string::npos){ - life = atoi(s.substr(start+1,end-start-1).c_str()); + life_s = s.substr(start+1,end-start-1); }else{ - life = atoi(s.substr(start+1).c_str()); + life_s = s.substr(start+1); } - + WParsedInt * life = NEW WParsedInt(life_s,spell,card); Damageable * d = NULL; - if (spell) d = spell->getNextPlayerTarget(); + if (spell) d = spell->getNextDamageableTarget(); MTGAbility * a = NEW AALifer(id,card,d,life,NULL,0,who); a->oneShot = 1; return a; @@ -536,7 +536,7 @@ MTGAbility * AbilityFactory::parseMagicLine(string s, int id, Spell * spell, MTG } Targetable * t = NULL; - if (spell) t = spell->getNextPlayerTarget(); + if (spell) t = spell->getNextTarget(); MTGAbility * a = NEW AADrawer(id,card,t,NULL,nbcards,0,who); a->oneShot = 1; return a; @@ -555,7 +555,7 @@ MTGAbility * AbilityFactory::parseMagicLine(string s, int id, Spell * spell, MTG } Targetable * t = NULL; - if (spell) t = spell->getNextPlayerTarget(); + if (spell) t = spell->getNextTarget(); MTGAbility * a = NEW AADepleter(id,card,t,nbcards,NULL,0,who); a->oneShot = 1; return a; @@ -565,7 +565,7 @@ MTGAbility * AbilityFactory::parseMagicLine(string s, int id, Spell * spell, MTG found = s.find("shuffle"); if (found != string::npos){ Targetable * t = NULL; - if (spell) t = spell->getNextPlayerTarget(); + if (spell) t = spell->getNextTarget(); MTGAbility * a = NEW AAShuffle(id,card,t,NULL,0,who); a->oneShot = 1; return a; @@ -677,10 +677,6 @@ MTGAbility * AbilityFactory::parseMagicLine(string s, int id, Spell * spell, MTG delete wppt; } - - - - //Mana Producer found = s.find("add"); if (found != string::npos){ @@ -692,7 +688,6 @@ MTGAbility * AbilityFactory::parseMagicLine(string s, int id, Spell * spell, MTG return a; } - //Gain/loose Ability for (int j = 0; j < Constants::NB_BASIC_ABILITIES; j++){ found = s.find(Constants::MTGBasicAbilities[j]); @@ -808,6 +803,7 @@ int AbilityFactory::abilityEfficiency(MTGAbility * a, Player * p, int mode, Targ badAbilities[Constants::DEFENDER] = true; badAbilities[Constants::DOESNOTUNTAP] = true; badAbilities[Constants::MUSTATTACK] = true; + badAbilities[Constants::CANTREGENERATE] = true; if (AInstantBasicAbilityModifierUntilEOT * abi = dynamic_cast(a)) { int result = badAbilities[abi->ability] ? BAKA_EFFECT_BAD : BAKA_EFFECT_GOOD; @@ -1296,26 +1292,7 @@ void AbilityFactory::addAbilities(int _id, Spell * spell){ game->addObserver(NEW AAspectOfWolf(_id, card, card->target)); break; } - case 1240: //Crumble - { - card->target->controller()->life+= card->target->getManaCost()->getConvertedCost(); - break; - } - case 1251: //Hurricane - { - int x = spell->cost->getConvertedCost() - 1; - for (int i = 0; i < 2 ; i++){ - game->mLayers->stackLayer()->addDamage(card, game->players[i], x); - for (int j = 0; j < game->players[i]->game->inPlay->nb_cards; j++){ - MTGCardInstance * current = game->players[i]->game->inPlay->cards[j]; - if (current->basicAbilities[Constants::FLYING] && current->isCreature()){ - game->mLayers->stackLayer()->addDamage(card, current, x); - } - } - } - break; - } - case 1262: //Regeneration + case 1262: //Regeneration { int cost[] = {Constants::MTG_COLOR_GREEN, 1}; game->addObserver(NEW AStandardRegenerate(_id,card,card->target,NEW ManaCost(cost,1))); @@ -1365,20 +1342,6 @@ void AbilityFactory::addAbilities(int _id, Spell * spell){ game->addObserver(NEW AEarthbind(_id, card, card->target)); break; } - case 1289: //earthquake - { - int x = computeX(spell,card); - for (int i = 0; i < 2 ; i++){ - game->mLayers->stackLayer()->addDamage(card, game->players[i], x); - for (int j = 0; j < game->players[i]->game->inPlay->nb_cards; j++){ - MTGCardInstance * current = game->players[i]->game->inPlay->cards[j]; - if (!current->basicAbilities[Constants::FLYING] && current->isCreature()){ - game->mLayers->stackLayer()->addDamage(card, current, x); - } - } - } - break; - } case 1344: //Eye for an Eye { Damage * damage = spell->getNextDamageTarget(); @@ -1450,12 +1413,6 @@ void AbilityFactory::addAbilities(int _id, Spell * spell){ game->addObserver(NEW AConvertLandToCreatures(id, card, "land")); break; } - case 1607: //Divine Offering - { - card->target->controller()->game->putInGraveyard(card->target); - game->currentlyActing()->life+= card->target->getManaCost()->getConvertedCost(); - break; - } case 1480: //Energy Tap { card->target->tap(); @@ -1481,11 +1438,6 @@ void AbilityFactory::addAbilities(int _id, Spell * spell){ //Addons ICE-AGE Cards - case 2660: //Word of Blasting - { - card->target->controller()->life-= card->target->getManaCost()->getConvertedCost(); - break; - } case 2474: //Minion of Leshrac { game->addObserver(NEW AMinionofLeshrac( _id, card)); @@ -1631,19 +1583,6 @@ void AbilityFactory::addAbilities(int _id, Spell * spell){ } -// --- addon Invasion--- - case 23195: //Artifact Mutation - { - card->target->controller()->game->putInGraveyard(card->target); - int x = card->target->getManaCost()->getConvertedCost(); - ATokenCreator * tok = NEW ATokenCreator(id,card,NEW ManaCost(),"Saproling","creature Saproling",1,1,"green",0); - for (int i=0; i < x; i++){ - tok->resolve(); - } - delete(tok); - break; - } - // --- addon Ravnica--- case 89114: //Psychic Drain @@ -1659,18 +1598,6 @@ void AbilityFactory::addAbilities(int _id, Spell * spell){ break; } - // --- addon ARB--- - case 179614: // Morbid Bloom - { - int x = card->target->toughness; - ATokenCreator * tok = NEW ATokenCreator(id,card,NEW ManaCost(),"Saproling","creature Saproling",1,1,"green",0); - for (int i=0; i < x; i++){ - tok->resolve(); - } - delete(tok); - break; - } - default: break; } diff --git a/projects/mtg/src/MTGCardInstance.cpp b/projects/mtg/src/MTGCardInstance.cpp index 1f9badb14..584076af9 100644 --- a/projects/mtg/src/MTGCardInstance.cpp +++ b/projects/mtg/src/MTGCardInstance.cpp @@ -231,11 +231,13 @@ int MTGCardInstance::isTapped(){ } int MTGCardInstance::regenerate(){ + if (has(Constants::CANTREGENERATE)) return 0; return ++regenerateTokens; } int MTGCardInstance::triggerRegenerate(){ if (! regenerateTokens) return 0; + if (has(Constants::CANTREGENERATE)) return 0; regenerateTokens--; tap(); life = toughness; @@ -401,18 +403,9 @@ int MTGCardInstance::toggleAttacker(){ setAttacker(1); return 1; }else{ - //Banding needs to be debugged... - /*MTGCardInstance * bandingPartner = getNextPartner(); - if (bandingPartner){ - if (banding) unband(); - if (!bandingPartner->banding) bandingPartner->banding = bandingPartner; - banding = bandingPartner->banding; - return 1; - }else{*/ untap(); setAttacker(0); return 1; - //} } return 0; }