You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用osmdroid NominatimPOIProvider获取附近公交站遇坐标范围异常

解决osmdroid NominatimPOIProvider的纬度范围异常问题

看起来你遇到的这个异常是因为Web墨卡托投影的纬度范围限制导致的——osmdroid的BoundingBox类对纬度有严格的范围校验,超出[-85.05112877980658, 85.05112877980658]就会抛出这个错误。即使你觉得当前坐标没问题,也可能是在计算搜索范围时出现了溢出。

我给你几个可行的解决思路,按优先级来:

1. 先校验并修正当前位置坐标

首先确认myLocationNewOverlay.getMyLocation()返回的坐标是否真的在合法范围内。有时候定位模块可能会返回异常值(比如纬度91或者-91),你可以先做个钳制处理:

public void poinOfInt(View view){ 
    GeoPoint bus_stop = myLocationNewOverlay.getMyLocation(); 
    // 先校验并修正纬度到Web墨卡托允许的范围
    if (bus_stop != null) {
        double clampedLat = Math.max(-85.05112877980658, Math.min(85.05112877980658, bus_stop.getLatitude()));
        bus_stop.setLatitude(clampedLat);
    } else {
        // 定位失败的处理逻辑,比如提示用户
        Toast.makeText(this, "无法获取当前位置", Toast.LENGTH_SHORT).show();
        return;
    }
    
    NominatimPOIProvider poiProvider = new NominatimPOIProvider(BuildConfig.APPLICATION_ID); 
    // 缩小搜索半径,避免范围溢出
    ArrayList<POI> pois = poiProvider.getPOICloseTo(bus_stop, "highway", 20, 100); 
    // 后续代码不变...
}

2. 缩小搜索半径

你当前设置的搜索半径是50(单位为千米),如果你的当前位置纬度很高(比如接近80度),这个半径会让计算出的south纬度超出限制。可以尝试把半径缩小到20或者10千米,看看是否能解决问题。

3. 手动构建合法的BoundingBox(最稳妥)

如果上面的方法还是不行,你可以手动构建不会超出范围的BoundingBox,然后调用getPOIInBoundingBox方法:

public void poinOfInt(View view){ 
    GeoPoint bus_stop = myLocationNewOverlay.getMyLocation(); 
    if (bus_stop == null) {
        Toast.makeText(this, "无法获取当前位置", Toast.LENGTH_SHORT).show();
        return;
    }
    
    // 手动计算BoundingBox,钳制纬度范围
    double lat = bus_stop.getLatitude();
    double lon = bus_stop.getLongitude();
    double radiusKm = 20; // 搜索半径,单位千米
    // 粗略计算经纬度范围(简单近似,适合低纬度地区,高纬度可使用更精确的球面距离计算)
    double deltaLat = radiusKm / 111.0; // 1度纬度≈111千米
    double deltaLon = radiusKm / (111.0 * Math.cos(Math.toRadians(lat)));
    
    double south = Math.max(-85.05112877980658, lat - deltaLat);
    double north = Math.min(85.05112877980658, lat + deltaLat);
    double west = lon - deltaLon;
    double east = lon + deltaLon;
    
    BoundingBox safeBox = new BoundingBox(north, east, south, west);
    
    NominatimPOIProvider poiProvider = new NominatimPOIProvider(BuildConfig.APPLICATION_ID); 
    ArrayList<POI> pois = poiProvider.getPOIInBoundingBox(safeBox, "highway", 100); 
    // 后续代码不变...
}

问题根源说明

Web墨卡托投影(osmdroid默认使用的投影)无法表示纬度超过±85.0511的区域,所以BoundingBox类会严格校验这个范围。当你调用getPOICloseTo时,它会根据当前坐标和半径计算出一个包围盒,如果这个包围盒的south或north超出了限制,就会抛出你看到的异常。

内容的提问来源于stack exchange,提问作者Idácio Zibia

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.13 07:58:12