1
0
mirror of https://github.com/vcmi/vcmi.git synced 2025-06-23 00:28:08 +02:00
Files
.github
AI
BattleAI
AttackPossibility.cpp
AttackPossibility.h
BattleAI.cbp
BattleAI.cpp
BattleAI.h
BattleAI.vcxproj
BattleEvaluator.cpp
BattleEvaluator.h
BattleExchangeVariant.cpp
BattleExchangeVariant.h
CMakeLists.txt
EnemyInfo.cpp
EnemyInfo.h
PossibleSpellcast.cpp
PossibleSpellcast.h
PotentialTargets.cpp
PotentialTargets.h
StackWithBonuses.cpp
StackWithBonuses.h
StdInc.cpp
StdInc.h
ThreatMap.cpp
ThreatMap.h
common.cpp
common.h
main.cpp
EmptyAI
FuzzyLite
Nullkiller
StupidAI
VCAI
CMakeLists.txt
FuzzyLite.cbp
GeniusAI.brain
CI
Mods
android
client
cmake_modules
config
debian
docs
include
ios
launcher
lib
lib_server
mapeditor
osx
rpm
scripting
scripts
server
test
win
xcode
.gitattributes
.gitignore
.gitmodules
.travis.yml
AUTHORS.h
CCallback.cpp
CCallback.h
CMakeLists.txt
CMakePresets.json
ChangeLog.md
Global.h
VCMI_VS15.sln
VCMI_global.props
VCMI_global_debug.props
VCMI_global_release.props
VCMI_global_user.props
Version.cpp.in
Version.h
conanfile.py
fuzzylite.pc.in
license.txt
vcmi.workspace
vcmibuilder
vcmi/AI/BattleAI/StackWithBonuses.cpp
Alexander Wilms 73019c204d Replace redundant types with auto for the lvalues of template factory functions for smart pointers
grep -r --include \*.h --include \*.cpp "= std::" * | grep -v auto | grep -Po ".*[^ ]+ [^ ]+ [^ ]*[ ]*=.*;" | grep -v "auto\|int\|char\|bool\|float|\double\|for\|if\|googletest\|fuzzylite\|size_t\|using\|return" | grep -v double | grep -v si64 | grep -v si32 | grep -v ui32 | grep \< | grep -v float | tr -d '\t' | grep -v assert > redundant_types.txt

import re

with open("redundant_types.txt") as f:
    for line in f:
        line = line.strip()
        path = line.split(":", 1)[0]
        original_code = ":".join(line.split(":")[1:]).strip()

        print()
        print(path)
        print(original_code)
        prefix = "auto "
        if original_code.startswith("static"):
            static = True
        else:
            static = False

        cpp_type = " ".join(original_code.split("=")[0].strip().split(" ")[0:-1])
        print(cpp_type)

        if static:
            new_code = "static auto "+ " ".join(original_code.split(" ")[2:])
        else:
            new_code = "auto "+ " ".join(original_code.split(" ")[1:])
        print(new_code)

        if True:
            with open(path, "r") as f:
                filedata = f.read()

            filedata = filedata.replace(original_code, new_code)

            with open(path, "w") as f:
                f.write(filedata)
2024-01-17 12:50:00 +00:00

600 lines
13 KiB
C++

