diff options
Diffstat (limited to 'src/mbgl/gl')
-rw-r--r-- | src/mbgl/gl/color_mode.hpp | 6 | ||||
-rw-r--r-- | src/mbgl/gl/context.cpp | 50 | ||||
-rw-r--r-- | src/mbgl/gl/context.hpp | 47 | ||||
-rw-r--r-- | src/mbgl/gl/gl.hpp | 30 | ||||
-rw-r--r-- | src/mbgl/gl/index_buffer.hpp | 1 | ||||
-rw-r--r-- | src/mbgl/gl/types.hpp | 9 |
6 files changed, 92 insertions, 51 deletions
diff --git a/src/mbgl/gl/color_mode.hpp b/src/mbgl/gl/color_mode.hpp index e73c8737eb..e394f43501 100644 --- a/src/mbgl/gl/color_mode.hpp +++ b/src/mbgl/gl/color_mode.hpp @@ -49,7 +49,7 @@ public: struct Replace { static constexpr BlendEquation equation = BlendEquation::Add; static constexpr BlendFactor srcFactor = One; - static constexpr BlendFactor dstFactor = One; + static constexpr BlendFactor dstFactor = Zero; }; using Add = LinearBlend<BlendEquation::Add>; @@ -85,6 +85,10 @@ public: static ColorMode alphaBlended() { return ColorMode { Add { One, OneMinusSrcAlpha }, {}, { true, true, true, true } }; } + + static ColorMode additive() { + return ColorMode { Add { One, One }, {}, { true, true, true, true } }; + } }; constexpr bool operator!=(const ColorMode::Mask& a, const ColorMode::Mask& b) { diff --git a/src/mbgl/gl/context.cpp b/src/mbgl/gl/context.cpp index 4b77954d12..ba44adb42b 100644 --- a/src/mbgl/gl/context.cpp +++ b/src/mbgl/gl/context.cpp @@ -60,6 +60,16 @@ static_assert(std::is_same<std::underlying_type_t<TextureFormat>, GLenum>::value static_assert(underlying_type(TextureFormat::RGBA) == GL_RGBA, "OpenGL type mismatch"); static_assert(underlying_type(TextureFormat::Alpha) == GL_ALPHA, "OpenGL type mismatch"); +static_assert(std::is_same<std::underlying_type_t<TextureType>, GLenum>::value, "OpenGL type mismatch"); +static_assert(underlying_type(TextureType::UnsignedByte) == GL_UNSIGNED_BYTE, "OpenGL type mismatch"); + +#if MBGL_USE_GLES2 && GL_HALF_FLOAT_OES +static_assert(underlying_type(TextureType::HalfFloat) == GL_HALF_FLOAT_OES, "OpenGL type mismatch"); +#endif +#if !MBGL_USE_GLES2 && GL_HALF_FLOAT_ARB +static_assert(underlying_type(TextureType::HalfFloat) == GL_HALF_FLOAT_ARB, "OpenGL type mismatch"); +#endif + static_assert(underlying_type(UniformDataType::Float) == GL_FLOAT, "OpenGL type mismatch"); static_assert(underlying_type(UniformDataType::FloatVec2) == GL_FLOAT_VEC2, "OpenGL type mismatch"); static_assert(underlying_type(UniformDataType::FloatVec3) == GL_FLOAT_VEC3, "OpenGL type mismatch"); @@ -116,6 +126,19 @@ void Context::initializeExtensions(const std::function<gl::ProcAddress(const cha programBinary = std::make_unique<extension::ProgramBinary>(fn); #endif +#if MBGL_USE_GLES2 + constexpr const char* halfFloatExtensionName = "OES_texture_half_float"; + constexpr const char* halfFloatColorBufferExtensionName = "EXT_color_buffer_half_float"; +#else + constexpr const char* halfFloatExtensionName = "ARB_half_float_pixel"; + constexpr const char* halfFloatColorBufferExtensionName = "ARB_color_buffer_float"; +#endif + if (strstr(extensions, halfFloatExtensionName) != nullptr && + strstr(extensions, halfFloatColorBufferExtensionName) != nullptr) { + + supportsHalfFloatTextures = true; + } + if (!supportsVertexArrays()) { Log::Warning(Event::OpenGL, "Not using Vertex Array Objects"); } @@ -226,16 +249,25 @@ void Context::updateVertexBuffer(UniqueBuffer& buffer, const void* data, std::si MBGL_CHECK_ERROR(glBufferSubData(GL_ARRAY_BUFFER, 0, size, data)); } -UniqueBuffer Context::createIndexBuffer(const void* data, std::size_t size) { +UniqueBuffer Context::createIndexBuffer(const void* data, std::size_t size, const BufferUsage usage) { BufferID id = 0; MBGL_CHECK_ERROR(glGenBuffers(1, &id)); UniqueBuffer result { std::move(id), { this } }; bindVertexArray = 0; globalVertexArrayState.indexBuffer = result; - MBGL_CHECK_ERROR(glBufferData(GL_ELEMENT_ARRAY_BUFFER, size, data, GL_STATIC_DRAW)); + MBGL_CHECK_ERROR(glBufferData(GL_ELEMENT_ARRAY_BUFFER, size, data, static_cast<GLenum>(usage))); return result; } +void Context::updateIndexBuffer(UniqueBuffer& buffer, const void* data, std::size_t size) { + // Be sure to unbind any existing vertex array object before binding the index buffer + // so that we don't mess up another VAO + bindVertexArray = 0; + globalVertexArrayState.indexBuffer = buffer; + MBGL_CHECK_ERROR(glBufferSubData(GL_ELEMENT_ARRAY_BUFFER, 0, size, data)); +} + + UniqueTexture Context::createTexture() { if (pooledTextures.empty()) { pooledTextures.resize(TextureMax); @@ -489,10 +521,10 @@ Context::createFramebuffer(const Texture& color, } UniqueTexture -Context::createTexture(const Size size, const void* data, TextureFormat format, TextureUnit unit) { +Context::createTexture(const Size size, const void* data, TextureFormat format, TextureUnit unit, TextureType type) { auto obj = createTexture(); pixelStoreUnpack = { 1 }; - updateTexture(obj, size, data, format, unit); + updateTexture(obj, size, data, format, unit, type); // We are using clamp to edge here since OpenGL ES doesn't allow GL_REPEAT on NPOT textures. // We use those when the pixelRatio isn't a power of two, e.g. on iPhone 6 Plus. MBGL_CHECK_ERROR(glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE)); @@ -503,11 +535,11 @@ Context::createTexture(const Size size, const void* data, TextureFormat format, } void Context::updateTexture( - TextureID id, const Size size, const void* data, TextureFormat format, TextureUnit unit) { + TextureID id, const Size size, const void* data, TextureFormat format, TextureUnit unit, TextureType type) { activeTextureUnit = unit; texture[unit] = id; MBGL_CHECK_ERROR(glTexImage2D(GL_TEXTURE_2D, 0, static_cast<GLenum>(format), size.width, - size.height, 0, static_cast<GLenum>(format), GL_UNSIGNED_BYTE, + size.height, 0, static_cast<GLenum>(format), static_cast<GLenum>(type), data)); } @@ -607,19 +639,19 @@ void Context::clear(optional<mbgl::Color> color, if (color) { mask |= GL_COLOR_BUFFER_BIT; clearColor = *color; - colorMask = { true, true, true, true }; + colorMask = value::ColorMask::Default; } if (depth) { mask |= GL_DEPTH_BUFFER_BIT; clearDepth = *depth; - depthMask = true; + depthMask = value::DepthMask::Default; } if (stencil) { mask |= GL_STENCIL_BUFFER_BIT; clearStencil = *stencil; - stencilMask = 0xFF; + stencilMask = value::StencilMask::Default; } MBGL_CHECK_ERROR(glClear(mask)); diff --git a/src/mbgl/gl/context.hpp b/src/mbgl/gl/context.hpp index 528113cbba..67624288e2 100644 --- a/src/mbgl/gl/context.hpp +++ b/src/mbgl/gl/context.hpp @@ -61,7 +61,7 @@ public: optional<std::pair<BinaryProgramFormat, std::string>> getBinaryProgram(ProgramID) const; template <class Vertex, class DrawMode> - VertexBuffer<Vertex, DrawMode> createVertexBuffer(VertexVector<Vertex, DrawMode>&& v, const BufferUsage usage=BufferUsage::StaticDraw) { + VertexBuffer<Vertex, DrawMode> createVertexBuffer(VertexVector<Vertex, DrawMode>&& v, const BufferUsage usage = BufferUsage::StaticDraw) { return VertexBuffer<Vertex, DrawMode> { v.vertexSize(), createVertexBuffer(v.data(), v.byteSize(), usage) @@ -75,11 +75,18 @@ public: } template <class DrawMode> - IndexBuffer<DrawMode> createIndexBuffer(IndexVector<DrawMode>&& v) { + IndexBuffer<DrawMode> createIndexBuffer(IndexVector<DrawMode>&& v, const BufferUsage usage = BufferUsage::StaticDraw) { return IndexBuffer<DrawMode> { - createIndexBuffer(v.data(), v.byteSize()) + v.indexSize(), + createIndexBuffer(v.data(), v.byteSize(), usage) }; } + + template <class DrawMode> + void updateIndexBuffer(IndexBuffer<DrawMode>& buffer, IndexVector<DrawMode>&& v) { + assert(v.indexSize() == buffer.indexCount); + updateIndexBuffer(buffer.buffer, v.data(), v.byteSize()); + } template <RenderbufferType type> Renderbuffer<type> createRenderbuffer(const Size size) { @@ -118,23 +125,29 @@ public: // Create a texture from an image with data. template <typename Image> - Texture createTexture(const Image& image, TextureUnit unit = 0) { + Texture createTexture(const Image& image, + TextureUnit unit = 0, + TextureType type = TextureType::UnsignedByte) { auto format = image.channels == 4 ? TextureFormat::RGBA : TextureFormat::Alpha; - return { image.size, createTexture(image.size, image.data.get(), format, unit) }; + return { image.size, createTexture(image.size, image.data.get(), format, unit, type) }; } template <typename Image> - void updateTexture(Texture& obj, const Image& image, TextureUnit unit = 0) { + void updateTexture(Texture& obj, + const Image& image, + TextureUnit unit = 0, + TextureType type = TextureType::UnsignedByte) { auto format = image.channels == 4 ? TextureFormat::RGBA : TextureFormat::Alpha; - updateTexture(obj.texture.get(), image.size, image.data.get(), format, unit); + updateTexture(obj.texture.get(), image.size, image.data.get(), format, unit, type); obj.size = image.size; } // Creates an empty texture with the specified dimensions. Texture createTexture(const Size size, TextureFormat format = TextureFormat::RGBA, - TextureUnit unit = 0) { - return { size, createTexture(size, nullptr, format, unit) }; + TextureUnit unit = 0, + TextureType type = TextureType::UnsignedByte) { + return { size, createTexture(size, nullptr, format, unit, type) }; } void bindTexture(Texture&, @@ -225,6 +238,8 @@ public: State<value::PixelTransferStencil> pixelTransferStencil; #endif // MBGL_USE_GLES2 + bool supportsHalfFloatTextures = false; + private: State<value::StencilFunc> stencilFunc; State<value::StencilMask> stencilMask; @@ -250,9 +265,10 @@ private: UniqueBuffer createVertexBuffer(const void* data, std::size_t size, const BufferUsage usage); void updateVertexBuffer(UniqueBuffer& buffer, const void* data, std::size_t size); - UniqueBuffer createIndexBuffer(const void* data, std::size_t size); - UniqueTexture createTexture(Size size, const void* data, TextureFormat, TextureUnit); - void updateTexture(TextureID, Size size, const void* data, TextureFormat, TextureUnit); + UniqueBuffer createIndexBuffer(const void* data, std::size_t size, const BufferUsage usage); + void updateIndexBuffer(UniqueBuffer& buffer, const void* data, std::size_t size); + UniqueTexture createTexture(Size size, const void* data, TextureFormat, TextureUnit, TextureType); + void updateTexture(TextureID, Size size, const void* data, TextureFormat, TextureUnit, TextureType); UniqueFramebuffer createFramebuffer(); UniqueRenderbuffer createRenderbuffer(RenderbufferType, Size size); std::unique_ptr<uint8_t[]> readFramebuffer(Size, TextureFormat, bool flip); @@ -281,8 +297,13 @@ private: std::vector<RenderbufferID> abandonedRenderbuffers; public: - // For testing + // For testing and Windows because Qt + ANGLE + // crashes with VAO enabled. +#if defined(_WINDOWS) + bool disableVAOExtension = true; +#else bool disableVAOExtension = false; +#endif }; } // namespace gl diff --git a/src/mbgl/gl/gl.hpp b/src/mbgl/gl/gl.hpp index 3e21731330..976b7d2f74 100644 --- a/src/mbgl/gl/gl.hpp +++ b/src/mbgl/gl/gl.hpp @@ -1,36 +1,10 @@ #pragma once +#include <mbgl/gl/gl_impl.hpp> + #include <stdexcept> #include <limits> -#if __APPLE__ - #include "TargetConditionals.h" - #if TARGET_OS_IPHONE - #include <OpenGLES/ES2/gl.h> - #include <OpenGLES/ES2/glext.h> - #elif TARGET_IPHONE_SIMULATOR - #include <OpenGLES/ES2/gl.h> - #include <OpenGLES/ES2/glext.h> - #elif TARGET_OS_MAC - #include <OpenGL/OpenGL.h> - #include <OpenGL/gl.h> - #include <OpenGL/glext.h> - #else - #error Unsupported Apple platform - #endif -#elif __ANDROID__ || MBGL_USE_GLES2 - #define GL_GLEXT_PROTOTYPES - #include <GLES2/gl2.h> - #include <GLES2/gl2ext.h> -#elif __QT__ && QT_VERSION >= 0x050000 - #define GL_GLEXT_PROTOTYPES - #include <QtGui/qopengl.h> -#else - #define GL_GLEXT_PROTOTYPES - #include <GL/gl.h> - #include <GL/glext.h> -#endif - namespace mbgl { namespace gl { diff --git a/src/mbgl/gl/index_buffer.hpp b/src/mbgl/gl/index_buffer.hpp index 01b6396e00..87bfb6068f 100644 --- a/src/mbgl/gl/index_buffer.hpp +++ b/src/mbgl/gl/index_buffer.hpp @@ -35,6 +35,7 @@ private: template <class DrawMode> class IndexBuffer { public: + std::size_t indexCount; UniqueBuffer buffer; }; diff --git a/src/mbgl/gl/types.hpp b/src/mbgl/gl/types.hpp index da08195e58..376a784a0c 100644 --- a/src/mbgl/gl/types.hpp +++ b/src/mbgl/gl/types.hpp @@ -64,6 +64,15 @@ enum class TextureFormat : uint32_t { #endif // MBGL_USE_GLES2 }; +enum class TextureType : uint32_t { + UnsignedByte = 0x1401, +#if MBGL_USE_GLES2 + HalfFloat = 0x8D61, +#else + HalfFloat = 0x140B, +#endif // MBGL_USE_GLES2 +}; + enum class PrimitiveType { Points = 0x0000, Lines = 0x0001, |