mirror of
https://github.com/vcmi/vcmi.git
synced 2024-12-24 22:14:36 +02:00
Creature spells are now functional.
It includes Master Genie, Archangel, Faerie Dragon & Elementals
This commit is contained in:
parent
47740cd683
commit
f4fc77ccb8
@ -2140,8 +2140,8 @@ void CBattleInterface::mouseMoved(const SDL_MouseMotionEvent &sEvent)
|
||||
std::ostringstream estDmg;
|
||||
estDmg << estimatedDmg.first << " - " << estimatedDmg.second;
|
||||
//printing
|
||||
sprintf(buf, CGI->generaltexth->allTexts[36].c_str(), shere->count == 1 ? shere->getCreature()->nameSing.c_str() : shere->getCreature()->namePl.c_str(),
|
||||
estDmg.str().c_str());
|
||||
sprintf(buf, CGI->generaltexth->allTexts[36].c_str(),
|
||||
shere->count == 1 ? shere->getCreature()->nameSing.c_str() : shere->getCreature()->namePl.c_str(), estDmg.str().c_str());
|
||||
console->alterTxt = buf;
|
||||
console->whoSetAlter = 0;
|
||||
}
|
||||
@ -2170,19 +2170,20 @@ void CBattleInterface::mouseMoved(const SDL_MouseMotionEvent &sEvent)
|
||||
else //available tile
|
||||
{
|
||||
//setting console text and cursor
|
||||
const CStack *sactive = activeStack;
|
||||
if(sactive) //there can be a moment when stack is dead ut next is not yet activated
|
||||
if(activeStack) //there can be a moment when stack is dead ut next is not yet activated
|
||||
{
|
||||
char buf[500];
|
||||
if(sactive->hasBonusOfType(Bonus::FLYING))
|
||||
if(activeStack->hasBonusOfType(Bonus::FLYING))
|
||||
{
|
||||
CCS->curh->changeGraphic(1,2);
|
||||
sprintf(buf, CGI->generaltexth->allTexts[295].c_str(), sactive->count == 1 ? sactive->getCreature()->nameSing.c_str() : sactive->getCreature()->namePl.c_str());
|
||||
sprintf(buf, CGI->generaltexth->allTexts[295].c_str(),
|
||||
activeStack->count == 1 ? activeStack->getCreature()->nameSing.c_str() : activeStack->getCreature()->namePl.c_str());
|
||||
}
|
||||
else
|
||||
{
|
||||
CCS->curh->changeGraphic(1,1);
|
||||
sprintf(buf, CGI->generaltexth->allTexts[294].c_str(), sactive->count == 1 ? sactive->getCreature()->nameSing.c_str() : sactive->getCreature()->namePl.c_str());
|
||||
sprintf(buf, CGI->generaltexth->allTexts[294].c_str(),
|
||||
activeStack->count == 1 ? activeStack->getCreature()->nameSing.c_str() : activeStack->getCreature()->namePl.c_str());
|
||||
}
|
||||
|
||||
console->alterTxt = buf;
|
||||
@ -2894,11 +2895,42 @@ void CBattleInterface::hexLclicked(int whichOne)
|
||||
endCastingSpell();
|
||||
}
|
||||
}
|
||||
else //we don't aim for spell target
|
||||
else //we don't aim for spell target area
|
||||
{
|
||||
bool walkableTile = false;
|
||||
if (dest)
|
||||
{
|
||||
bool ourStack = actSt->owner == dest->owner;
|
||||
|
||||
//try to cast stack spell first
|
||||
if (stackCanCastSpell && spellSelMode > STACK_SPELL_CANCELLED) //player did not decide to cancel this spell
|
||||
{
|
||||
if ((int)creatureSpellToCast > -1) //use randomized spell (Faerie Dragon), or only avaliable spell (Archangel)
|
||||
{
|
||||
const CSpell * spell = CGI->spellh->spells[creatureSpellToCast];
|
||||
if (curInt->cb->battleCanCastThisSpell(spell, THex(whichOne)) == SpellCasting::OK)
|
||||
{
|
||||
if (spell->positiveness > -1 && ourStack || spell->positiveness < 1 && !ourStack)
|
||||
{
|
||||
giveCommand(BattleAction::MONSTER_SPELL, whichOne, actSt->ID, creatureSpellToCast);
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (ourStack) //must have only random positive spell (genie)
|
||||
{
|
||||
if (dest != actSt) //can't cast on itself
|
||||
{
|
||||
int spellID = curInt->cb->battleGetRandomStackSpell(dest, CBattleInfoCallback::RANDOM_GENIE);
|
||||
if (spellID > -1) //can cast any spell on target stack
|
||||
{
|
||||
giveCommand(BattleAction::MONSTER_SPELL, whichOne, actSt->ID, spellID); //use randomized spell
|
||||
}
|
||||
}
|
||||
}
|
||||
creatureSpellToCast = -1;
|
||||
return; //no further action after cast
|
||||
}
|
||||
|
||||
if (dest->alive())
|
||||
{
|
||||
if(dest->owner != actSt->owner && curInt->cb->battleCanShoot(activeStack, whichOne)) //shooting
|
||||
@ -2906,7 +2938,7 @@ void CBattleInterface::hexLclicked(int whichOne)
|
||||
CCS->curh->changeGraphic(1, 6); //cursor should be changed
|
||||
giveCommand (BattleAction::SHOOT, whichOne, activeStack->ID);
|
||||
}
|
||||
else if(dest->owner != actSt->owner) //attacking
|
||||
else if(!ourStack) //attacking
|
||||
{
|
||||
const CStack * actStack = activeStack;
|
||||
int attackFromHex = -1; //hex from which we will attack chosen stack
|
||||
|
@ -396,8 +396,8 @@
|
||||
"level": 5,
|
||||
"name": [ "Caliph" ],
|
||||
"faction": 2,
|
||||
"ability_add": [ [ "CREATURE_ENCHANT_POWER", 5, 0, 0 ], //spells last 6 turns
|
||||
[ "RANDOM_SPELLCASTER", 0, 0, 0 ], //master genies cast spells
|
||||
"ability_add": [ [ "CREATURE_ENCHANT_POWER", 5, 0, 0 ], //spells last 5 turns
|
||||
[ "RANDOM_SPELLCASTER", 2, 0, 0 ], //master genies cast spells on advanced level
|
||||
[ "CASTS", 3, 0, 0],
|
||||
[ "HATE", 50, 53, 0 ],
|
||||
[ "HATE", 50, 52, 0 ] ], //master genies hate efreet sultans
|
||||
@ -1293,7 +1293,7 @@
|
||||
"faction": 8,
|
||||
"ability_add": [ [ "NON_LIVING", 0, 0, 0 ],
|
||||
[ "DOUBLE_WIDE", 0, 0, 0 ], //ice elemental should be treated as double-wide
|
||||
[ "CREATURE_ENCHANT_POWER", 5, 0, 0 ],
|
||||
[ "CREATURE_ENCHANT_POWER", 6, 0, 0 ],
|
||||
[ "CASTS", 3, 0, 0 ],
|
||||
[ "SPELLCASTER", 2, 32, 0 ]],
|
||||
"defname": "CICEE.DEF",
|
||||
@ -1307,7 +1307,7 @@
|
||||
"name": [ "StoneElemental" ],
|
||||
"faction": 8,
|
||||
"ability_add": [ [ "NON_LIVING", 0, 0, 0 ], //magma elementals shouldn't get morale
|
||||
[ "CREATURE_ENCHANT_POWER", 5, 0, 0 ],
|
||||
[ "CREATURE_ENCHANT_POWER", 6, 0, 0 ],
|
||||
[ "CASTS", 3, 0, 0 ],
|
||||
[ "SPELLCASTER", 2, 33, 0 ]],
|
||||
"defname": "CSTONE.DEF"
|
||||
@ -1319,7 +1319,7 @@
|
||||
"name": [ "StormElemental" ],
|
||||
"faction": 8,
|
||||
"ability_add": [ [ "NON_LIVING", 0, 0, 0 ], //storm elementals shouldn't get morale
|
||||
[ "CREATURE_ENCHANT_POWER", 5, 0, 0 ],
|
||||
[ "CREATURE_ENCHANT_POWER", 6, 0, 0 ],
|
||||
[ "CASTS", 3, 0, 0 ],
|
||||
[ "SPELLCASTER", 2, 30, 0 ]],
|
||||
"defname": "CSTORM.DEF",
|
||||
@ -1334,7 +1334,7 @@
|
||||
"name": [ "ElectricityElemental" ],
|
||||
"faction": 8,
|
||||
"ability_add": [ [ "NON_LIVING", 0, 0, 0 ] , //energy elementals shouldn't get morale //Crystal Dragons do not fly
|
||||
[ "CREATURE_ENCHANT_POWER", 5, 0, 0 ],
|
||||
[ "CREATURE_ENCHANT_POWER", 6, 0, 0 ],
|
||||
[ "CASTS", 3, 0, 0 ],
|
||||
[ "SPELLCASTER", 2, 31, 0 ]],
|
||||
"defname": "CNRG.DEF"
|
||||
|
@ -2007,6 +2007,9 @@ TSpell BattleInfo::getRandomBeneficialSpell(const CStack * subject) const
|
||||
continue;
|
||||
}
|
||||
break;
|
||||
case 65: //clone - not allowed
|
||||
continue;
|
||||
break;
|
||||
}
|
||||
possibleSpells.push_back(i);
|
||||
}
|
||||
|
@ -102,7 +102,7 @@ namespace PrimarySkill
|
||||
BONUS_NAME(SPELL_DAMAGE_REDUCTION) /*eg. golems; value - reduction in %, subtype - spell school; -1 - all, 0 - air, 1 - fire, 2 - water, 3 - earth*/ \
|
||||
BONUS_NAME(NO_WALL_PENALTY) \
|
||||
BONUS_NAME(NON_LIVING) /*eg. gargoyle*/ \
|
||||
BONUS_NAME(RANDOM_SPELLCASTER) /*eg. master genie, For Genie spells, subtype - spell id */ \
|
||||
BONUS_NAME(RANDOM_SPELLCASTER) /*eg. master genie, val - level*/ \
|
||||
BONUS_NAME(BLOCKS_RETALIATION) /*eg. naga*/ \
|
||||
BONUS_NAME(SPELL_IMMUNITY) /*subid - spell id*/ \
|
||||
BONUS_NAME(MANA_CHANNELING) /*value in %, eg. familiar*/ \
|
||||
|
@ -1278,15 +1278,16 @@ DLL_EXPORT void BattleStackAdded::applyGs(CGameState *gs)
|
||||
|
||||
DLL_EXPORT void BattleSetStackProperty::applyGs(CGameState *gs)
|
||||
{
|
||||
CStack * stack = gs->curB->getStack(stackID);
|
||||
switch (which)
|
||||
{
|
||||
case CASTS:
|
||||
{
|
||||
if (absolute)
|
||||
gs->curB->stacks[stackID]->casts = val;
|
||||
stack->casts = val;
|
||||
else
|
||||
gs->curB->stacks[stackID]->casts--;
|
||||
amax(gs->curB->stacks[stackID]->casts, 0);
|
||||
stack->casts += val;
|
||||
amax(stack->casts, 0);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -3312,12 +3312,45 @@ bool CGameHandler::makeBattleAction( BattleAction &ba )
|
||||
|
||||
BattleSetStackProperty ssp;
|
||||
ssp.stackID = ba.stackNumber;
|
||||
ssp.which = BattleSetStackProperty::CASTS;
|
||||
ssp.which = BattleSetStackProperty::CASTS; //reduce number of casts
|
||||
ssp.val = -1;
|
||||
ssp.absolute = false;
|
||||
sendAndApply(&ssp);
|
||||
}
|
||||
|
||||
sendAndApply(&end_action);
|
||||
break;
|
||||
}
|
||||
case BattleAction::MONSTER_SPELL:
|
||||
{
|
||||
StartAction start_action(ba);
|
||||
sendAndApply(&start_action);
|
||||
|
||||
CStack * stack = gs->curB->getStack(ba.stackNumber);
|
||||
int spellID = ba.additionalInfo;
|
||||
THex destination(ba.destinationTile);
|
||||
|
||||
int spellLvl = 0;
|
||||
Bonus * bonus = stack->getBonus(Selector::typeSubtype(Bonus::SPELLCASTER, spellID));
|
||||
if (bonus)
|
||||
amax(spellLvl, bonus->val);
|
||||
bonus = stack->getBonus(Selector::type(Bonus::RANDOM_SPELLCASTER));
|
||||
if (bonus)
|
||||
amax(spellLvl, bonus->val);
|
||||
amin (spellLvl, 3);
|
||||
|
||||
int casterSide = gs->curB->whatSide(stack->owner);
|
||||
const CGHeroInstance * secHero = gs->curB->getHero(gs->curB->theOtherPlayer(stack->owner));
|
||||
|
||||
handleSpellCasting(spellID, spellLvl, destination, casterSide, stack->owner, NULL, secHero, 0, SpellCasting::CREATURE_ACTIVE_CASTING, stack);
|
||||
|
||||
BattleSetStackProperty ssp;
|
||||
ssp.stackID = ba.stackNumber;
|
||||
ssp.which = BattleSetStackProperty::CASTS; //reduce number of casts
|
||||
ssp.val = -1;
|
||||
ssp.absolute = false;
|
||||
sendAndApply(&ssp);
|
||||
|
||||
sendAndApply(&end_action);
|
||||
break;
|
||||
}
|
||||
@ -3520,7 +3553,10 @@ void CGameHandler::handleSpellCasting( int spellID, int spellLvl, THex destinati
|
||||
if (unitSpellPower)
|
||||
sc.dmgToDisplay = spellDamage = stack->count * unitSpellPower; //TODO: handle immunities
|
||||
else //Faerie Dragon
|
||||
{
|
||||
usedSpellPower = stack->valOfBonuses(Bonus::CREATURE_SPELL_POWER) * stack->count / 100;
|
||||
sc.dmgToDisplay = 0;
|
||||
}
|
||||
}
|
||||
for(std::set<CStack*>::iterator it = attackedCres.begin(); it != attackedCres.end(); ++it)
|
||||
{
|
||||
@ -3536,7 +3572,10 @@ void CGameHandler::handleSpellCasting( int spellID, int spellLvl, THex destinati
|
||||
if (spellDamage)
|
||||
bsa.damageAmount = spellDamage;
|
||||
else
|
||||
{
|
||||
bsa.damageAmount = gs->curB->calculateSpellDmg(spell, caster, *it, spellLvl, usedSpellPower);
|
||||
sc.dmgToDisplay += bsa.damageAmount;
|
||||
}
|
||||
bsa.stackAttacked = (*it)->ID;
|
||||
bsa.attackerID = -1;
|
||||
(*it)->prepareAttacked(bsa);
|
||||
|
Loading…
Reference in New Issue
Block a user