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

Kivy Python中如何配置For循环实现多架飞机位置坐标的全部展示

解决多架飞机位置只显示一个的问题

你的问题出在循环里一直在修改同一个MapMarkerPopup的属性,而不是为每架飞机创建独立的标记。原来的kv文件里只定义了一个固定的markerview,循环中每次迭代都会覆盖它的坐标和角度,最后自然只能看到最后一架飞机的位置。

下面是修改后的完整代码,我会一步步说明核心改动:

第一步:调整main.kv,给MapView添加ID并移除固定标记

我们需要动态添加标记,所以先去掉kv里固定的MapMarkerPopup,给MapView加上ID方便后续在Python代码中操作:

#:import MapView kivy_garden.mapview.MapView
<ExpertServer>:
    name: 'expert'
    FloatLayout:
        MapView:
            id: mapview
            zoom: 3
            lat: 0
            lon: 0
            double_tap_zoom: True

第二步:修改main.py,循环创建新标记并挂载到地图

在循环中为每架飞机实例化一个新的MapMarkerPopup,同时把原来kv里的旋转Canvas逻辑用Python代码实现,最后将标记添加到MapView中:

from kivy_garden.mapview import MapMarkerPopup
from kivy.graphics import PushMatrix, PopMatrix, Rotate
from kivy.uix.screenmanager import Screen
from kivymd.app import MDApp
from kivy.lang import Builder

def get_json():
    # 这里模拟你的API返回数据,替换成实际接口调用即可
    return [
        {"latitude": 39.9042, "longitude": 116.4074, "heading": 90},
        {"latitude": 31.2304, "longitude": 121.4737, "heading": 180},
        {"latitude": 23.1291, "longitude": 113.2644, "heading": 270}
    ]

class ExpertServer(Screen):
    def __init__(self, **kwargs):
        super().__init__(**kwargs)
        data = get_json()
        for plane in data:
            # 为当前飞机创建独立的标记实例
            marker = MapMarkerPopup(
                lat=plane['latitude'],
                lon=plane['longitude'],
                source="map_marker.png"
            )
            # 添加旋转Canvas指令,和原kv逻辑保持一致
            with marker.canvas.before:
                PushMatrix()
                rotate = Rotate(angle=plane['heading'], origin=marker.center)
                # 绑定角度更新,后续如果飞机航向变化可以直接修改rotate.angle
                marker.bind(center=lambda _, c: setattr(rotate, 'origin', c))
            with marker.canvas.after:
                PopMatrix()
            
            # 将新标记添加到地图组件中
            self.ids.mapview.add_widget(marker)

class MyApp(MDApp):
    def build(self):
        Builder.load_file('main.kv')
        self.sm = ScreenManager()
        self.sm.add_widget(Screen(name='menu'))  # 保留你的原有菜单页逻辑
        self.sm.add_widget(ExpertServer(name='expert'))
        return self.sm

MyApp().run()

核心改动说明:

  • 放弃复用单个标记:不再修改同一个标记的属性,而是为每架飞机生成独立的MapMarkerPopup实例
  • 迁移Canvas旋转逻辑:动态创建的标记无法直接使用kv里的Canvas定义,所以用Python代码实现同样的旋转效果
  • 挂载新标记到地图:通过add_widget方法将每个新标记都添加到MapView,确保所有飞机位置都能显示

这样修改后,循环每执行一次就会生成一个新的飞机标记,所有飞机的位置都会完整展示在地图上了。

内容的提问来源于stack exchange,提问作者Dalmo Cabral

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.04.28 13:57:43