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

求助:PHP路由加载本地JSON填充下拉框及Leaflet地图定位问题

问题描述

尝试通过PHP读取本地JSON国家边界数据,将国家列表填充到<select>下拉框,但始终无法正常运行;同时需要实现选中国家后,在Leaflet地图中自动定位到该国家。确认AJAX调用存在问题,已耗时多日未解决。

现有代码

HTML

<div class="wrapper">   
   <form class="form">
       <select class="custom-select custom-select-sm text-center border-secondary font-weight-bold text-uppercase" id="selCountry">
        <option value="1">Country</option>
       </select>
    </form>
</div>

PHP

<?php
    ini_set('display_errors', 'On');
    error_reporting(E_ALL);

    $executionStartTime = microtime(true);
    $result = file_get_contents("../js/countryBorders.geo.json");

    function compare($a, $b) {
        if ($a["name"] == $b["name"]) return 0;
        return ($a["name"] < $b["name"]) ? -1 : 1;
    }

    $decode = json_decode($result,true);
    $countries = [];

    for ($i = 0; $i < count($decode['features']); $i++) {
        array_push($countries,$decode['features'][$i]['properties']);
    };

    usort($countries, "compare");
    $output['status']['code'] = "200";
    $output['status']['name'] = "ok";
    $output['status']['description'] = "success";
    $output['status']['returnedIn'] = intval((microtime(true) - $executionStartTime) * 1000) . " ms";
    $output['data'] = $countries;

    header('Content-Type: application/json; charset=UTF-8');
    echo json_encode($output);
?>

AJAX

$.ajax({
    url: "php/select.php",
    type: 'POST',
    dataType: "json",
    
    success: function(result) {
        console.log(result);
    if (result.status.name == "ok") {
          $('#selCountry').append($('<option>', {
          value: result.data.border.features[i].properties.iso_a3,
          text: result.data.border.features[i].properties.name,
        }));
      
    }
  },
  error: function(jqXHR, textStatus, errorThrown) {
    console.log(textStatus, errorThrown);
  }
});

JSON数据结构

{
  "type": "FeatureCollection",
  "features": [
    {
      "type": "Feature",
      "properties": {
        "name": "Bahamas",
        "iso_a2": "BS",
        "iso_a3": "BHS",
        "iso_n3": "044"
      },
      "geometry": {
        "type": "MultiPolygon",
        "coordinates": []
      }
    }
  ]
}

解决方案

1. 修复AJAX填充下拉框问题

AJAX核心错误:PHP返回的result.data是整理好的国家属性数组(每个元素是properties对象),并非原始GeoJSON结构;同时缺少循环遍历逻辑,直接访问未定义的i变量。修改后的AJAX代码:

$.ajax({
    url: "php/select.php",
    type: 'POST',
    dataType: "json",
    
    success: function(result) {
        console.log(result);
        if (result.status.name == "ok") {
            // 清空默认选项外的内容,避免重复加载
            $('#selCountry').find('option:not(:first)').remove();
            // 遍历国家数组,添加下拉选项
            $.each(result.data, function(index, country) {
                $('#selCountry').append($('<option>', {
                    value: country.iso_a3, // 用iso_a3作为值,方便后续匹配地图数据
                    text: country.name
                }));
            });
        }
    },
    error: function(jqXHR, textStatus, errorThrown) {
        console.log(textStatus, errorThrown);
    }
});

2. 实现Leaflet地图定位功能

先加载Leaflet库,监听下拉框change事件,根据选中的iso_a3匹配对应GeoJSON几何数据,最后调用Leaflet方法完成定位。

步骤:

  1. 引入Leaflet资源:
<link rel="stylesheet" href="https://unpkg.com/leaflet@1.9.4/dist/leaflet.css" />
<script src="https://unpkg.com/leaflet@1.9.4/dist/leaflet.js"></script>
  1. 添加地图容器:
<div id="map" style="width: 100%; height: 400px;"></div>
  1. 初始化地图并实现定位逻辑:
// 初始化基础地图
var map = L.map('map').setView([0, 0], 2);
L.tileLayer('https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png', {
    attribution: '&copy; OpenStreetMap contributors'
}).addTo(map);

// 预加载完整的国家GeoJSON数据
var countryGeoData;
$.getJSON("../js/countryBorders.geo.json", function(data) {
    countryGeoData = data;
});

// 监听下拉框选择事件
$('#selCountry').on('change', function() {
    var selectedIsoA3 = $(this).val();
    if (selectedIsoA3 === '1') return; // 跳过默认选项

    // 匹配选中国家的GeoJSON特征
    var selectedCountry = countryGeoData.features.find(function(feature) {
        return feature.properties.iso_a3 === selectedIsoA3;
    });

    if (selectedCountry) {
        // 创建国家边界图层并添加到地图
        var countryLayer = L.geoJSON(selectedCountry);
        map.addLayer(countryLayer);
        // 定位到国家边界范围
        map.fitBounds(countryLayer.getBounds());
    }
});

额外注意事项

  • 确认PHP文件中../js/countryBorders.geo.json路径正确,文件权限为可读。
  • 检查iso_a3大小写是否与GeoJSON数据一致(通常为大写),避免匹配失败。
  • 若AJAX请求报错,打开浏览器开发者工具的Network面板,查看请求状态码和返回内容,排查路径或PHP语法错误。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.08 19:30:38