欢迎来到徐庆高(Tea)的个人博客网站
磨难很爱我,一度将我连根拔起。从惊慌失措到心力交瘁,我孤身一人,但并不孤独无依。依赖那些依赖我的人,信任那些信任我的人,帮助那些给予我帮助的人。如果我愿意,可以分裂成无数面镜子,让他们看见我,就像看见自己。察言观色和模仿学习是我的领域。像每个深受创伤的人那样,最终,我学会了随遇而安。
当前位置: 日志文章 > 详细内容

Python利用GeoPandas打造一个交互式中国地图选择器

2025年08月12日 Python
在数据分析和可视化领域,地图是展示地理信息的强大工具。它能直观地揭示数据在空间上的分布模式。今天,我将带你深入了解一个使用 python、wxpython 和 geopandas 构建的交互式中国地图

在数据分析和可视化领域,地图是展示地理信息的强大工具。它能直观地揭示数据在空间上的分布模式。今天,我将带你深入了解一个使用 pythonwxpythongeopandas 构建的交互式中国地图行政区划选择器。这个应用不仅能让你轻松选择省份,还能将选定的区域高亮显示在地图上,并支持导出地图截图和自动保存状态。

c:\pythoncode\new\china_map_app.py

技术栈概览

在深入代码之前,我们先了解一下这个项目使用的主要技术栈:

  • wxpython:一个用于创建图形用户界面(gui)的跨平台 python 库。它提供了丰富的控件和事件处理机制,是构建桌面应用的利器。
  • geopandas:一个强大的库,它扩展了 pandas 的功能,使其能够处理地理空间数据。你可以把它看作是 pandas 的地理空间版,可以方便地读取、操作和绘制 geojson、shapefile 等格式的地理数据。
  • matplotlib:python 中最流行的绘图库之一。geopandas 依赖它来完成地图的绘制。
  • python 标准库:包括 json(用于读写应用状态)和 os(用于文件路径操作)。

整个应用的核心思想是:使用 wxpython 构建 gui 框架,利用 geopandas 读取和渲染地图数据,再通过事件绑定将 gui 按钮操作与地图的重新绘制联系起来。

代码结构分析

我们的应用主要由一个主窗口类 chinamapframe 组成。让我们逐一剖析它的关键部分。

1. __init__ 方法:初始化与状态管理

__init__ 中,我们完成了应用的初始化工作:

class chinamapframe(wx.frame):
    def __init__(self):
        super().__init__(none, title="中国地图行政区划选择器", size=(1200, 800))
        
        self.state_file = "map_state.json"
        
        # 定义所有省份列表
        self.provinces = [...] 
        # 定义省份名称映射,以兼容不同地图文件的命名方式
        self.province_mapping = {...}
        
        self.selected_provinces = set()
        self.gdf = none
        self.last_map_file = none # 存储上次加载成功的地图文件路径
        
        self.init_ui()
        self.load_state()
        self.load_geo_data()
        
        self.bind(wx.evt_close, self.on_close)

这里定义了几个重要的实例变量:

  • self.provinces:一个包含所有中国省份、自治区和直辖市的列表。
  • self.selected_provinces:一个 set 集合,用于高效地存储当前选中的省份,方便添加和删除。
  • self.gdf:geopandas 的核心数据结构,用于存储从 geojson 或 shapefile 文件加载的地理数据。
  • self.last_map_file:这是一个关键改进!它记录了上一次成功加载的地图文件路径,以便应用下次启动时能自动加载。

load_state()on_close() 方法负责应用的状态持久化。当程序关闭时,save_state() 会将 self.selected_provincesself.last_map_file 保存到 map_state.json 文件中。下次启动时,load_state() 会自动读取这个文件,恢复到上次关闭时的状态,这大大提升了用户体验。

2. init_ui 方法:构建用户界面

init_ui 方法负责构建整个窗口的布局和控件。它使用了 wx.boxsizerwx.gridsizer 来组织界面。

