如何在tkintermapview中绘制列表选点间路线并修复距离计算问题?
基于tkintermapview的路线绘制与距离计算修复方案
一、修复路线绘制函数(draw_route)
AI生成的代码错误使用了set_path方法——tkintermapview的set_path无需循环调用,直接传入完整坐标列表即可生成连贯路线。同时需先清除旧标记和路径,避免重复绘制导致的显示异常:
def draw_route(self, coords): # 清除已有内容,防止叠加绘制 self.map_widget.delete_all_markers() self.map_widget.delete_all_path() # 添加带序号的途经点标记 for idx, (lat, lon) in enumerate(coords): self.map_widget.set_marker(lat, lon, text=f"途经点 {idx+1}", marker_color="red") # 绘制完整路线 if len(coords) >= 2: self.map_widget.set_path(coords, color="blue", width=2)
核心修正点:
- 调用
delete_all_markers和delete_all_path清空旧内容 set_path直接接收坐标列表(元素为(纬度, 经度)元组),无需拆分起点终点- 给标记添加序号,便于区分途经点顺序
二、修复距离计算函数(calculate_distance)
当前代码计算的是球面大圆直线距离,与实际运输道路距离偏差较大;同时存在文本占位符无效的问题。以下分两种场景修复:
场景1:继续使用球面距离(仅作参考)
确保great_circle导入正确,修正文本显示逻辑:
from geopy.distance import great_circle def calculate_distance(self): if len(self.route_coords) < 2: self.distance_label.configure(text="请选择至少2个途经点") return total_distance = 0.0 for i in range(len(self.route_coords) - 1): start = self.route_coords[i] end = self.route_coords[i + 1] # 确保坐标格式为(纬度, 经度),与great_circle参数要求匹配 total_distance += great_circle(start, end).kilometers self.distance_label.configure(text=f"直线总距离: {total_distance:.2f} KM")
场景2:计算实际道路距离(更贴合运输需求)
需调用第三方地图API(如OpenRouteService)获取道路导航距离,示例代码如下:
import requests def calculate_road_distance(self): if len(self.route_coords) < 2: self.distance_label.configure(text="请选择至少2个途经点") return # 转换坐标为API要求的[经度, 纬度]格式 waypoints = ";".join([f"{lon},{lat}" for lat, lon in self.route_coords]) api_key = "你的API密钥" # 需自行申请OpenRouteService密钥 request_url = f"https://api.openrouteservice.org/v2/directions/driving-car?api_key={api_key}&start={waypoints.split(';')[0]}&end={waypoints.split(';')[-1]}&waypoints={';'.join(waypoints.split(';')[1:-1])}" try: response = requests.get(request_url) data = response.json() road_distance = data['features'][0]['properties']['segments'][0]['distance'] / 1000 # 转换为公里 self.distance_label.configure(text=f"道路总距离: {road_distance:.2f} KM") except Exception as e: self.distance_label.configure(text="距离计算失败") print(f"API调用异常: {e}")
三、使用示例
# 示例地点坐标列表(纬度, 经度) route_locations = [ (39.9042, 116.4074), # 北京 (31.2304, 121.4737), # 上海 (23.1291, 113.2644) # 广州 ] # 绘制路线 self.draw_route(route_locations) # 计算并显示距离 self.calculate_distance() # 或调用self.calculate_road_distance()
内容的提问来源于stack exchange,提问作者Ratte
相关产品推荐
相关产品推荐

