diff options
Diffstat (limited to 'platform/default/mbgl')
-rw-r--r-- | platform/default/mbgl/gl/headless_backend.cpp | 4 | ||||
-rw-r--r-- | platform/default/mbgl/gl/headless_backend.hpp | 1 | ||||
-rw-r--r-- | platform/default/mbgl/gl/headless_frontend.cpp | 8 | ||||
-rw-r--r-- | platform/default/mbgl/gl/headless_frontend.hpp | 5 | ||||
-rw-r--r-- | platform/default/mbgl/map/map_snapshotter.cpp | 76 | ||||
-rw-r--r-- | platform/default/mbgl/map/map_snapshotter.hpp | 40 | ||||
-rw-r--r-- | platform/default/mbgl/storage/file_source_request.hpp | 31 | ||||
-rw-r--r-- | platform/default/mbgl/storage/offline.cpp | 35 | ||||
-rw-r--r-- | platform/default/mbgl/storage/offline_download.cpp | 4 | ||||
-rw-r--r-- | platform/default/mbgl/storage/offline_download.hpp | 2 |
10 files changed, 188 insertions, 18 deletions
diff --git a/platform/default/mbgl/gl/headless_backend.cpp b/platform/default/mbgl/gl/headless_backend.cpp index fe77b80985..edf637a560 100644 --- a/platform/default/mbgl/gl/headless_backend.cpp +++ b/platform/default/mbgl/gl/headless_backend.cpp @@ -64,6 +64,10 @@ void HeadlessBackend::bind() { context_.viewport = { 0, 0, size }; } +Size HeadlessBackend::getFramebufferSize() const { + return size; +} + void HeadlessBackend::updateAssumedState() { // no-op } diff --git a/platform/default/mbgl/gl/headless_backend.hpp b/platform/default/mbgl/gl/headless_backend.hpp index 8d86ea8c47..66f861e213 100644 --- a/platform/default/mbgl/gl/headless_backend.hpp +++ b/platform/default/mbgl/gl/headless_backend.hpp @@ -15,6 +15,7 @@ public: ~HeadlessBackend() override; void bind() override; + Size getFramebufferSize() const override; void updateAssumedState() override; void setSize(Size); diff --git a/platform/default/mbgl/gl/headless_frontend.cpp b/platform/default/mbgl/gl/headless_frontend.cpp index ad03706be7..5d2932258a 100644 --- a/platform/default/mbgl/gl/headless_frontend.cpp +++ b/platform/default/mbgl/gl/headless_frontend.cpp @@ -5,11 +5,11 @@ namespace mbgl { -HeadlessFrontend::HeadlessFrontend(float pixelRatio_, FileSource& fileSource, Scheduler& scheduler) - : HeadlessFrontend({ 256, 256 }, pixelRatio_, fileSource, scheduler) { +HeadlessFrontend::HeadlessFrontend(float pixelRatio_, FileSource& fileSource, Scheduler& scheduler, const optional<std::string> programCacheDir) + : HeadlessFrontend({ 256, 256 }, pixelRatio_, fileSource, scheduler, programCacheDir) { } -HeadlessFrontend::HeadlessFrontend(Size size_, float pixelRatio_, FileSource& fileSource, Scheduler& scheduler) +HeadlessFrontend::HeadlessFrontend(Size size_, float pixelRatio_, FileSource& fileSource, Scheduler& scheduler, const optional<std::string> programCacheDir) : size(size_), pixelRatio(pixelRatio_), backend({ static_cast<uint32_t>(size.width * pixelRatio), @@ -20,7 +20,7 @@ HeadlessFrontend::HeadlessFrontend(Size size_, float pixelRatio_, FileSource& fi renderer->render(*updateParameters); } }), - renderer(std::make_unique<Renderer>(backend, pixelRatio, fileSource, scheduler)) { + renderer(std::make_unique<Renderer>(backend, pixelRatio, fileSource, scheduler, GLContextMode::Unique, programCacheDir)) { } HeadlessFrontend::~HeadlessFrontend() = default; diff --git a/platform/default/mbgl/gl/headless_frontend.hpp b/platform/default/mbgl/gl/headless_frontend.hpp index 18d0d2527b..33503bc13b 100644 --- a/platform/default/mbgl/gl/headless_frontend.hpp +++ b/platform/default/mbgl/gl/headless_frontend.hpp @@ -3,6 +3,7 @@ #include <mbgl/renderer/renderer_frontend.hpp> #include <mbgl/gl/headless_backend.hpp> #include <mbgl/util/async_task.hpp> +#include <mbgl/util/optional.hpp> #include <memory> @@ -16,8 +17,8 @@ class Map; class HeadlessFrontend : public RendererFrontend { public: - HeadlessFrontend(float pixelRatio_, FileSource&, Scheduler&); - HeadlessFrontend(Size, float pixelRatio_, FileSource&, Scheduler&); + HeadlessFrontend(float pixelRatio_, FileSource&, Scheduler&, const optional<std::string> programCacheDir = {}); + HeadlessFrontend(Size, float pixelRatio_, FileSource&, Scheduler&, const optional<std::string> programCacheDir = {}); ~HeadlessFrontend() override; void reset() override; diff --git a/platform/default/mbgl/map/map_snapshotter.cpp b/platform/default/mbgl/map/map_snapshotter.cpp new file mode 100644 index 0000000000..95c46344fe --- /dev/null +++ b/platform/default/mbgl/map/map_snapshotter.cpp @@ -0,0 +1,76 @@ +#include <mbgl/map/map_snapshotter.hpp> + +#include <mbgl/actor/actor_ref.hpp> +#include <mbgl/gl/headless_frontend.hpp> +#include <mbgl/map/map.hpp> +#include <mbgl/storage/file_source.hpp> +#include <mbgl/style/style.hpp> +#include <mbgl/util/event.hpp> + +namespace mbgl { + +class MapSnapshotter::Impl { +public: + Impl(FileSource&, + Scheduler&, + const std::string& styleURL, + const Size&, + const float pixelRatio, + const CameraOptions&, + const optional<LatLngBounds> region, + const optional<std::string> programCacheDir); + + void snapshot(ActorRef<MapSnapshotter::Callback>); + +private: + HeadlessFrontend frontend; + Map map; +}; + +MapSnapshotter::Impl::Impl(FileSource& fileSource, + Scheduler& scheduler, + const std::string& styleURL, + const Size& size, + const float pixelRatio, + const CameraOptions& cameraOptions, + const optional<LatLngBounds> region, + const optional<std::string> programCacheDir) + : frontend(size, pixelRatio, fileSource, scheduler, programCacheDir) + , map(frontend, MapObserver::nullObserver(), size, pixelRatio, fileSource, scheduler, MapMode::Still) { + + map.getStyle().loadURL(styleURL); + + map.jumpTo(cameraOptions); + + // Set region, if specified + if (region) { + mbgl::EdgeInsets insets = { 0, 0, 0, 0 }; + std::vector<LatLng> latLngs = { region->southwest(), region->northeast() }; + map.jumpTo(map.cameraForLatLngs(latLngs, insets)); + } +} + +void MapSnapshotter::Impl::snapshot(ActorRef<MapSnapshotter::Callback> callback) { + map.renderStill([this, callback = std::move(callback)] (std::exception_ptr error) mutable { + callback.invoke(&MapSnapshotter::Callback::operator(), error, error ? PremultipliedImage() : frontend.readStillImage()); + }); +} + +MapSnapshotter::MapSnapshotter(FileSource& fileSource, + Scheduler& scheduler, + const std::string& styleURL, + const Size& size, + const float pixelRatio, + const CameraOptions& cameraOptions, + const optional<LatLngBounds> region, + const optional<std::string> programCacheDir) + : impl(std::make_unique<util::Thread<MapSnapshotter::Impl>>("Map Snapshotter", fileSource, scheduler, styleURL, size, pixelRatio, cameraOptions, region, programCacheDir)) { +} + +MapSnapshotter::~MapSnapshotter() = default; + +void MapSnapshotter::snapshot(ActorRef<MapSnapshotter::Callback> callback) { + impl->actor().invoke(&Impl::snapshot, std::move(callback)); +} + +} // namespace mbgl diff --git a/platform/default/mbgl/map/map_snapshotter.hpp b/platform/default/mbgl/map/map_snapshotter.hpp new file mode 100644 index 0000000000..0afa848fd8 --- /dev/null +++ b/platform/default/mbgl/map/map_snapshotter.hpp @@ -0,0 +1,40 @@ +#pragma once + +#include <mbgl/util/image.hpp> +#include <mbgl/util/thread.hpp> +#include <mbgl/util/optional.hpp> + +#include <exception> +#include <string> +#include <functional> + +namespace mbgl { + +template<class> class ActorRef; +struct CameraOptions; +class FileSource; +class Size; +class LatLngBounds; + +class MapSnapshotter { +public: + MapSnapshotter(FileSource& fileSource, + Scheduler& scheduler, + const std::string& styleURL, + const Size&, + const float pixelRatio, + const CameraOptions&, + const optional<LatLngBounds> region, + const optional<std::string> cacheDir = {}); + + ~MapSnapshotter(); + + using Callback = std::function<void (std::exception_ptr, PremultipliedImage)>; + void snapshot(ActorRef<Callback>); + +private: + class Impl; + std::unique_ptr<util::Thread<Impl>> impl; +}; + +} // namespace mbgl diff --git a/platform/default/mbgl/storage/file_source_request.hpp b/platform/default/mbgl/storage/file_source_request.hpp new file mode 100644 index 0000000000..6bd0d44df6 --- /dev/null +++ b/platform/default/mbgl/storage/file_source_request.hpp @@ -0,0 +1,31 @@ +#pragma once + +#include <mbgl/actor/actor_ref.hpp> +#include <mbgl/storage/file_source.hpp> +#include <mbgl/util/async_request.hpp> + +#include <memory> +#include <functional> + +namespace mbgl { + +class Mailbox; + +class FileSourceRequest : public AsyncRequest { +public: + FileSourceRequest(FileSource::Callback&& callback); + ~FileSourceRequest() final; + + void onCancel(std::function<void()>&& callback); + void setResponse(const Response& res); + + ActorRef<FileSourceRequest> actor(); + +private: + FileSource::Callback responseCallback = nullptr; + std::function<void()> cancelCallback = nullptr; + + std::shared_ptr<Mailbox> mailbox; +}; + +} // namespace mbgl diff --git a/platform/default/mbgl/storage/offline.cpp b/platform/default/mbgl/storage/offline.cpp index fd2d47819b..7670790be9 100644 --- a/platform/default/mbgl/storage/offline.cpp +++ b/platform/default/mbgl/storage/offline.cpp @@ -1,6 +1,7 @@ #include <mbgl/storage/offline.hpp> #include <mbgl/util/tile_cover.hpp> #include <mbgl/util/tileset.hpp> +#include <mbgl/util/projection.hpp> #include <rapidjson/document.h> #include <rapidjson/stringbuffer.h> @@ -23,18 +24,12 @@ OfflineTilePyramidRegionDefinition::OfflineTilePyramidRegionDefinition( } } -std::vector<CanonicalTileID> OfflineTilePyramidRegionDefinition::tileCover(SourceType type, uint16_t tileSize, const Range<uint8_t>& zoomRange) const { - double minZ = std::max<double>(util::coveringZoomLevel(minZoom, type, tileSize), zoomRange.min); - double maxZ = std::min<double>(util::coveringZoomLevel(maxZoom, type, tileSize), zoomRange.max); - - assert(minZ >= 0); - assert(maxZ >= 0); - assert(minZ < std::numeric_limits<uint8_t>::max()); - assert(maxZ < std::numeric_limits<uint8_t>::max()); +std::vector<CanonicalTileID> OfflineTilePyramidRegionDefinition::tileCover(style::SourceType type, uint16_t tileSize, const Range<uint8_t>& zoomRange) const { + const Range<uint8_t> clampedZoomRange = coveringZoomRange(type, tileSize, zoomRange); std::vector<CanonicalTileID> result; - for (uint8_t z = minZ; z <= maxZ; z++) { + for (uint8_t z = clampedZoomRange.min; z <= clampedZoomRange.max; z++) { for (const auto& tile : util::tileCover(bounds, z)) { result.emplace_back(tile.canonical); } @@ -43,6 +38,28 @@ std::vector<CanonicalTileID> OfflineTilePyramidRegionDefinition::tileCover(Sourc return result; } +uint64_t OfflineTilePyramidRegionDefinition::tileCount(style::SourceType type, uint16_t tileSize, const Range<uint8_t>& zoomRange) const { + + const Range<uint8_t> clampedZoomRange = coveringZoomRange(type, tileSize, zoomRange); + unsigned long result = 0;; + for (uint8_t z = clampedZoomRange.min; z <= clampedZoomRange.max; z++) { + result += util::tileCount(bounds, z, tileSize); + } + + return result; +} + +Range<uint8_t> OfflineTilePyramidRegionDefinition::coveringZoomRange(style::SourceType type, uint16_t tileSize, const Range<uint8_t>& zoomRange) const { + double minZ = std::max<double>(util::coveringZoomLevel(minZoom, type, tileSize), zoomRange.min); + double maxZ = std::min<double>(util::coveringZoomLevel(maxZoom, type, tileSize), zoomRange.max); + + assert(minZ >= 0); + assert(maxZ >= 0); + assert(minZ < std::numeric_limits<uint8_t>::max()); + assert(maxZ < std::numeric_limits<uint8_t>::max()); + return { static_cast<uint8_t>(minZ), static_cast<uint8_t>(maxZ) }; +} + OfflineRegionDefinition decodeOfflineRegionDefinition(const std::string& region) { rapidjson::GenericDocument<rapidjson::UTF8<>, rapidjson::CrtAllocator> doc; doc.Parse<0>(region.c_str()); diff --git a/platform/default/mbgl/storage/offline_download.cpp b/platform/default/mbgl/storage/offline_download.cpp index 7f0001f64b..ff61114888 100644 --- a/platform/default/mbgl/storage/offline_download.cpp +++ b/platform/default/mbgl/storage/offline_download.cpp @@ -80,7 +80,7 @@ OfflineRegionStatus OfflineDownload::getStatus() const { auto handleTiledSource = [&] (const variant<std::string, Tileset>& urlOrTileset, const uint16_t tileSize) { if (urlOrTileset.is<Tileset>()) { result.requiredResourceCount += - definition.tileCover(type, tileSize, urlOrTileset.get<Tileset>().zoomRange).size(); + definition.tileCount(type, tileSize, urlOrTileset.get<Tileset>().zoomRange); } else { result.requiredResourceCount += 1; const auto& url = urlOrTileset.get<std::string>(); @@ -90,7 +90,7 @@ OfflineRegionStatus OfflineDownload::getStatus() const { optional<Tileset> tileset = style::conversion::convertJSON<Tileset>(*sourceResponse->data, error); if (tileset) { result.requiredResourceCount += - definition.tileCover(type, tileSize, (*tileset).zoomRange).size(); + definition.tileCount(type, tileSize, (*tileset).zoomRange); } } else { result.requiredResourceCountIsPrecise = false; diff --git a/platform/default/mbgl/storage/offline_download.hpp b/platform/default/mbgl/storage/offline_download.hpp index c978ded931..437f221c11 100644 --- a/platform/default/mbgl/storage/offline_download.hpp +++ b/platform/default/mbgl/storage/offline_download.hpp @@ -60,7 +60,7 @@ private: std::deque<Resource> resourcesRemaining; void queueResource(Resource); - void queueTiles(SourceType, uint16_t tileSize, const Tileset&); + void queueTiles(style::SourceType, uint16_t tileSize, const Tileset&); }; } // namespace mbgl |