#pragma once #include #include #include #include #include namespace pg { class App { public: App() = default; virtual ~App() = default; App(const App&) = delete; App(App&&) = delete; App& operator=(const App&) = delete; App& operator=(App&&) = delete; virtual void Update() noexcept = 0; protected: struct TypeInfo final { public: using Factory = std::function()>; template static TypeInfo Create(const char* name) noexcept { return {name, []() { return std::make_unique(); }}; } TypeInfo(const char* name, Factory&& f) noexcept : name_(name), factory_(std::move(f)) { registry_[name_] = this; } ~TypeInfo() noexcept { registry_.erase(name_); } std::unique_ptr Create() noexcept { return factory_(); } const char* name() const noexcept { return name_; } private: const char* name_; Factory factory_; }; static const std::map& registry() noexcept { return registry_; } private: static inline std::map registry_; }; } // namespace pg