Extra2D/include/module/module_registry.h

112 lines
2.8 KiB
C
Raw Normal View History

#pragma once
#include <functional>
#include <memory>
#include <module/module.h>
#include <string>
#include <typeindex>
#include <vector>
namespace extra2d {
/**
* @brief
*/
using ModuleFactory = std::function<std::unique_ptr<Module>()>;
/**
* @brief
*/
struct ModuleInfo {
std::string name;
ModuleFactory factory;
int32 priority;
std::type_index type;
};
/**
* @brief
*
*
* 使
*/
class ModuleRegistry {
public:
/**
* @brief
*/
static ModuleRegistry &instance();
/**
* @brief
* @tparam T
* @param name
* @param priority
*/
template <typename T>
void registerModule(const char *name, int32 priority = 100) {
static_assert(std::is_base_of_v<Module, T>, "T must inherit from Module");
ModuleInfo info{
name, []() -> std::unique_ptr<Module> { return std::make_unique<T>(); },
priority, std::type_index(typeid(T))};
registrations_.push_back(std::move(info));
}
/**
* @brief
* @return
*/
std::vector<std::unique_ptr<Module>> createModules();
/**
* @brief
*/
const std::vector<ModuleInfo> &getRegistrations() const {
return registrations_;
}
private:
ModuleRegistry() = default;
std::vector<ModuleInfo> registrations_;
};
/**
* @brief
*/
template <typename T> class ModuleRegistrar {
public:
ModuleRegistrar(const char *name, int32 priority = 100) {
ModuleRegistry::instance().registerModule<T>(name, priority);
}
};
/**
* @brief
*
* 使
*
* class MyModule : public Module {
* E2D_REGISTER_MODULE(MyModule, "MyModule", 10)
* public:
* // ...
* };
*/
#define E2D_REGISTER_MODULE(ClassName, Name, Priority) \
private: \
static inline const extra2d::ModuleRegistrar<ClassName> _registrar{ \
Name, Priority}; \
\
public: \
const char *getName() const override { return Name; } \
int32 getPriority() const override { return Priority; }
/**
* @brief 使
*/
#define E2D_REGISTER_MODULE_SIMPLE(ClassName) \
E2D_REGISTER_MODULE(ClassName, #ClassName, 100)
} // namespace extra2d