diff options
Diffstat (limited to 'src/mbgl/gl/context.hpp')
-rw-r--r-- | src/mbgl/gl/context.hpp | 153 |
1 files changed, 112 insertions, 41 deletions
diff --git a/src/mbgl/gl/context.hpp b/src/mbgl/gl/context.hpp index cf8bb2658b..093afa20ed 100644 --- a/src/mbgl/gl/context.hpp +++ b/src/mbgl/gl/context.hpp @@ -8,12 +8,21 @@ #include <mbgl/gl/framebuffer.hpp> #include <mbgl/gl/vertex_buffer.hpp> #include <mbgl/gl/index_buffer.hpp> -#include <mbgl/gl/attribute.hpp> +#include <mbgl/gl/types.hpp> +#include <mbgl/gl/draw_mode.hpp> +#include <mbgl/gl/depth_mode.hpp> +#include <mbgl/gl/stencil_mode.hpp> +#include <mbgl/gl/color_mode.hpp> +#include <mbgl/gl/segment.hpp> #include <mbgl/util/noncopyable.hpp> + +#include <functional> #include <memory> #include <vector> #include <array> +#include <string> +#include <unordered_map> namespace mbgl { @@ -27,32 +36,31 @@ class Context : private util::noncopyable { public: ~Context(); - UniqueProgram createProgram(); - UniqueShader createVertexShader(); - UniqueShader createFragmentShader(); + UniqueShader createShader(ShaderType type, const std::string& source); + UniqueProgram createProgram(ShaderID vertexShader, ShaderID fragmentShader); + void linkProgram(ProgramID); UniqueTexture createTexture(); - UniqueVertexArray createVertexArray(); - template <class V> - VertexBuffer<V> createVertexBuffer(std::vector<V>&& v) { - return VertexBuffer<V> { - v.size(), - createVertexBuffer(v.data(), v.size() * sizeof(V)) + template <class Vertex, class DrawMode> + VertexBuffer<Vertex, DrawMode> createVertexBuffer(VertexVector<Vertex, DrawMode>&& v) { + return VertexBuffer<Vertex, DrawMode> { + v.vertexSize(), + createVertexBuffer(v.data(), v.byteSize()) }; } - template <class P> - IndexBuffer<P> createIndexBuffer(std::vector<P>&& v) { - return IndexBuffer<P> { - createIndexBuffer(v.data(), v.size() * sizeof(P)) + template <class DrawMode> + IndexBuffer<DrawMode> createIndexBuffer(IndexVector<DrawMode>&& v) { + return IndexBuffer<DrawMode> { + createIndexBuffer(v.data(), v.byteSize()) }; } template <RenderbufferType type> - Renderbuffer<type> createRenderbuffer(const std::array<uint16_t, 2>& size) { + Renderbuffer<type> createRenderbuffer(const Size size) { static_assert(type == RenderbufferType::RGBA || type == RenderbufferType::DepthStencil, "invalid renderbuffer type"); - return { size, createRenderbuffer(type, size[0], size[1]) }; + return { size, createRenderbuffer(type, size) }; } Framebuffer createFramebuffer(const Renderbuffer<RenderbufferType::RGBA>&, @@ -62,30 +70,73 @@ public: const Renderbuffer<RenderbufferType::DepthStencil>&); Framebuffer createFramebuffer(const Texture&); + template <typename Image, + TextureFormat format = Image::channels == 4 ? TextureFormat::RGBA + : TextureFormat::Alpha> + Image readFramebuffer(const Size size, bool flip = true) { + static_assert(Image::channels == (format == TextureFormat::RGBA ? 4 : 1), + "image format mismatch"); + return { size, readFramebuffer(size, format, flip) }; + } + +#if not MBGL_USE_GLES2 + template <typename Image> + void drawPixels(const Image& image) { + auto format = image.channels == 4 ? TextureFormat::RGBA : TextureFormat::Alpha; + drawPixels(image.size, image.data.get(), format); + } +#endif // MBGL_USE_GLES2 + // Create a texture from an image with data. template <typename Image> Texture createTexture(const Image& image, TextureUnit unit = 0) { - return { {{ image.width, image.height }}, - createTexture(image.width, image.height, image.data.get(), unit) }; + auto format = image.channels == 4 ? TextureFormat::RGBA : TextureFormat::Alpha; + return { image.size, createTexture(image.size, image.data.get(), format, unit) }; + } + + template <typename Image> + void updateTexture(Texture& obj, const Image& image, TextureUnit unit = 0) { + auto format = image.channels == 4 ? TextureFormat::RGBA : TextureFormat::Alpha; + updateTexture(obj.texture.get(), image.size, image.data.get(), format, unit); + obj.size = image.size; } // Creates an empty texture with the specified dimensions. - Texture createTexture(const std::array<uint16_t, 2>& size, TextureUnit unit = 0) { - return { size, createTexture(size[0], size[1], nullptr, unit) }; + Texture createTexture(const Size size, + TextureFormat format = TextureFormat::RGBA, + TextureUnit unit = 0) { + return { size, createTexture(size, nullptr, format, unit) }; } void bindTexture(Texture&, TextureUnit = 0, TextureFilter = TextureFilter::Nearest, - TextureMipMap = TextureMipMap::No); - - template <class Shader, class Vertex> - void bindAttributes(const Shader& shader, const VertexBuffer<Vertex>&, const int8_t* offset) { - static_assert(std::is_same<typename Shader::VertexType, Vertex>::value, "vertex type mismatch"); - for (const auto& binding : AttributeBindings<Shader, Vertex>()(shader)) { - bindAttribute(binding, sizeof(Vertex), offset); - } - } + TextureMipMap = TextureMipMap::No, + TextureWrap wrapX = TextureWrap::Clamp, + TextureWrap wrapY = TextureWrap::Clamp); + + void clear(optional<mbgl::Color> color, + optional<float> depth, + optional<int32_t> stencil); + + struct Drawable { + DrawMode drawMode; + DepthMode depthMode; + StencilMode stencilMode; + ColorMode colorMode; + gl::ProgramID program; + gl::BufferID vertexBuffer; + gl::BufferID indexBuffer; + const std::vector<Segment>& segments; + std::function<void ()> bindUniforms; + std::function<void (std::size_t)> bindAttributes; + }; + + void draw(const Drawable&); + + void setDepthMode(const DepthMode&); + void setStencilMode(const StencilMode&); + void setColorMode(const ColorMode&); // Actually remove the objects we marked as abandoned with the above methods. // Only call this while the OpenGL context is exclusive to this thread. @@ -107,6 +158,23 @@ public: void setDirtyState(); + State<value::ActiveTexture> activeTexture; + State<value::BindFramebuffer> bindFramebuffer; + State<value::Viewport> viewport; + std::array<State<value::BindTexture>, 2> texture; + State<value::BindVertexArray> vertexArrayObject; + State<value::Program> program; + +#if not MBGL_USE_GLES2 + State<value::PixelZoom> pixelZoom; + State<value::RasterPos> rasterPos; + State<value::PixelStorePack> pixelStorePack; + State<value::PixelStoreUnpack> pixelStoreUnpack; + State<value::PixelTransferDepth> pixelTransferDepth; + State<value::PixelTransferStencil> pixelTransferStencil; +#endif // MBGL_USE_GLES2 + +private: State<value::StencilFunc> stencilFunc; State<value::StencilMask> stencilMask; State<value::StencilTest> stencilTest; @@ -116,34 +184,37 @@ public: State<value::DepthTest> depthTest; State<value::DepthFunc> depthFunc; State<value::Blend> blend; + State<value::BlendEquation> blendEquation; State<value::BlendFunc> blendFunc; State<value::BlendColor> blendColor; State<value::ColorMask> colorMask; State<value::ClearDepth> clearDepth; State<value::ClearColor> clearColor; State<value::ClearStencil> clearStencil; - State<value::Program> program; State<value::LineWidth> lineWidth; - State<value::ActiveTexture> activeTexture; - State<value::BindFramebuffer> bindFramebuffer; - State<value::Viewport> viewport; State<value::BindRenderbuffer> bindRenderbuffer; #if not MBGL_USE_GLES2 - State<value::PixelZoom> pixelZoom; - State<value::RasterPos> rasterPos; + State<value::PointSize> pointSize; #endif // MBGL_USE_GLES2 - std::array<State<value::BindTexture>, 2> texture; State<value::BindVertexBuffer> vertexBuffer; State<value::BindElementBuffer> elementBuffer; - State<value::BindVertexArray> vertexArrayObject; -private: UniqueBuffer createVertexBuffer(const void* data, std::size_t size); UniqueBuffer createIndexBuffer(const void* data, std::size_t size); - UniqueTexture createTexture(uint16_t width, uint16_t height, const void* data, TextureUnit); + UniqueTexture createTexture(Size size, const void* data, TextureFormat, TextureUnit); + void updateTexture(TextureID, Size size, const void* data, TextureFormat, TextureUnit); UniqueFramebuffer createFramebuffer(); - UniqueRenderbuffer createRenderbuffer(RenderbufferType, uint16_t width, uint16_t height); - void bindAttribute(const AttributeBinding&, std::size_t stride, const int8_t* offset); + UniqueRenderbuffer createRenderbuffer(RenderbufferType, Size size); + std::unique_ptr<uint8_t[]> readFramebuffer(Size, TextureFormat, bool flip); +#if not MBGL_USE_GLES2 + void drawPixels(Size size, const void* data, TextureFormat); +#endif // MBGL_USE_GLES2 + + PrimitiveType operator()(const Points&); + PrimitiveType operator()(const Lines&); + PrimitiveType operator()(const LineStrip&); + PrimitiveType operator()(const Triangles&); + PrimitiveType operator()(const TriangleStrip&); friend detail::ProgramDeleter; friend detail::ShaderDeleter; |