def init_ui(self):
    # ...
    # 上部分:地图区域,使用 figurecanvas 承载 matplotlib 图
    self.figure = figure(figsize=(12, 8), dpi=80)
    self.canvas = figurecanvas(panel, -1, self.figure)
    # ...
    # 下部分:按钮区域,使用 gridsizer 布局
    button_sizer = wx.gridsizer(rows=0, cols=6, hgap=5, vgap=5)
    # ...
    # 控制按钮,包括新增的“导出地图”按钮
    control_sizer.add(load_btn, 0, wx.right, 10)
    control_sizer.add(export_btn, 0)
    # ...

这里,figurecanvaswxagg 是连接 matplotlib 图形和 wxpython 窗口的关键桥梁。地图将在 matplotlib 的 figure 对象上绘制,并通过 figurecanvas 呈现在窗口中。

新增的“导出地图”按钮(export_btn)及其事件绑定,为用户提供了保存地图视图的功能。

3. load_geo_data 与 on_load_geo_file:数据加载逻辑

这两个方法是应用的核心数据加载部分。

  • load_geo_data 实现了智能加载。它首先检查 self.last_map_file 是否有效,如果有效则直接加载。如果无效,它会尝试加载几个预设的默认文件名(如 china.geojson)。这种设计保证了应用在大多数情况下都能找到并加载地图数据。
  • on_load_geo_file 则响应“加载地图文件”按钮的点击事件,通过文件对话框让用户手动选择地图文件。加载成功后,它会更新 self.last_map_file 并重新绘制地图。

4. create_map 方法:地图绘制核心

这是地图可视化的核心逻辑。它根据 self.selected_provinces 的状态,为每个行政区划分配不同的颜色,然后调用 geopandas 的 plot 方法进行绘制。

def create_map(self):
    if self.gdf is none:
        self.show_no_data_message()
        return

    self.figure.clear()
    ax = self.figure.add_subplot(111)

    colors = []
    # 遍历 geodataframe 的每一行
    for idx, row in self.gdf.iterrows():
        is_selected = false
        province_name = none
        # 尝试匹配不同的列名('name', 'name', 'province' 等)
        # ...
        
        # 匹配选中的省份
        if province_name:
            for selected_province in self.selected_provinces:
                # 使用直接匹配和映射匹配,提高兼容性
                # ...
                
        colors.append('#0066ff' if is_selected else '#e6f3ff')

    self.gdf.plot(ax=ax, color=colors, edgecolor='white', linewidth=0.5)
    # ... 绘制图例和标题 ...
    self.canvas.draw()

代码中的一个亮点是它对地图文件列名的鲁棒性。它会尝试匹配多个常见的列名('name', 'name', '省份' 等),以确保它能兼容不同来源的 geojson 或 shapefile 文件。

5. on_province_click 与 on_export_map:交互与导出

on_province_click 负责处理省份按钮的点击事件。它会 toggles(切换)省份在 self.selected_provinces 集合中的状态,并改变按钮的背景颜色,最后调用 create_map 来更新地图视图。

on_export_map 则是新增的导出功能。它使用 wx.filedialog 弹出保存对话框,然后调用 self.figure.savefig(filepath, dpi=300) 将当前 matplotlib 的 figure 保存为高分辨率的 png 图片。

如何运行和使用

要运行这个应用,请确保你已经安装了所有必需的库:

pip install wxpython geopandas matplotlib

然后,你需要一个中国行政区划的 geojson 或 shapefile 文件。你可以在 load_geo_data 方法中指定的几个默认文件名(china.geojson 等),或者在 github 等网站找到类似的文件,然后通过“加载地图文件”按钮导入。

运行脚本后,你会看到一个包含中国地图和所有省份按钮的窗口。你可以:

  • 点击按钮来选择或取消选择省份。
  • 使用“全选”和“清除所有”按钮来快速操作。
  • 点击“导出地图”将当前视图保存为图片。

这个应用是一个很好的例子,展示了如何将多个 python 库(gui、地理空间数据、绘图)有机地结合起来,创建一个功能实用且用户友好的桌面工具。通过这种方式,你可以将复杂的数据处理和可视化任务封装在一个直观的界面中,大大降低了非技术人员的使用门槛。

到此这篇关于python利用geopandas打造一个交互式中国地图选择器的文章就介绍到这了,更多相关python交互式中国地图选择器内容请搜索代码网以前的文章或继续浏览下面的相关文章希望大家以后多多支持代码网!