驾车导航
使用 sdk.Navi 进行当前网页内的汽车实时引导。步行使用独立步行控制器;静态距离查询使用驾车规划。
可接入的页面代码
安装当前 npm 包、引入 SDK CSS,页面提供有高度的 map 容器及 start、stop 按钮。把示例终点替换为用户选择的实际可达入口。以下为 ESM 写法,普通网页可使用 SukhaSDK.load(...)。
import {load} from '@sukha/maps';
const sdk = await load({key:'YOUR_WEB_KEY', serviceBaseUrl:'https://map.sukha.cn',
datasetId:'shan', language:'zh-CN', voiceLanguage:'zh-CN'});
const map = new sdk.Map('map', {center:[100.02228,21.67623], zoom:16});
const gps = new sdk.Geolocation({enableHighAccuracy:true, timeout:15000, maximumAge:0});
const navi = new sdk.Navi();
let alive = true, epoch = 0;
/** @type {import('@sukha/maps').Polyline | undefined} */
let routeLine;
navi.on('calculateRouteSuccess', event => {
if (!alive) return;
if (routeLine) routeLine.setPath(event.route.path);
else routeLine = new sdk.Polyline({map, path:event.route.path, strokeColor:'#1268e5'});
});
navi.on('naviInfoUpdate', info => {
console.log(info.instruction, info.remainingMeters, info.remainingSeconds);
});
navi.on('locationError', event => console.error(event.error));
navi.on('voiceError', event => console.error(event.error));
navi.on('arriveDestination', () => console.log('已到达目的地'));
async function startDriving() {
navi.unlockVoice(); // 必须仍在用户点击的同步阶段。
const ticket = ++epoch;
try {
const fix = await gps.getCurrentPosition();
if (!alive || ticket !== epoch) return;
await navi.calculateDriveRoute(fix.position, [100.024,21.678]);
if (!alive || ticket !== epoch) return;
const departure = Date.now()-fix.timestamp > 8000 ? await gps.getCurrentPosition() : fix;
if (!alive || ticket !== epoch) return;
await navi.startNavi({position:departure.position.toArray(), accuracy:departure.accuracy,
timestamp:departure.timestamp, speed:departure.speed, heading:departure.heading});
} catch (error) { if (alive) console.error(error.code, error.message); }
}
document.getElementById('start')?.addEventListener('click', () => { void startDriving(); });
document.getElementById('stop')?.addEventListener('click', () => { epoch++; navi.stopNavi(); });
window.addEventListener('pagehide', () => {
alive = false; epoch++; navi.destroy(); gps.destroy(); routeLine?.remove(); map.destroy();
}, {once:true});
这里的 gps.getCurrentPosition() 取得真实开始位置;开始后 Navi 自行订阅浏览器定位。不要再叠加另一个定时器注入虚构坐标。多次点击开始应由宿主禁用按钮或管理会话,防止并发开始操作。
调用与事件
| 接口 / 事件 | 说明 |
|---|---|
calculateDriveRoute(origin,destination,{policy,heading}) |
策略为 TIME 或 DISTANCE;heading 可省略;返回导航路线 |
startNavi(fix) |
Promise;需真实新鲜定位,不能传 Driving 的预览对象 |
naviInfoUpdate |
直接接收信息对象,含 instruction、remainingMeters、remainingSeconds、speed、accuracy、arrived |
locationChange |
事件中的 fix 为当前定位 |
locationError / voiceError |
错误对象位于 event.error |
arriveDestination |
到达事件;停止/订单完成等业务操作由宿主处理 |
setVoiceEnabled(false) / repeat() |
静音或重播当前指引 |
stopNavi() / destroy() |
停止会话 / 最终释放;不自动销毁宿主地图 |
原始速度按米/秒处理,显示 km/h 时乘 3.6。位置未知或不可靠时显示等待状态,不把缺失速度当成 0。
语音、断网与后台
先在点击时解锁语音,再等待异步定位与算路。可监听 offlinePreparation 或等待 prepareOfflineNavigation(),只在路线和当前语种录音均就绪时显示相应准备状态。离线偏航重算及浏览器后台运行仍不可用,边界见导航总览。