navigator.geolocation需HTTPS、用户授权、设备支持三前提,常见失败因环境不达标;getCurrentPosition()适合一次性定位,watchPosition()适合持续追踪;WGS84坐标须转GCJ02才适配国内地图。

浏览器里直接用 navigator.geolocation 就能拿到用户地理位置,但必须满足 HTTPS、用户授权、设备支持三个前提,缺一不可。
为什么 navigator.geolocation 调用没反应或报错
常见原因不是代码写错,而是环境不达标:
- 当前页面不是 HTTPS(本地
file://或 HTTP 站点下会被浏览器静默禁用) - 用户首次访问时拒绝了定位权限,之后再调用
getCurrentPosition()会直接进error回调,且error.code通常是1(PERMISSION_DENIED) - 设备没 GPS 模块(如某些台式机),或系统级定位服务被关闭(iOS/Android 设置里关了“定位服务”)
- 部分浏览器(如 Safari 在无用户交互上下文中)会延迟触发或直接拒绝请求
getCurrentPosition() 和 watchPosition() 怎么选
前者只取一次位置,后者持续监听变化,适合地图实时追踪:
-
getCurrentPosition():适合表单提交、签到、附近搜索等一次性场景;建议加timeout和maximumAge防卡死,例如{ timeout: 5000, maximumAge: 60000 } -
watchPosition():返回一个watchId,可用clearWatch(watchId)主动停止;注意它可能频繁触发,别在回调里直接更新 DOM 或发请求,建议节流 - 两者都支持第三个参数
options,其中enableHighAccuracy: true会尝试用 GPS(更准但更耗电、更慢),普通场景不建议默认开
拿到的坐标是 WGS84,但地图 SDK 要 GCJ02 怎么办
国内高德、百度、腾讯地图要求使用加密坐标系(GCJ02 或 BD09),而 navigator.geolocation 返回的是国际标准 WGS84 坐标,直接传过去会导致位置偏移几百米:
立即学习“Java免费学习笔记(深入)”;
- 不能靠“估算偏移量”硬调,不同地区偏移方向和大小不一致
- 推荐用现成转换库,比如
gcoord(轻量、无依赖):import { transform } from 'gcoord';
const wgs84 = [116.397428, 39.90923];
const gcj02 = transform(wgs84, gcoord.WGS84, gcoord.GCJ02); - 注意:百度地图用的是 BD09,需额外转一次,
gcoord也支持BD09类型
真正容易被忽略的不是怎么调 API,而是权限拒绝后的降级处理——比如显示手动输入地址入口,或者用 IP 地址粗略定位(fetch('https://ipapi.co/json/'))兜底。WGS84 到 GCJ02 的转换也常被当成“前端可省略步骤”,结果上线后发现所有标记点全歪了。











