Loads of work on capturing pokemon
All checks were successful
continuous-integration/drone/push Build is passing

This commit is contained in:
2022-03-26 16:23:24 +01:00
parent 1b14f31bd7
commit 09638c8d14
12 changed files with 110 additions and 13 deletions

View File

@@ -0,0 +1,26 @@
#ifndef PKMNLIB_CAPTUREATTEMPTEVENT_HPP
#define PKMNLIB_CAPTUREATTEMPTEVENT_HPP
#include <CreatureLib/Battling/EventHooks/Events/EventData.hpp>
#include "../Pokemon/Pokemon.hpp"
#include "Arbutils/Memory/Memory.hpp"
#include "PkmnEventKind.hpp"
namespace PkmnLib::Battling {
class CaptureAttemptEvent final : public CreatureLib::Battling::EventData {
ArbUt::BorrowedPtr<PkmnLib::Battling::Pokemon> _pokemon;
CaptureLibrary::CaptureResult _result;
public:
explicit CaptureAttemptEvent(PkmnLib::Battling::Pokemon* pokemon, const CaptureLibrary::CaptureResult& result)
: _pokemon(pokemon), _result(result) {}
[[nodiscard]] CreatureLib::Battling::EventDataKind GetKind() const noexcept override {
return static_cast<CreatureLib::Battling::EventDataKind>(PkmnEventDataKind::CaptureAttempt);
}
const ArbUt::BorrowedPtr<PkmnLib::Battling::Pokemon>& GetPokemon() const noexcept { return _pokemon; }
const CaptureLibrary::CaptureResult& GetResult() const noexcept { return _result; }
};
}
#endif // PKMNLIB_CAPTUREATTEMPTEVENT_HPP

View File

@@ -2,6 +2,6 @@
#define PKMNLIB_PKMNEVENTKIND_HPP
#include <CreatureLib/Battling/EventHooks/EventDataKind.hpp>
ENUM_WITH_START_VALUE(PkmnEventDataKind, u8, 128, WeatherChange)
ENUM_WITH_START_VALUE(PkmnEventDataKind, u8, 128, WeatherChange, CaptureAttempt)
#endif // PKMNLIB_PKMNEVENTKIND_HPP

View File

