#pragma once #include #include #include namespace mln { namespace gfx { class Shader; using ShaderPtr = std::shared_ptr; // Assert that a type is a valid shader for downcasting. // A valid shader must: // * Inherit gfx::Shader // * Have properly called DECLARE_SHADER_TYPEINFO in the class body // * Be a final class template inline constexpr bool is_shader_v = std::is_base_of_v && std::is_same_v, std::string_view> && std::is_final_v; /// @brief A shader is used as the base class for all programs across any supported /// backend API. Shaders are registered with a `gfx::ShaderRegistry` instance. class Shader { public: virtual ~Shader() noexcept = default; /// @brief Get the type name of this shader /// @return Shader type name virtual const std::string_view typeName() const noexcept = 0; /// @brief Downcast to a type /// @tparam T Derived type /// @return Type or nullptr if type info was not a match template T* to() noexcept requires(is_shader_v) { if (typeName() != T::Name) { return nullptr; } return static_cast(this); } }; } // namespace gfx } // namespace mln