diff options
author | Asheem Mamoowala <asheem.mamoowala@mapbox.com> | 2018-01-05 06:35:31 -0800 |
---|---|---|
committer | Asheem Mamoowala <asheem.mamoowala@mapbox.com> | 2018-02-08 12:39:30 -0800 |
commit | 64374711a09f27c41c93eb6b72d0f6a560234083 (patch) | |
tree | c96aece37da9d5a17dc6029bb89d1e6047a2eac6 /include | |
parent | aeba621573d77e1ce4f72b1e9b39bde92bf174a2 (diff) | |
download | qtlocation-mapboxgl-64374711a09f27c41c93eb6b72d0f6a560234083.tar.gz |
Support TileJSON bounds property (#10701)
* [core] Parse TileJSON bounds property
* [core] Add TileRange and LatLngBounds::contains(CanonicalTileID)
Move LatLngBounds::contains impl to cpp file
* [core] Skip tile creation outside of tileset bounds
* [core] Fix TileRange for wrapped bounds and use for CustomTileLoader instead of LatLngBounds comparisons for tiles.
Diffstat (limited to 'include')
-rw-r--r-- | include/mbgl/style/conversion/tileset.hpp | 31 | ||||
-rw-r--r-- | include/mbgl/util/geo.hpp | 18 | ||||
-rw-r--r-- | include/mbgl/util/projection.hpp | 4 | ||||
-rw-r--r-- | include/mbgl/util/tileset.hpp | 14 |
4 files changed, 51 insertions, 16 deletions
diff --git a/include/mbgl/style/conversion/tileset.hpp b/include/mbgl/style/conversion/tileset.hpp index 377170aa6a..6577e39576 100644 --- a/include/mbgl/style/conversion/tileset.hpp +++ b/include/mbgl/style/conversion/tileset.hpp @@ -10,6 +10,11 @@ namespace conversion { template <> struct Converter<Tileset> { public: + + bool validateLatitude(const double lat) const { + return lat < 90 && lat > -90; + } + template <class V> optional<Tileset> operator()(const V& value, Error& error) const { Tileset result; @@ -72,6 +77,32 @@ public: result.attribution = std::move(*attribution); } + auto boundsValue = objectMember(value, "bounds"); + if (boundsValue) { + if (!isArray(*boundsValue) || arrayLength(*boundsValue) != 4) { + error = { "bounds must be an array with left, bottom, top, and right values" }; + return {}; + } + optional<double> left = toDouble(arrayMember(*boundsValue, 0)); + optional<double> bottom = toDouble(arrayMember(*boundsValue, 1)); + optional<double> right = toDouble(arrayMember(*boundsValue, 2)); + optional<double> top = toDouble(arrayMember(*boundsValue, 3)); + + if (!left || !right || !bottom || !top) { + error = { "bounds array must contain numeric longitude and latitude values" }; + return {}; + } + if (!validateLatitude(*bottom) || !validateLatitude(*top) || top <= bottom){ + error = { "bounds latitude values must be between -90 and 90 with bottom less than top" }; + return {}; + } + if(*left >= *right) { + error = { "bounds left longitude should be less than right longitude" }; + return {}; + } + result.bounds = LatLngBounds::hull({ *bottom, *left }, { *top, *right }); + } + return result; } }; diff --git a/include/mbgl/util/geo.hpp b/include/mbgl/util/geo.hpp index 6d725b102b..dacdb968f3 100644 --- a/include/mbgl/util/geo.hpp +++ b/include/mbgl/util/geo.hpp @@ -154,19 +154,15 @@ public: sw.longitude() > ne.longitude(); } - bool contains(const LatLng& point) const { - return (point.latitude() >= sw.latitude() && - point.latitude() <= ne.latitude() && - point.longitude() >= sw.longitude() && - point.longitude() <= ne.longitude()); + bool crossesAntimeridian() const { + return (sw.wrapped().longitude() > ne.wrapped().longitude()); } - bool intersects(const LatLngBounds area) const { - return (area.ne.latitude() > sw.latitude() && - area.sw.latitude() < ne.latitude() && - area.ne.longitude() > sw.longitude() && - area.sw.longitude() < ne.longitude()); - } + bool contains(const CanonicalTileID& tileID) const; + bool contains(const LatLng& point, LatLng::WrapMode wrap = LatLng::Unwrapped) const; + bool contains(const LatLngBounds& area, LatLng::WrapMode wrap = LatLng::Unwrapped) const; + + bool intersects(const LatLngBounds area, LatLng::WrapMode wrap = LatLng::Unwrapped) const; private: LatLng sw; diff --git a/include/mbgl/util/projection.hpp b/include/mbgl/util/projection.hpp index f64502c5bc..a9c12e595b 100644 --- a/include/mbgl/util/projection.hpp +++ b/include/mbgl/util/projection.hpp @@ -78,6 +78,10 @@ public: return project_(latLng, worldSize(scale)); } + static Point<double> project(const LatLng& latLng, uint8_t zoom) { + return project_(latLng, std::pow(2.0, zoom)); + } + static LatLng unproject(const Point<double>& p, double scale, LatLng::WrapMode wrapMode = LatLng::Unwrapped) { auto p2 = p * util::DEGREES_MAX / worldSize(scale); return LatLng { diff --git a/include/mbgl/util/tileset.hpp b/include/mbgl/util/tileset.hpp index 61aa47d4ea..7bef0e89ed 100644 --- a/include/mbgl/util/tileset.hpp +++ b/include/mbgl/util/tileset.hpp @@ -2,7 +2,9 @@ #include <mbgl/util/range.hpp> #include <mbgl/util/constants.hpp> - +#include <mbgl/util/optional.hpp> +#include <mbgl/util/geo.hpp> +#include <tuple> #include <vector> #include <string> #include <cstdint> @@ -17,6 +19,7 @@ public: Range<uint8_t> zoomRange; std::string attribution; Scheme scheme; + optional<LatLngBounds> bounds; Tileset(std::vector<std::string> tiles_ = std::vector<std::string>(), Range<uint8_t> zoomRange_ = { 0, util::DEFAULT_MAX_ZOOM }, @@ -25,13 +28,14 @@ public: : tiles(std::move(tiles_)), zoomRange(std::move(zoomRange_)), attribution(std::move(attribution_)), - scheme(scheme_) {} + scheme(scheme_), + bounds() {} - // TileJSON also includes center, zoom, and bounds, but they are not used by mbgl. + // TileJSON also includes center and zoom but they are not used by mbgl. friend bool operator==(const Tileset& lhs, const Tileset& rhs) { - return std::tie(lhs.tiles, lhs.zoomRange, lhs.attribution, lhs.scheme) - == std::tie(rhs.tiles, rhs.zoomRange, rhs.attribution, rhs.scheme); + return std::tie(lhs.tiles, lhs.zoomRange, lhs.attribution, lhs.scheme, lhs.bounds) + == std::tie(rhs.tiles, rhs.zoomRange, rhs.attribution, rhs.scheme, rhs.bounds); } }; |