diff options
Diffstat (limited to 'src/mbgl/util/raster.cpp')
-rw-r--r-- | src/mbgl/util/raster.cpp | 62 |
1 files changed, 38 insertions, 24 deletions
diff --git a/src/mbgl/util/raster.cpp b/src/mbgl/util/raster.cpp index b4e838ec00..7417c8bcd5 100644 --- a/src/mbgl/util/raster.cpp +++ b/src/mbgl/util/raster.cpp @@ -10,53 +10,67 @@ namespace mbgl { bool Raster::isLoaded() const { - std::lock_guard<std::mutex> lock(mtx); return loaded; } -void Raster::load(PremultipliedImage image) { +void Raster::load(PremultipliedImage image, uint32_t mipmapLevel) { assert(image.data.get()); - img = std::move(image); - width = GLsizei(img.width); - height = GLsizei(img.height); + if (images.size() <= mipmapLevel) { + images.resize(mipmapLevel + 1); + } + images.at(mipmapLevel) = std::move(image); - std::lock_guard<std::mutex> lock(mtx); loaded = true; } +void Raster::bind(gl::ObjectStore& store, Scaling newFilter, MipMap newMipMap) { + bool updateFilter = false; -void Raster::bind(bool linear, gl::ObjectStore& store) { - if (!width || !height) { - Log::Error(Event::OpenGL, "trying to bind texture without dimension"); - return; - } - - if (img.data && !texture) { - upload(store); - } else if (texture) { + if (!texture) { + if (images.empty()) { + Log::Error(Event::OpenGL, "trying to bind texture without images"); + return; + } else { + upload(store); + updateFilter = true; + } + } else { MBGL_CHECK_ERROR(glBindTexture(GL_TEXTURE_2D, *texture)); + updateFilter = (filter != newFilter || mipmap != newMipMap); } - GLint new_filter = linear ? GL_LINEAR : GL_NEAREST; - if (new_filter != this->filter) { - MBGL_CHECK_ERROR(glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, new_filter)); - MBGL_CHECK_ERROR(glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, new_filter)); - filter = new_filter; + if (updateFilter) { + filter = newFilter; + mipmap = newMipMap; + MBGL_CHECK_ERROR(glTexParameteri( + GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, + filter == Scaling::Linear + ? (mipmap == MipMap::Yes ? GL_LINEAR_MIPMAP_NEAREST : GL_LINEAR) + : (mipmap == MipMap::Yes ? GL_NEAREST_MIPMAP_NEAREST : GL_NEAREST))); + MBGL_CHECK_ERROR(glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, + filter == Scaling::Linear ? GL_LINEAR : GL_NEAREST)); } } void Raster::upload(gl::ObjectStore& store) { - if (img.data && !texture) { + if (!images.empty() && !texture) { texture = store.createTexture(); MBGL_CHECK_ERROR(glBindTexture(GL_TEXTURE_2D, *texture)); #ifndef GL_ES_VERSION_2_0 - MBGL_CHECK_ERROR(glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, 0)); + MBGL_CHECK_ERROR(glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, images.size())); #endif MBGL_CHECK_ERROR(glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE)); MBGL_CHECK_ERROR(glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE)); - MBGL_CHECK_ERROR(glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, width, height, 0, GL_RGBA, GL_UNSIGNED_BYTE, img.data.get())); - img.data.reset(); + GLint level = 0; + for (auto& img : images) { + assert(img.data.get()); + MBGL_CHECK_ERROR(glTexImage2D( + GL_TEXTURE_2D, level++, GL_RGBA, static_cast<GLsizei>(img.width), + static_cast<GLsizei>(img.height), 0, GL_RGBA, GL_UNSIGNED_BYTE, img.data.get())); + } + images.clear(); + images.shrink_to_fit(); } } |