@@ -3,6 +3,7 @@
#include <CreatureLib/Battling/Library/BattleLibrary.hpp>
#include "../../Library/PokemonLibrary.hpp"
#include "CaptureLibrary.hpp"
#include "DamageLibrary.hpp"
#include "ExperienceLibrary.hpp"
#include "MiscLibrary.hpp"
@@ -11,13 +12,16 @@
namespace PkmnLib::Battling {
class BattleLibrary final : public CreatureLib::Battling::BattleLibrary {
std::unique_ptr<const CaptureLibrary> _captureLibrary;
public:
BattleLibrary(Library::PokemonLibrary* non_null staticLib, StatCalculator* non_null statCalculator,
DamageLibrary* non_null damageLibrary,
PkmnLib::Battling::ExperienceLibrary* non_null experienceLibrary,
ScriptResolver* non_null scriptResolver, PkmnLib::Battling::MiscLibrary* non_null miscLibrary)
DamageLibrary* non_null damageLibrary, ExperienceLibrary* non_null experienceLibrary,
ScriptResolver* non_null scriptResolver, MiscLibrary* non_null miscLibrary,
CaptureLibrary* non_null captureLibrary)
: CreatureLib::Battling::BattleLibrary(staticLib, statCalculator, damageLibrary, experienceLibrary,
scriptResolver, miscLibrary) {}
scriptResolver, miscLibrary),
_captureLibrary(captureLibrary) {}
const std::unique_ptr<const Library::LibrarySettings>& GetSettings() const {
return reinterpret_cast<const std::unique_ptr<const Library::LibrarySettings>&>(_staticLib->GetSettings());
@@ -43,6 +47,9 @@ namespace PkmnLib::Battling {
const ArbUt::BorrowedPtr<const Library::NatureLibrary> GetNatureLibrary() const {
return GetStaticLib()->GetNatureLibrary();
}
[[nodiscard]] inline const ArbUt::BorrowedPtr<const CaptureLibrary> GetCaptureLibrary() const noexcept {
return _captureLibrary;
}
static PkmnLib::Battling::ScriptResolver* non_null CreateScriptResolver();
};

View File

@@ -1,10 +1,11 @@
#include "CaptureLibrary.hpp"
#include "../PkmnItemUseScript.hpp"
#include "../PkmnScriptHook.hpp"
#include "../Pokemon/Pokemon.hpp"
namespace PkmnLib::Battling {
CaptureLibrary::CaptureResult CaptureLibrary::TryCatch(Pokemon* non_null pokemon, Library::Item* non_null catchItem,
ArbUt::Random* non_null random) const {
CreatureLib::Battling::BattleRandom* non_null random) const {
auto hpMax = pokemon->GetMaxHealth();
auto hpCurrent = pokemon->GetCurrentHealth();
auto rate = pokemon->GetSpecies()->GetCaptureRate();

View File

@@ -1,9 +1,13 @@
#ifndef PKMNLIB_CAPTURELIBRARY_HPP
#define PKMNLIB_CAPTURELIBRARY_HPP
#include <CreatureLib/Battling/Models/BattleRandom.hpp>
#include <CreatureLib/Defines.hpp>
#include "../Pokemon/Pokemon.hpp"
#include "../../Library/Items/Item.hpp"
namespace PkmnLib::Battling {
class Pokemon;
class CaptureLibrary {
public:
struct CaptureResult {
@@ -13,7 +17,7 @@ namespace PkmnLib::Battling {
};
CaptureResult TryCatch(Pokemon* non_null pokemon, Library::Item* non_null catchItem,
ArbUt::Random* non_null random) const;
CreatureLib::Battling::BattleRandom* non_null random) const;
};
}

View File

@@ -1,5 +1,6 @@
#include "Pokemon.hpp"
#include <CreatureLib/Battling/Models/Battle.hpp>
#include "../EventHooks/CaptureAttemptEvent.hpp"
#include "../PkmnScriptCategory.hpp"
void PkmnLib::Battling::Pokemon::Evolve(ArbUt::BorrowedPtr<const Library::PokemonSpecies> mon,
@@ -71,5 +72,30 @@ bool PkmnLib::Battling::Pokemon::IsUsable() const noexcept {
if (IsEgg()) {
return false;
}
if (_wasCaught) {
return false;
}
return Creature::IsUsable();
}
void PkmnLib::Battling::Pokemon::AttemptCapture(PkmnLib::Library::Item* catchItem) {
Ensure(_battleData.OnBattleField);
Ensure(_battleData.Battle.HasValue());
Ensure(_battleData.Side.HasValue());
Ensure(!IsFainted());
Ensure(IsUsable());
Ensure(!GetBattleSide().GetValue()->IsSlotUnfillabe(this)) auto captureLibrary =
GetLibrary().ForceAs<const BattleLibrary>()->GetCaptureLibrary();
auto result = captureLibrary->TryCatch(this, catchItem, _battleData.Battle.GetValue()->GetRandom());
_battleData.Battle.GetValue()->TriggerEventListener<CaptureAttemptEvent>(this, result);
if (result.WasCaught) {
// By marking the pokemon as caught, it becomes no longer usable for switch in.
_wasCaught = true;
// As the pokemon is caught now, we replace it with an empty space.
_battleData.Side.GetValue()->SetCreature(nullptr, _battleData.Index.GetCreatureIndex());
}
}
void PkmnLib::Battling::Pokemon::ClearBattleData() noexcept {
Creature::ClearBattleData();
_wasCaught = false;
}

View File

@@ -4,6 +4,7 @@
#include <CreatureLib/Battling/Models/Creature.hpp>
#include "../../Library/Statistic.hpp"
#include "../Library/BattleLibrary.hpp"
#include "../Library/CaptureLibrary.hpp"
#include "../PkmnScript.hpp"
#include "LearnedMove.hpp"
@@ -16,6 +17,7 @@ namespace PkmnLib::Battling {
ArbUt::BorrowedPtr<const PkmnLib::Library::Nature> _nature;
u8 _friendship = 0;
bool _isEgg;
bool _wasCaught = {};
public:
Pokemon(ArbUt::BorrowedPtr<const BattleLibrary> library,
@@ -81,6 +83,15 @@ namespace PkmnLib::Battling {
_friendship = newValue;
}
/// @brief Attempt to capture the Pokemon.
/// @param catchItem The item used to try and catch the Pokemon with (generally a pokeball).
/// @warning This requires the Pokemon to be on the battle field, not fainted, and usable (so not already caught
/// and not an egg).
void AttemptCapture(Library::Item* non_null catchItem);
inline bool WasCaught() const noexcept { return _wasCaught; }
void ClearBattleData() noexcept override;
bool IsUsable() const noexcept override;
Creature* non_null Clone() const override;