diff options
| author | robojumper <robojumper@gmail.com> | 2024-11-12 19:37:21 +0100 |
|---|---|---|
| committer | robojumper <robojumper@gmail.com> | 2024-11-13 19:08:38 +0100 |
| commit | 31ddec9bd4d3b399412fd87bd53c41feb43e1c80 (patch) | |
| tree | 669a756be1b1eb0d1a98cfa90c7037a37bf2d21a /include/s | |
| parent | 3a45e6536a1deec0cd5a4c108dfeb4c374ca34d9 (diff) | |
Implement a solution that seemingly works
Diffstat (limited to 'include/s')
| -rw-r--r-- | include/s/README.txt | 4 | ||||
| -rw-r--r-- | include/s/s_FStateVirtualID.hpp | 35 | ||||
| -rw-r--r-- | include/s/s_State.hpp | 34 | ||||
| -rw-r--r-- | include/s/s_StateID.hpp | 2 |
4 files changed, 74 insertions, 1 deletions
diff --git a/include/s/README.txt b/include/s/README.txt index 53c6cb63..22881597 100644 --- a/include/s/README.txt +++ b/include/s/README.txt @@ -22,3 +22,7 @@ the other abstract interface classes and provides this dtor. We're observing a lot of word-to-bool casts in code after these operators are invoked, and while there are ways to force the conversion, this seems the most reasonable. + +## s_FStateVirtualID + +Implemented by SS based on NSMBW symbols. Probably missing some parts, sync with NSMBW if they get around to it. diff --git a/include/s/s_FStateVirtualID.hpp b/include/s/s_FStateVirtualID.hpp new file mode 100644 index 00000000..e48600a2 --- /dev/null +++ b/include/s/s_FStateVirtualID.hpp @@ -0,0 +1,35 @@ +#ifndef S_FSTATE_VIRTUAL_ID_H +#define S_FSTATE_VIRTUAL_ID_H + +#include "s/s_FStateID.hpp" +#include "s/s_StateID.hpp" + +template <typename T> +class sFStateVirtualID_c : public sFStateID_c<T> { +public: + typedef void (T::*stateFunc)(); + sFStateVirtualID_c( + const sStateID_c *superState, const char *name, stateFunc initialize, stateFunc execute, stateFunc finalize + ) + : sFStateID_c<T>(name, initialize, execute, finalize), mpSuperState(superState) {} + + virtual unsigned int number() const { + return superID()->numberBase(); + } + + const sFStateVirtualID_c<T> *superID() const { + if (!mpSuperState->isNull()) { + return static_cast<const sFStateVirtualID_c<T> *>(mpSuperState)->superID(); + } + return this; + } + + unsigned int numberBase() const { + return sStateID_c::number(); + } + +private: + const sStateID_c *mpSuperState; +}; + +#endif diff --git a/include/s/s_State.hpp b/include/s/s_State.hpp index 76339e3a..3a8c4ec5 100644 --- a/include/s/s_State.hpp +++ b/include/s/s_State.hpp @@ -3,6 +3,7 @@ #include "s/s_FStateMgr.hpp" #include "s/s_StateMethodUsr_FI.hpp" +#include "s/s_FStateVirtualID.hpp" // Note: Ported from https://github.com/NSMBW-Community/NSMBW-Decomp/tree/master/include/dol/sLib // See include/s/README.txt for changes made @@ -29,4 +30,37 @@ #define STATE_MGR(class_name) sFStateMgr_c<class_name, sStateMethodUsr_FI_c> +// TODO this is probably not the whole solution. +// The problems with this approach are: +// * You can't define the same state name for multiple files in the same TU due to baseID_ symbol clash. +// * The use of the templated baseID_ function isn't quite justified (could just use normal functions). + +#define STATE_VIRTUAL_FUNC_DECLARE(class, name) \ + virtual void initializeState_##name(); \ + virtual void executeState_##name(); \ + virtual void finalizeState_##name(); \ + static const sFStateVirtualID_c<class> StateID_##name; \ + typedef sStateID_c StateID_##name##_BaseIDClass + +#define STATE_VIRTUAL_OVERRIDE_FUNC_DECLARE(class, super_class, name) \ + virtual void initializeState_##name() override; \ + virtual void executeState_##name() override; \ + virtual void finalizeState_##name() override; \ + static const sFStateVirtualID_c<class> StateID_##name; \ + typedef super_class StateID_##name##_BaseIDClass + +#define STATE_VIRTUAL_DEFINE(class, name) \ + template <typename T> \ + static const sStateID_c &baseID_##name() { \ + return T::StateID_##name; \ + } \ + template <> \ + const sStateID_c &baseID_##name<sStateID_c>() { \ + return sStateID::null; \ + } \ + const sFStateVirtualID_c<class> class ::StateID_##name( \ + &baseID_##name<class ::StateID_##name##_BaseIDClass>(), #class "::StateID_" #name, \ + &class ::initializeState_##name, &class ::executeState_##name, &class ::finalizeState_##name \ + ) + #endif diff --git a/include/s/s_StateID.hpp b/include/s/s_StateID.hpp index cff3ed9f..d385f354 100644 --- a/include/s/s_StateID.hpp +++ b/include/s/s_StateID.hpp @@ -44,7 +44,7 @@ protected: namespace sStateID { /// @ingroup state -extern sStateID_c null; ///< A null state instance. +extern const sStateID_c null; ///< A null state instance. } // namespace sStateID #endif |
