Exemplo n.º 1
0
CameraOptions Map::cameraForLatLngBounds(const LatLngBounds& bounds, optional<EdgeInsets> padding) const {
    return cameraForLatLngs({
        bounds.northwest(),
        bounds.southwest(),
        bounds.southeast(),
        bounds.northeast(),
    }, padding);
}
LatLngBounds ShapeAnnotationImpl::bounds() const {
    LatLngBounds result;

    for (const auto& segment : shape.segments) {
        for (const auto& point : segment) {
            result.extend(point);
        }
    }

    return result;
}
Exemplo n.º 3
0
LatLngBounds AnnotationManager::getBoundsForAnnotations(const AnnotationIDs& ids) const {
    LatLngBounds bounds;
    for (auto id : ids) {
        const auto annotation_it = annotations.find(id);
        if (annotation_it != annotations.end()) {
            bounds.extend(annotation_it->second->getBounds());
        }
    }

    return bounds;
}
Exemplo n.º 4
0
LatLngBounds AnnotationManager::getBoundsForAnnotations(const AnnotationIDs& ids) const {
    std::lock_guard<std::mutex> lock(mtx);

    LatLngBounds bounds;
    for (auto id : ids) {
        const auto annotation_it = annotations.find(id);
        if (annotation_it != annotations.end()) {
            bounds.extend(annotation_it->second->getPoint());
        }
    }

    return bounds;
}
Exemplo n.º 5
0
LatLngBounds AnnotationManager::getBoundsForAnnotations(const AnnotationIDs& ids) const {
    LatLngBounds result = LatLngBounds::getExtendable();

    for (const auto& id : ids) {
        if (pointAnnotations.find(id) != pointAnnotations.end()) {
            result.extend(pointAnnotations.at(id)->bounds());
        } else if (shapeAnnotations.find(id) != shapeAnnotations.end()) {
            result.extend(shapeAnnotations.at(id)->bounds());
        }
    }

    return result;
}
// Taken from https://github.com/mapbox/sphericalmercator#xyzbbox-zoom-tms_style-srs
// Computes the projected tiles for the lower left and upper right points of the bounds
// and uses that to compute the tile cover count
uint64_t tileCount(const LatLngBounds& bounds, uint8_t zoom){
    if (zoom == 0) {
        return 1;
    }
    auto sw = Projection::project(bounds.southwest(), zoom);
    auto ne = Projection::project(bounds.northeast(), zoom);
    auto maxTile = std::pow(2.0, zoom);
    auto x1 = floor(sw.x);
    auto x2 = ceil(ne.x) - 1;
    auto y1 = util::clamp(floor(sw.y), 0.0, maxTile - 1);
    auto y2 = util::clamp(floor(ne.y), 0.0, maxTile - 1);

    auto dx = x1 > x2 ? (maxTile - x1) + x2 : x2 - x1;
    auto dy = y1 - y2;
    return (dx + 1) * (dy + 1);
}
Exemplo n.º 7
0
// Taken from https://github.com/mapbox/sphericalmercator#xyzbbox-zoom-tms_style-srs
// Computes the projected tiles for the lower left and upper right points of the bounds
// and uses that to compute the tile cover count
uint64_t tileCount(const LatLngBounds& bounds, uint8_t zoom, uint16_t tileSize_){

    auto sw = Projection::project(bounds.southwest().wrapped(), zoom, tileSize_);
    auto ne = Projection::project(bounds.northeast().wrapped(), zoom, tileSize_);

    auto x1 = floor(sw.x/ tileSize_);
    auto x2 = floor((ne.x - 1) / tileSize_);
    auto y1 = floor(sw.y/ tileSize_);
    auto y2 = floor((ne.y - 1) / tileSize_);

    auto minX = ::fmax(std::min(x1, x2), 0);
    auto maxX = std::max(x1, x2);
    auto minY = (std::pow(2, zoom) - 1) - std::max(y1, y2);
    auto maxY = (std::pow(2, zoom) - 1) - ::fmax(std::min(y1, y2), 0);
    
    return (maxX - minX + 1) * (maxY - minY + 1);
}
TileCover::TileCover(const LatLngBounds&bounds_, int32_t z) {
    LatLngBounds bounds = LatLngBounds::hull(
        { std::max(bounds_.south(), -util::LATITUDE_MAX), bounds_.west() },
        { std::min(bounds_.north(),  util::LATITUDE_MAX), bounds_.east() });

    if (bounds.isEmpty() ||
        bounds.south() >  util::LATITUDE_MAX ||
        bounds.north() < -util::LATITUDE_MAX) {
        bounds = LatLngBounds::world();
    }

    auto sw = Projection::project(bounds.southwest(), z);
    auto ne = Projection::project(bounds.northeast(), z);
    auto se = Projection::project(bounds.southeast(), z);
    auto nw = Projection::project(bounds.northwest(), z);

    Polygon<double> p({ {sw, nw, ne, se, sw} });
    impl = std::make_unique<TileCover::Impl>(z, p, false);
}
std::vector<UnwrappedTileID> tileCover(const LatLngBounds& bounds_, int32_t z) {
    if (bounds_.isEmpty() ||
        bounds_.south() >  util::LATITUDE_MAX ||
        bounds_.north() < -util::LATITUDE_MAX) {
        return {};
    }

    LatLngBounds bounds = LatLngBounds::hull(
        { std::max(bounds_.south(), -util::LATITUDE_MAX), bounds_.west() },
        { std::min(bounds_.north(),  util::LATITUDE_MAX), bounds_.east() });

    return tileCover(
        Projection::project(bounds.northwest(), z),
        Projection::project(bounds.northeast(), z),
        Projection::project(bounds.southeast(), z),
        Projection::project(bounds.southwest(), z),
        Projection::project(bounds.center(), z),
        z);
}
Exemplo n.º 10
0
void MapSnapshotter::Impl::setRegion(LatLngBounds region) {
    mbgl::EdgeInsets insets = { 0, 0, 0, 0 };
    std::vector<LatLng> latLngs = { region.southwest(), region.northeast() };
    map.jumpTo(map.cameraForLatLngs(latLngs, insets));
}
Exemplo n.º 11
0
std::vector<UnwrappedTileID> tileCover(const LatLngBounds& bounds_, int32_t z) {
    if (bounds_.isEmpty() ||
        bounds_.south() >  util::LATITUDE_MAX ||
        bounds_.north() < -util::LATITUDE_MAX) {
        return {};
    }

    LatLngBounds bounds = LatLngBounds::hull(
        { std::max(bounds_.south(), -util::LATITUDE_MAX), bounds_.west() },
        { std::min(bounds_.north(),  util::LATITUDE_MAX), bounds_.east() });

    const TransformState state;
    return tileCover(
        TileCoordinate::fromLatLng(state, z, bounds.northwest()).p,
        TileCoordinate::fromLatLng(state, z, bounds.northeast()).p,
        TileCoordinate::fromLatLng(state, z, bounds.southeast()).p,
        TileCoordinate::fromLatLng(state, z, bounds.southwest()).p,
        TileCoordinate::fromLatLng(state, z, bounds.center()).p,
        z);
}
Exemplo n.º 12
0
AnnotationIDs AnnotationManager::getAnnotationsInBounds(const LatLngBounds& queryBounds,
                                                        const uint8_t maxZoom,
                                                        const AnnotationType& type) const {
    const uint8_t z = maxZoom;
    const uint32_t z2 = 1 << z;
    const vec2<double> swPoint = projectPoint(queryBounds.sw);
    const vec2<double> nePoint = projectPoint(queryBounds.ne);

    // tiles number y from top down
    const TileID nwTile(z, swPoint.x * z2, nePoint.y * z2, z);
    const TileID seTile(z, nePoint.x * z2, swPoint.y * z2, z);

    std::unordered_set<uint32_t> matchingAnnotations;

    for (auto& tile : tiles) {
        TileID id = tile.first;
        if (id.z == z) {
            if (id.x >= nwTile.x && id.x <= seTile.x && id.y >= nwTile.y && id.y <= seTile.y) {
                if (id.x > nwTile.x && id.x < seTile.x && id.y > nwTile.y && id.y < seTile.y) {
                    // Trivial accept; this tile is completely inside the query bounds, so
                    // we'll return all of its annotations that match type (if specified).
                    if (type != AnnotationType::Any) {
                        std::copy_if(tile.second.first.begin(), tile.second.first.end(),
                                     std::inserter(matchingAnnotations, matchingAnnotations.begin()),
                                     [&](const uint32_t annotationID) -> bool {
                            const auto it = annotations.find(annotationID);
                            if (it != annotations.end()) {
                                return (it->second->type == type);
                            } else {
                                return false;
                            }
                        });
                    } else {
                        std::copy(tile.second.first.begin(), tile.second.first.end(),
                                  std::inserter(matchingAnnotations, matchingAnnotations.begin()));
                    }
                } else {
                    // This tile is intersected by the query bounds. We need to check the
                    // tile's annotations' bounding boxes individually.
                    std::copy_if(tile.second.first.begin(), tile.second.first.end(),
                                 std::inserter(matchingAnnotations, matchingAnnotations.begin()),
                                 [&](const uint32_t annotationID) -> bool {
                        const auto it = annotations.find(annotationID);
                        if (it != annotations.end()) {
                            // check type
                            if (type != AnnotationType::Any && it->second->type != type) {
                                return false;
                            }

                            // check bounds
                            if (it->second->type == AnnotationType::Point) {
                                return queryBounds.contains(it->second->getPoint());
                            } else if (it->second->type == AnnotationType::Shape) {
                                return queryBounds.intersects(it->second->getBounds());
                            }
                        }
                        return false;
                    });
                }
            }
        }
    }

    return AnnotationIDs(matchingAnnotations.begin(), matchingAnnotations.end());
}