/*
* StackWithBonuses.cpp, part of VCMI engine
*
* Authors: listed in file AUTHORS in main folder
*
* License: GNU General Public License v2.0 or later
* Full text of license available in license.txt file, in main folder
*
*/
#include "StdInc.h"
#include "StackWithBonuses.h"
#include <vcmi/events/EventBus.h>
#include "../../lib/CStack.h"
#include "../../lib/ScriptHandler.h"
#include "../../lib/networkPacks/PacksForClientBattle.h"
#include "../../lib/networkPacks/SetStackEffect.h"
#if SCRIPTING_ENABLED
using scripting::Pool;
#endif
void actualizeEffect(TBonusListPtr target, const Bonus & ef)
{
for(auto & bonus : *target) //TODO: optimize
{
if(bonus->source == BonusSource::SPELL_EFFECT && bonus->type == ef.type && bonus->subtype == ef.subtype)
{
if(bonus->turnsRemain < ef.turnsRemain)
{
bonus.reset(new Bonus(*bonus));
bonus->turnsRemain = ef.turnsRemain;
}
}
}
}
StackWithBonuses::StackWithBonuses(const HypotheticBattle * Owner, const battle::CUnitState * Stack)
: battle::CUnitState(),
origBearer(Stack->getBonusBearer()),
owner(Owner),
type(Stack->unitType()),
baseAmount(Stack->unitBaseAmount()),
id(Stack->unitId()),
side(Stack->unitSide()),
player(Stack->unitOwner()),
slot(Stack->unitSlot()),
treeVersionLocal(0)
{
localInit(Owner);
battle::CUnitState::operator=(*Stack);
}
StackWithBonuses::StackWithBonuses(const HypotheticBattle * Owner, const battle::Unit * Stack)
: battle::CUnitState(),
origBearer(Stack->getBonusBearer()),
owner(Owner),
type(Stack->unitType()),
baseAmount(Stack->unitBaseAmount()),
id(Stack->unitId()),
side(Stack->unitSide()),
player(Stack->unitOwner()),
slot(Stack->unitSlot()),
treeVersionLocal(0)
{
localInit(Owner);
auto state = Stack->acquireState();
battle::CUnitState::operator=(*state);
}
StackWithBonuses::StackWithBonuses(const HypotheticBattle * Owner, const battle::UnitInfo & info)
: battle::CUnitState(),
origBearer(nullptr),
owner(Owner),
baseAmount(info.count),
id(info.id),
side(info.side),
slot(SlotID::SUMMONED_SLOT_PLACEHOLDER),
treeVersionLocal(0)
{
type = info.type.toCreature();
origBearer = type;
player = Owner->getSidePlayer(side);
localInit(Owner);
position = info.position;
summoned = info.summoned;
}
StackWithBonuses::~StackWithBonuses() = default;
StackWithBonuses & StackWithBonuses::operator=(const battle::CUnitState & other)
{
battle::CUnitState::operator=(other);
return *this;
}
const CCreature * StackWithBonuses::unitType() const
{
return type;
}
int32_t StackWithBonuses::unitBaseAmount() const
{
return baseAmount;
}
uint32_t StackWithBonuses::unitId() const
{
return id;
}
ui8 StackWithBonuses::unitSide() const
{
return side;
}
PlayerColor StackWithBonuses::unitOwner() const
{
return player;
}
SlotID StackWithBonuses::unitSlot() const
{
return slot;
}
TConstBonusListPtr StackWithBonuses::getAllBonuses(const CSelector & selector, const CSelector & limit,
const CBonusSystemNode * root, const std::string & cachingStr) const
{
auto ret = std::make_shared<BonusList>();
TConstBonusListPtr originalList = origBearer->getAllBonuses(selector, limit, root, cachingStr);
vstd::copy_if(*originalList, std::back_inserter(*ret), [this](const std::shared_ptr<Bonus> & b)
{
return !vstd::contains(bonusesToRemove, b);
});
for(const Bonus & bonus : bonusesToUpdate)
{
if(selector(&bonus) && (!limit || limit(&bonus)))
{
if(ret->getFirst(Selector::source(BonusSource::SPELL_EFFECT, bonus.sid).And(Selector::typeSubtype(bonus.type, bonus.subtype))))
{
actualizeEffect(ret, bonus);
}
else
{
auto b = std::make_shared<Bonus>(bonus);
ret->push_back(b);
}
}
}
for(auto & bonus : bonusesToAdd)
{
auto b = std::make_shared<Bonus>(bonus);
if(selector(b.get()) && (!limit || !limit(b.get())))
ret->push_back(b);
}
//TODO limiters?
return ret;
}
int64_t StackWithBonuses::getTreeVersion() const
{
auto result = owner->getTreeVersion();
if(bonusesToAdd.empty() && bonusesToUpdate.empty() && bonusesToRemove.empty())
return result;
else
return result + treeVersionLocal;
}
void StackWithBonuses::addUnitBonus(const std::vector<Bonus> & bonus)
{
vstd::concatenate(bonusesToAdd, bonus);
treeVersionLocal++;
}
void StackWithBonuses::updateUnitBonus(const std::vector<Bonus> & bonus)
{
//TODO: optimize, actualize to last value
vstd::concatenate(bonusesToUpdate, bonus);
treeVersionLocal++;
}
void StackWithBonuses::removeUnitBonus(const std::vector<Bonus> & bonus)
{
for(auto & one : bonus)
{
CSelector selector([&one](const Bonus * b) -> bool
{
//compare everything but turnsRemain, limiter and propagator
return one.duration == b->duration
&& one.type == b->type
&& one.subtype == b->subtype
&& one.source == b->source
&& one.val == b->val
&& one.sid == b->sid
&& one.valType == b->valType
&& one.additionalInfo == b->additionalInfo
&& one.effectRange == b->effectRange
&& one.description == b->description;
});
removeUnitBonus(selector);
}
}
void StackWithBonuses::removeUnitBonus(const CSelector & selector)
{
TConstBonusListPtr toRemove = origBearer->getBonuses(selector);
for(auto b : *toRemove)
bonusesToRemove.insert(b);
vstd::erase_if(bonusesToAdd, [&](const Bonus & b){return selector(&b);});
vstd::erase_if(bonusesToUpdate, [&](const Bonus & b){return selector(&b);});
treeVersionLocal++;
}
std::string StackWithBonuses::getDescription() const
{
std::ostringstream oss;
oss << unitOwner().toString();
oss << " battle stack [" << unitId() << "]: " << getCount() << " of ";
if(type)
oss << type->getJsonKey();
else
oss << "[UNDEFINED TYPE]";
oss << " from slot " << slot;
return oss.str();
}
void StackWithBonuses::spendMana(ServerCallback * server, const int spellCost) const
{
//TODO: evaluate cast use
}
HypotheticBattle::HypotheticBattle(const Environment * ENV, Subject realBattle)
: BattleProxy(realBattle),
env(ENV),
bonusTreeVersion(1)
{
auto activeUnit = realBattle->battleActiveUnit();
activeUnitId = activeUnit ? activeUnit->unitId() : -1;
nextId = 0x00F00000;
eventBus.reset(new events::EventBus());
localEnvironment.reset(new HypotheticEnvironment(this, env));
serverCallback.reset(new HypotheticServerCallback(this));
#if SCRIPTING_ENABLED
pool.reset(new scripting::PoolImpl(localEnvironment.get(), serverCallback.get()));
#endif
}
bool HypotheticBattle::unitHasAmmoCart(const battle::Unit * unit) const
{
//FIXME: check ammocart alive state here
return false;
}
PlayerColor HypotheticBattle::unitEffectiveOwner(const battle::Unit * unit) const
{
return battleGetOwner(unit);
}
std::shared_ptr<StackWithBonuses> HypotheticBattle::getForUpdate(uint32_t id)
{
auto iter = stackStates.find(id);
if(iter == stackStates.end())
{
const battle::Unit * s = subject->battleGetUnitByID(id);
auto ret = std::make_shared<StackWithBonuses>(this, s);
stackStates[id] = ret;
return ret;
}
else
{
return iter->second;
}
}
battle::Units HypotheticBattle::getUnitsIf(const battle::UnitFilter & predicate) const
{
battle::Units proxyed = BattleProxy::getUnitsIf(predicate);
battle::Units ret;
ret.reserve(proxyed.size());
for(auto unit : proxyed)
{
//unit was not changed, trust proxyed data
if(stackStates.find(unit->unitId()) == stackStates.end())
ret.push_back(unit);
}
for(auto id_unit : stackStates)
{
if(predicate(id_unit.second.get()))
ret.push_back(id_unit.second.get());
}
return ret;
}
BattleID HypotheticBattle::getBattleID() const
{
return subject->getBattle()->getBattleID();
}
int32_t HypotheticBattle::getActiveStackID() const
{
return activeUnitId;
}
void HypotheticBattle::nextRound()
{
//TODO:HypotheticBattle::nextRound
for(auto unit : battleAliveUnits())
{
auto forUpdate = getForUpdate(unit->unitId());
//TODO: update Bonus::NTurns effects
forUpdate->afterNewRound();
}
}
void HypotheticBattle::nextTurn(uint32_t unitId)
{
activeUnitId = unitId;
auto unit = getForUpdate(unitId);
unit->removeUnitBonus(Bonus::UntilGetsTurn);
unit->afterGetsTurn();
}
void HypotheticBattle::addUnit(uint32_t id, const JsonNode & data)
{
battle::UnitInfo info;
info.load(id, data);
auto newUnit = std::make_shared<StackWithBonuses>(this, info);
stackStates[newUnit->unitId()] = newUnit;
}
void HypotheticBattle::moveUnit(uint32_t id, BattleHex destination)
{
std::shared_ptr<StackWithBonuses> changed = getForUpdate(id);
changed->position = destination;
}
void HypotheticBattle::setUnitState(uint32_t id, const JsonNode & data, int64_t healthDelta)
{
std::shared_ptr<StackWithBonuses> changed = getForUpdate(id);
changed->load(data);
if(healthDelta < 0)
{
changed->removeUnitBonus(Bonus::UntilBeingAttacked);
}
}
void HypotheticBattle::removeUnit(uint32_t id)
{
std::set<uint32_t> ids;
ids.insert(id);
while(!ids.empty())
{
auto toRemoveId = *ids.begin();
auto toRemove = getForUpdate(toRemoveId);
if(!toRemove->ghost)
{
toRemove->onRemoved();
//TODO: emulate detachFromAll() somehow
//stack may be removed instantly (not being killed first)
//handle clone remove also here
if(toRemove->cloneID >= 0)
{
ids.insert(toRemove->cloneID);
toRemove->cloneID = -1;
}
//TODO: cleanup remaining clone links if any
// for(auto s : stacks)
// {
// if(s->cloneID == toRemoveId)
// s->cloneID = -1;
// }
}
ids.erase(toRemoveId);
}
}
void HypotheticBattle::updateUnit(uint32_t id, const JsonNode & data)
{
//TODO:
}
void HypotheticBattle::addUnitBonus(uint32_t id, const std::vector<Bonus> & bonus)
{
getForUpdate(id)->addUnitBonus(bonus);
bonusTreeVersion++;
}
void HypotheticBattle::updateUnitBonus(uint32_t id, const std::vector<Bonus> & bonus)
{
getForUpdate(id)->updateUnitBonus(bonus);
bonusTreeVersion++;
}
void HypotheticBattle::removeUnitBonus(uint32_t id, const std::vector<Bonus> & bonus)
{
getForUpdate(id)->removeUnitBonus(bonus);
bonusTreeVersion++;
}
void HypotheticBattle::setWallState(EWallPart partOfWall, EWallState state)
{
//TODO:HypotheticBattle::setWallState
}
void HypotheticBattle::addObstacle(const ObstacleChanges & changes)
{
//TODO:HypotheticBattle::addObstacle
}
void HypotheticBattle::updateObstacle(const ObstacleChanges& changes)
{
//TODO:HypotheticBattle::updateObstacle
}
void HypotheticBattle::removeObstacle(uint32_t id)
{
//TODO:HypotheticBattle::removeObstacle
}
uint32_t HypotheticBattle::nextUnitId() const
{
return nextId++;
}
int64_t HypotheticBattle::getActualDamage(const DamageRange & damage, int32_t attackerCount, vstd::RNG & rng) const
{
return (damage.min + damage.max) / 2;
}
std::vector<SpellID> HypotheticBattle::getUsedSpells(ui8 side) const
{
// TODO
return {};
}
int3 HypotheticBattle::getLocation() const
{
// TODO
return int3(-1, -1, -1);
}
bool HypotheticBattle::isCreatureBank() const
{
// TODO
return false;
}
int64_t HypotheticBattle::getTreeVersion() const
{
return getBonusBearer()->getTreeVersion() + bonusTreeVersion;
}
#if SCRIPTING_ENABLED
Pool * HypotheticBattle::getContextPool() const
{
return pool.get();
}
#endif
ServerCallback * HypotheticBattle::getServerCallback()
{
return serverCallback.get();
}
HypotheticBattle::HypotheticServerCallback::HypotheticServerCallback(HypotheticBattle * owner_)
:owner(owner_)
{
}
void HypotheticBattle::HypotheticServerCallback::complain(const std::string & problem)
{
logAi->error(problem);
}
bool HypotheticBattle::HypotheticServerCallback::describeChanges() const
{
return false;
}
vstd::RNG * HypotheticBattle::HypotheticServerCallback::getRNG()
{
return &rngStub;
}
void HypotheticBattle::HypotheticServerCallback::apply(CPackForClient * pack)
{
logAi->error("Package of type %s is not allowed in battle evaluation", typeid(pack).name());
}
void HypotheticBattle::HypotheticServerCallback::apply(BattleLogMessage * pack)
{
pack->applyBattle(owner);
}
void HypotheticBattle::HypotheticServerCallback::apply(BattleStackMoved * pack)
{
pack->applyBattle(owner);
}
void HypotheticBattle::HypotheticServerCallback::apply(BattleUnitsChanged * pack)
{
pack->applyBattle(owner);
}
void HypotheticBattle::HypotheticServerCallback::apply(SetStackEffect * pack)
{
pack->applyBattle(owner);
}
void HypotheticBattle::HypotheticServerCallback::apply(StacksInjured * pack)
{
pack->applyBattle(owner);
}
void HypotheticBattle::HypotheticServerCallback::apply(BattleObstaclesChanged * pack)
{
pack->applyBattle(owner);
}
void HypotheticBattle::HypotheticServerCallback::apply(CatapultAttack * pack)
{
pack->applyBattle(owner);
}
HypotheticBattle::HypotheticEnvironment::HypotheticEnvironment(HypotheticBattle * owner_, const Environment * upperEnvironment)
: owner(owner_),
env(upperEnvironment)
{
}
const Services * HypotheticBattle::HypotheticEnvironment::services() const
{
return env->services();
}
const Environment::BattleCb * HypotheticBattle::HypotheticEnvironment::battle(const BattleID & battleID) const
{
assert(battleID == owner->getBattleID());
return owner;
}
const Environment::GameCb * HypotheticBattle::HypotheticEnvironment::game() const
{
return env->game();
}
vstd::CLoggerBase * HypotheticBattle::HypotheticEnvironment::logger() const
{
return env->logger();
}
events::EventBus * HypotheticBattle::HypotheticEnvironment::eventBus() const
{
return owner->eventBus.get();
}