mirror of
https://github.com/vcmi/vcmi.git
synced 2025-02-03 13:01:33 +02:00
Fixes for battle interface, including #932. Basic funtionality is restored.
This commit is contained in:
parent
918452d37c
commit
f9dff013eb
@ -570,14 +570,14 @@ void CBattleInterface::show(SDL_Surface * to)
|
||||
//calculating spell school level
|
||||
const CSpell & spToCast = *CGI->spellh->spells[spellToCast->additionalInfo];
|
||||
ui8 schoolLevel = 0;
|
||||
if( activeStack->attackerOwned )
|
||||
if (activeStack->attackerOwned)
|
||||
{
|
||||
if(attackingHeroInstance)
|
||||
schoolLevel = attackingHeroInstance->getSpellSchoolLevel(&spToCast);
|
||||
}
|
||||
else
|
||||
{
|
||||
if(defendingHeroInstance)
|
||||
if (defendingHeroInstance)
|
||||
schoolLevel = defendingHeroInstance->getSpellSchoolLevel(&spToCast);
|
||||
}
|
||||
//obtaining range and printing it
|
||||
@ -1801,34 +1801,34 @@ void CBattleInterface::castThisSpell(int spellID)
|
||||
|
||||
//choosing possible tragets
|
||||
const CGHeroInstance * castingHero = (attackingHeroInstance->tempOwner == curInt->playerID) ? attackingHeroInstance : defendingHeroInstance;
|
||||
const CSpell & spell = *CGI->spellh->spells[spellID];
|
||||
sp = CGI->spellh->spells[spellID];
|
||||
spellSelMode = ANY_LOCATION;
|
||||
if(spell.getTargetType() == CSpell::CREATURE)
|
||||
if(sp->getTargetType() == CSpell::CREATURE)
|
||||
{
|
||||
spellSelMode = selectionTypeByPositiveness(spell);
|
||||
spellSelMode = selectionTypeByPositiveness(*sp);
|
||||
}
|
||||
if(spell.getTargetType() == CSpell::CREATURE_EXPERT_MASSIVE)
|
||||
if(sp->getTargetType() == CSpell::CREATURE_EXPERT_MASSIVE)
|
||||
{
|
||||
if(castingHero && castingHero->getSpellSchoolLevel(&spell) < 3)
|
||||
spellSelMode = selectionTypeByPositiveness(spell);
|
||||
if(castingHero && castingHero->getSpellSchoolLevel(sp) < 3)
|
||||
spellSelMode = selectionTypeByPositiveness(*sp);
|
||||
else
|
||||
spellSelMode = NO_LOCATION;
|
||||
}
|
||||
if(spell.getTargetType() == CSpell::OBSTACLE)
|
||||
if(sp->getTargetType() == CSpell::OBSTACLE)
|
||||
{
|
||||
spellSelMode = OBSTACLE;
|
||||
}
|
||||
if(spell.range[ castingHero->getSpellSchoolLevel(&spell) ] == "X") //spell has no range
|
||||
if(sp->range[ castingHero->getSpellSchoolLevel(sp) ] == "X") //spell has no range
|
||||
{
|
||||
spellSelMode = NO_LOCATION;
|
||||
}
|
||||
|
||||
if(spell.id == 63) //teleport
|
||||
if(sp->id == Spells::TELEPORT) //teleport
|
||||
{
|
||||
spellSelMode = TELEPORT;
|
||||
spellSelMode = TELEPORT; //FIXME: duplicating?
|
||||
}
|
||||
|
||||
if(spell.range[ castingHero->getSpellSchoolLevel(&spell) ].size() > 1) //spell has many-hex range
|
||||
if(sp->range[ castingHero->getSpellSchoolLevel(sp) ].size() > 1) //spell has many-hex range
|
||||
{
|
||||
spellSelMode = ANY_LOCATION;
|
||||
}
|
||||
@ -1971,16 +1971,17 @@ void CBattleInterface::endCastingSpell()
|
||||
|
||||
delete spellToCast;
|
||||
spellToCast = NULL;
|
||||
sp = NULL;
|
||||
spellDestSelectMode = false;
|
||||
CCS->curh->changeGraphic(1, 6);
|
||||
|
||||
//restore actions for current stack
|
||||
possibleActions.clear();
|
||||
getPossibleActionsForStack (activeStack);
|
||||
}
|
||||
|
||||
void CBattleInterface::getPossibleActionsForStack(const CStack * stack)
|
||||
{
|
||||
possibleActions.clear();
|
||||
//first action will be prioritized over later ones
|
||||
if (stack->casts) //TODO: check for battlefield effects that prevent casting?
|
||||
{
|
||||
@ -2013,6 +2014,9 @@ void CBattleInterface::getPossibleActionsForStack(const CStack * stack)
|
||||
}
|
||||
|
||||
}
|
||||
std::sort(possibleActions.begin(), possibleActions.end());
|
||||
auto it = std::unique (possibleActions.begin(), possibleActions.end());
|
||||
possibleActions.erase (it, possibleActions.end());
|
||||
}
|
||||
if (stack->hasBonusOfType (Bonus::RANDOM_SPELLCASTER))
|
||||
possibleActions.push_back (RANDOM_GENIE_SPELL);
|
||||
@ -2605,6 +2609,19 @@ std::string formatDmgRange(std::pair<ui32, ui32> dmgRange)
|
||||
return (boost::format("%d") % dmgRange.first).str();
|
||||
}
|
||||
|
||||
bool CBattleInterface::canStackMoveHere (const CStack * activeStack, BattleHex myNumber)
|
||||
{
|
||||
std::vector<BattleHex> acc = curInt->cb->battleGetAvailableHexes (activeStack, false);
|
||||
int shiftedDest = myNumber + (activeStack->attackerOwned ? 1 : -1);
|
||||
|
||||
if (vstd::contains(acc, myNumber))
|
||||
return true;
|
||||
else if (activeStack->doubleWide() && vstd::contains(acc, shiftedDest))
|
||||
return true;
|
||||
else
|
||||
return false;
|
||||
}
|
||||
|
||||
void CBattleInterface::handleHex(BattleHex myNumber, int eventType)
|
||||
{
|
||||
if(!myTurn) //we are not permit to do anything
|
||||
@ -2671,12 +2688,7 @@ void CBattleInterface::handleHex(BattleHex myNumber, int eventType)
|
||||
break;
|
||||
case MOVE_STACK:
|
||||
{
|
||||
std::vector<BattleHex> acc = curInt->cb->battleGetAvailableHexes (activeStack, false);
|
||||
int shiftedDest = myNumber + (activeStack->attackerOwned ? 1 : -1);
|
||||
|
||||
if (vstd::contains(acc, myNumber))
|
||||
legalAction = true;
|
||||
else if (sactive->doubleWide() && vstd::contains(acc, shiftedDest))
|
||||
if (canStackMoveHere (sactive, myNumber))
|
||||
legalAction = true;
|
||||
}
|
||||
break;
|
||||
@ -2684,13 +2696,16 @@ void CBattleInterface::handleHex(BattleHex myNumber, int eventType)
|
||||
case WALK_AND_ATTACK:
|
||||
case ATTACK_AND_RETURN:
|
||||
{
|
||||
if (shere && shere->alive())
|
||||
if (shere && !ourStack && shere->alive())
|
||||
{
|
||||
setBattleCursor(myNumber); // temporary - needed for following function :(
|
||||
BattleHex attackFromHex = fromWhichHexAttack(myNumber);
|
||||
if (isTileAttackable(myNumber))
|
||||
{
|
||||
setBattleCursor(myNumber); // temporary - needed for following function :(
|
||||
BattleHex attackFromHex = fromWhichHexAttack(myNumber);
|
||||
|
||||
if (isTileAttackable(myNumber) && attackFromHex >= 0) //we can be in this line when unreachable creature is L - clicked (as of revision 1308)
|
||||
legalAction = true;
|
||||
if (attackFromHex >= 0) //we can be in this line when unreachable creature is L - clicked (as of revision 1308)
|
||||
legalAction = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
@ -2728,8 +2743,11 @@ void CBattleInterface::handleHex(BattleHex myNumber, int eventType)
|
||||
break;
|
||||
case TELEPORT:
|
||||
{
|
||||
const ui8 skill = spellToCast ? getActiveHero()->getSpellSchoolLevel(CGI->spellh->spells[spellToCast->additionalInfo]) : 0; //skill level
|
||||
//TODO: creature can cast a spell with some skill / spellpower as well
|
||||
ui8 skill = 0;
|
||||
if (creatureCasting)
|
||||
skill = sactive->valOfBonuses(Selector::typeSubtype(Bonus::SPELLCASTER, Spells::TELEPORT));
|
||||
else
|
||||
skill = getActiveHero()->getSpellSchoolLevel (CGI->spellh->spells[spellToCast->additionalInfo]);
|
||||
//TODO: explicitely save power, skill
|
||||
if (curInt->cb->battleCanTeleportTo(activeStack, myNumber, skill))
|
||||
legalAction = true;
|
||||
@ -2853,14 +2871,26 @@ void CBattleInterface::handleHex(BattleHex myNumber, int eventType)
|
||||
case FRIENDLY_CREATURE_SPELL:
|
||||
case RISING_SPELL:
|
||||
case RANDOM_GENIE_SPELL:
|
||||
if (spellToCast) //TODO: merge hero spell and creature spell into it
|
||||
if (sp)
|
||||
{
|
||||
consoleMsg = boost::str(boost::format(CGI->generaltexth->allTexts[27]) % sp->name % shere->getName()); //Cast %s on %s
|
||||
else
|
||||
consoleMsg = boost::str(boost::format(CGI->generaltexth->allTexts[301]) % shere->getName()); //Cast a spell on %s
|
||||
|
||||
isCastingPossible = true;
|
||||
|
||||
//TODO: refactor -> include Teleport and Remove Obstacle
|
||||
switch (sp->id)
|
||||
{
|
||||
case Spells::TELEPORT: //don't cast spell yet, only select target
|
||||
possibleActions.clear();
|
||||
possibleActions.push_back (TELEPORT);
|
||||
break;
|
||||
case Spells::SACRIFICE:
|
||||
possibleActions.clear();
|
||||
possibleActions.push_back (SACRIFICE);
|
||||
break;
|
||||
default:
|
||||
isCastingPossible = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
else //spell is random
|
||||
consoleMsg = boost::str(boost::format(CGI->generaltexth->allTexts[301]) % shere->getName()); //Cast a spell on %
|
||||
break;
|
||||
case TELEPORT:
|
||||
consoleMsg = CGI->generaltexth->allTexts[25]; //Teleport Here
|
||||
@ -2935,30 +2965,16 @@ void CBattleInterface::handleHex(BattleHex myNumber, int eventType)
|
||||
|
||||
realizeAction = [=]
|
||||
{
|
||||
switch (sp->id)
|
||||
if(creatureCasting)
|
||||
{
|
||||
case TELEPORT: //TODO: choose second target for Teleport or Sacrifice
|
||||
possibleActions.clear();
|
||||
possibleActions.push_back (TELEPORT);
|
||||
break;
|
||||
case SACRIFICE:
|
||||
possibleActions.clear();
|
||||
possibleActions.push_back (SACRIFICE);
|
||||
break;
|
||||
default:
|
||||
if(creatureCasting)
|
||||
{
|
||||
giveCommand(BattleAction::MONSTER_SPELL, myNumber, sactive->ID, creatureSpellToCast);
|
||||
}
|
||||
else
|
||||
{
|
||||
spellToCast->destinationTile = myNumber;
|
||||
curInt->cb->battleMakeAction(spellToCast);
|
||||
endCastingSpell();
|
||||
}
|
||||
break;
|
||||
giveCommand(BattleAction::MONSTER_SPELL, myNumber, sactive->ID, creatureSpellToCast);
|
||||
}
|
||||
else
|
||||
{
|
||||
spellToCast->destinationTile = myNumber;
|
||||
curInt->cb->battleMakeAction(spellToCast);
|
||||
endCastingSpell();
|
||||
}
|
||||
|
||||
};
|
||||
}
|
||||
|
||||
@ -2970,9 +2986,7 @@ void CBattleInterface::handleHex(BattleHex myNumber, int eventType)
|
||||
|
||||
bool CBattleInterface::isCastingPossibleHere (const CStack * sactive, const CStack * shere, BattleHex myNumber)
|
||||
{
|
||||
creatureCasting = (spellDestSelectMode >= NO_LOCATION && spellDestSelectMode <= RANDOM_GENIE_SPELL) && //what does it really check?
|
||||
stackCanCastSpell && shere != sactive;
|
||||
//TODO: use currentAction
|
||||
creatureCasting = (stackCanCastSpell) && (shere != sactive); //is it really useful?
|
||||
|
||||
bool isCastingPossible = true;
|
||||
|
||||
@ -2980,7 +2994,7 @@ bool CBattleInterface::isCastingPossibleHere (const CStack * sactive, const CSta
|
||||
if (creatureCasting)
|
||||
{
|
||||
if (creatureSpellToCast > -1)
|
||||
spellID = creatureSpellToCast;
|
||||
spellID = creatureSpellToCast; //TODO: merge with SpellTocast?
|
||||
}
|
||||
else if(spellDestSelectMode) //hero casting
|
||||
spellID = spellToCast->additionalInfo;
|
||||
|
@ -132,7 +132,7 @@ private:
|
||||
bool tacticsMode;
|
||||
bool stackCanCastSpell; //if true, active stack could possibly cats some target spell
|
||||
bool creatureCasting; //if true, stack currently aims to cats a spell
|
||||
bool spellDestSelectMode; //if true, player is choosing destination for his spell
|
||||
bool spellDestSelectMode; //if true, player is choosing destination for his spell - only for GUI / console
|
||||
PossibleActions spellSelMode;
|
||||
BattleAction * spellToCast; //spell for which player is choosing destination
|
||||
const CSpell * sp; //spell pointer for convenience
|
||||
@ -264,6 +264,7 @@ public:
|
||||
|
||||
void handleHex(BattleHex myNumber, int eventType);
|
||||
bool isCastingPossibleHere (const CStack * sactive, const CStack * shere, BattleHex myNumber);
|
||||
bool canStackMoveHere (const CStack * sactive, BattleHex MyNumber); //TODO: move to BattleState / callback
|
||||
|
||||
BattleHex fromWhichHexAttack(BattleHex myNumber);
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user