使用Google Directions API绘制多标记点折线的问题求助
问题分析与解决方案
核心问题
你的代码存在三个关键问题,导致折线未按途经点顺序连接:
- API请求URL中
waypoints参数后多了一个多余的右大括号},引发参数解析失败 - 未在
waypoints参数中添加optimize:false,Google Directions API默认会优化途经点顺序,忽略你指定的路径 - 绘制折线时仅遍历第一个
leg的steps,且只取每个step的起点/终点,未解码完整的道路路线点
分步修复
1. 修正API请求URL
修改URL构建逻辑,解决参数错误和途经点优化问题:
// 处理途经点:排除已在origin/destination中指定的起点和终点 var waypointsList = latLen.sublist(1, latLen.length - 1); var ltLn = waypointsList .map((latLng) => "${latLng.latitude},${latLng.longitude}") .join("|"); // 构建正确的URL:添加optimize:false强制按指定顺序,移除多余的} url = "https://maps.googleapis.com/maps/api/directions/json?key=${Keys.googleApiKey}&units=metric&origin=${latLen.first.latitude},${latLen.first.longitude}&destination=${latLen.last.latitude},${latLen.last.longitude}&mode=driving&waypoints=optimize:false|$ltLn";
2. 修复折线绘制逻辑
使用PolylinePoints库解码完整的道路路线点,并遍历所有legs和steps:
首先在pubspec.yaml添加依赖:
dependencies: polyline_points: ^1.0.0
然后修改drawPolyLines方法:
import 'package:polyline_points/polyline_points.dart'; void drawPolyLines() async { String url = ""; http.Response? response; PolylinePoints polylinePoints = PolylinePoints(); // 处理途经点:排除起点和终点 var waypointsList = latLen.sublist(1, latLen.length - 1); var ltLn = waypointsList .map((latLng) => "${latLng.latitude},${latLng.longitude}") .join("|"); // 构建正确的请求URL,注意用GET请求而非POST url = "https://maps.googleapis.com/maps/api/directions/json?key=${Keys.googleApiKey}&units=metric&origin=${latLen.first.latitude},${latLen.first.longitude}&destination=${latLen.last.latitude},${latLen.last.longitude}&mode=driving&waypoints=optimize:false|$ltLn"; response = await http.get(Uri.parse(url)); pResponse = pRes.polylineResponseFromJson(response.body); log("请求URL: $url"); log("API响应: ${response.body}"); polylin.clear(); // 清空旧折线 List<LatLng> routePoints = []; try { // 遍历所有legs(每个途经点对应一个leg分段) for (var leg in pResponse.routes![0].legs!) { // 遍历当前leg的所有道路步骤 for (var step in leg.steps!) { // 解码step的polyline编码点,转换为LatLng格式 List<PointLatLng> decodedPoints = polylinePoints.decodePolyline(step.polyline!.points!); routePoints.addAll(decodedPoints.map((point) => LatLng(point.latitude, point.longitude))); } } // 添加完整的道路折线 if (routePoints.isNotEmpty) { polylin.add(Polyline( polylineId: const PolylineId("route"), points: routePoints, width: 3, color: Colors.red, )); } } catch (e) { log("绘制折线出错: $e"); rethrow; } }
额外注意事项
- Directions API仅支持GET请求,原代码中的
http.post会导致请求失败,需改为http.get - 移除代码中无用的
placemarks遍历逻辑,该代码未产生实际作用,还会增加不必要的地理编码请求 - 确保
latLen是包含所有标记点(起点、途经点、终点)的LatLng列表
问题效果截图:
内容的提问来源于stack exchange,提问作者Saurav
相关产品推荐
相关产品推荐

