#include #include #include #include #include #include #include #include #include #include #include namespace mbgl { namespace gl { RendererBackend::RendererBackend(const gfx::ContextMode contextMode_) : gfx::RendererBackend(contextMode_) {} RendererBackend::RendererBackend(const gfx::ContextMode contextMode_, const TaggedScheduler& threadPool_) : gfx::RendererBackend(contextMode_, threadPool_) {} std::unique_ptr RendererBackend::createContext() { MLN_TRACE_FUNC(); auto result = std::make_unique( *this); // Tagged background thread pool will be owned by the RendererBackend result->enableDebugging(); result->initializeExtensions(std::bind(&RendererBackend::getExtensionFunctionPointer, this, std::placeholders::_1)); return result; } PremultipliedImage RendererBackend::readFramebuffer(const Size& size) { MLN_TRACE_FUNC(); return getContext().readFramebuffer(size); } void RendererBackend::assumeFramebufferBinding(const gl::FramebufferID fbo) { MLN_TRACE_FUNC(); getContext().bindFramebuffer.setCurrentValue(fbo); if (fbo != ImplicitFramebufferBinding) { assert(gl::value::BindFramebuffer::Get() == getContext().bindFramebuffer.getCurrentValue()); } } void RendererBackend::assumeViewport(int32_t x, int32_t y, const Size& size) { MLN_TRACE_FUNC(); getContext().viewport.setCurrentValue({x, y, size}); assert(gl::value::Viewport::Get() == getContext().viewport.getCurrentValue()); } void RendererBackend::assumeScissorTest(int32_t x, int32_t y, uint32_t width, uint32_t height) { MLN_TRACE_FUNC(); getContext().scissorTest.setCurrentValue({x, y, width, height}); assert(gl::value::ScissorTest::Get() == getContext().scissorTest.getCurrentValue()); } bool RendererBackend::implicitFramebufferBound() { MLN_TRACE_FUNC(); return getContext().bindFramebuffer.getCurrentValue() == ImplicitFramebufferBinding; } void RendererBackend::setFramebufferBinding(const gl::FramebufferID fbo) { MLN_TRACE_FUNC(); getContext().bindFramebuffer = fbo; if (fbo != ImplicitFramebufferBinding) { assert(gl::value::BindFramebuffer::Get() == getContext().bindFramebuffer.getCurrentValue()); } } void RendererBackend::setViewport(int32_t x, int32_t y, const Size& size) { MLN_TRACE_FUNC(); getContext().viewport = {x, y, size}; assert(gl::value::Viewport::Get() == getContext().viewport.getCurrentValue()); } void RendererBackend::setScissorTest(int32_t x, int32_t y, uint32_t width, uint32_t height) { MLN_TRACE_FUNC(); getContext().scissorTest = {x, y, width, height}; assert(gl::value::ScissorTest::Get() == getContext().scissorTest.getCurrentValue()); } RendererBackend::~RendererBackend() = default; /// @brief Register a list of types with a shader registry instance /// @tparam ...ShaderID Pack of BuiltIn:: shader IDs /// @param registry A shader registry instance /// @param programParameters ProgramParameters used to initialize each instance template void registerTypes(gfx::ShaderRegistry& registry, const ProgramParameters& programParameters) { MLN_TRACE_FUNC(); /// The following fold expression will create a shader for every type /// in the parameter pack and register it with the shader registry. /// Registration calls are wrapped in a lambda that throws on registration /// failure, we shouldn't expect registration to fail unless the shader /// registry instance provided already has conflicting programs present. ( [&]() { const auto name = std::string(shaders::ShaderSource::name); if (!registry.registerShaderGroup(std::make_shared>(programParameters), name)) { throw std::runtime_error("Failed to register " + name + " with shader registry!"); } }(), ...); } void RendererBackend::initShaders(gfx::ShaderRegistry& shaders, const ProgramParameters& programParameters) { MLN_TRACE_FUNC(); registerTypes(shaders, programParameters); // Initialize legacy shader programs Programs programs(programParameters); programs.registerWith(shaders); } } // namespace gl } // namespace mbgl