如何基于省份选择通过JSON动态填充城市下拉框?
省份与城市联动下拉框问题解决
问题背景
需要实现两个联动下拉框:选择加泰罗尼亚的省份后,城市下拉框仅展示对应省份下辖的城市。现有JSON结构中,省份对应嵌套数组形式的城市列表,已成功渲染省份下拉框,但城市下拉框渲染时出现所有城市拼接成单个选项的问题。
现有JSON结构(精简版)
{ "Barcelona": [ ["Abrera"], ["Aguilar de Segarra"], ["Alella"] ], "Girona": [ ["Agullana"], ["Aiguaviva"], ["Albanyà"] ], "Tarragona": [ ["Aiguamúrcia"], ["Albinyana"], ["Albiol, l'"] ], "Lleida": [ ["Abella de la Conca"], ["Àger"], ["Agramunt"] ] }
现有省份下拉框代码(可正常工作)
<select name="activity_province" class="form-select" id="activity_province"> <option hidden selected></option> <script type="text/javascript"> $(document).on('ready',function (){ $.getJSON('/../public/utils/municipios.json', function(data) { $.each(data, function(key, value) { $("#activity_province").append('<option name="' + key + '">' + key + '</option>'); }); }); }); </script> </select> <label for="activity_province">Province</label>
现有城市下拉框代码(存在问题)
<select name="activity_city" class="form-select" id="activity_city"> <option hidden selected></option> <script type="text/javascript"> $(document).on('ready',function (){ $.getJSON('/../public/utils/municipios.json', function(data) { $.each(data, function(key, value) { $("#activity_city").append('<option name="' + value + '">' + value + '</option>'); }); }); }); </script> </select> <label for="activity_city">City</label>
解决方案
1. JSON结构优化
当前JSON中每个城市被包裹在单独的子数组中,增加了遍历复杂度,建议调整为一维数组直接存储城市名称,简化数据访问:
{ "Barcelona": ["Abrera", "Aguilar de Segarra", "Alella"], "Girona": ["Agullana", "Aiguaviva", "Albanyà"], "Tarragona": ["Aiguamúrcia", "Albinyana", "Albiol, l'"], "Lleida": ["Abella de la Conca", "Àger", "Agramunt"] }
若无法修改原JSON,后续代码中需通过city[0]提取城市名称,但优化后的结构更直观,能减少不必要的嵌套层级,提升数据处理效率。
2. 实现省份与城市联动的代码
核心逻辑:先加载并缓存JSON数据,监听省份下拉框的change事件,根据选中省份动态渲染对应城市选项。
完整代码示例:
<!-- 省份下拉框 --> <select name="activity_province" class="form-select" id="activity_province"> <option hidden selected>请选择省份</option> </select> <label for="activity_province">Province</label> <!-- 城市下拉框 --> <select name="activity_city" class="form-select" id="activity_city" disabled> <option hidden selected>请先选择省份</option> </select> <label for="activity_city">City</label> <script type="text/javascript"> $(document).ready(function() { // 缓存JSON数据,避免重复请求 let provinceData = null; // 加载JSON数据并渲染省份下拉框 $.getJSON('/../public/utils/municipios.json', function(data) { provinceData = data; // 渲染省份选项 $.each(data, function(province) { $("#activity_province").append(`<option value="${province}">${province}</option>`); }); }); // 监听省份选择变化事件 $("#activity_province").on('change', function() { const selectedProvince = $(this).val(); const citySelect = $("#activity_city"); // 清空城市下拉框并重置状态 citySelect.empty().append('<option hidden selected>请选择城市</option>'); if (selectedProvince && provinceData) { // 启用城市下拉框 citySelect.prop('disabled', false); // 获取对应省份的城市列表(若JSON未优化,需改为 provinceData[selectedProvince].map(item => item[0])) const cities = provinceData[selectedProvince]; // 渲染城市选项 $.each(cities, function(index, city) { // 若JSON未优化,替换为 city = city[0] citySelect.append(`<option value="${city}">${city}</option>`); }); } else { // 未选择省份时禁用城市下拉框 citySelect.prop('disabled', true); citySelect.append('<option hidden selected>请先选择省份</option>'); } }); }); </script>
代码说明:
- 缓存
provinceData,避免每次省份变化重复请求JSON; - 初始状态下城市下拉框设为
disabled,引导用户先选择省份; - 省份选择变化时,清空城市下拉框,根据选中省份渲染对应城市;
- 若无法修改原JSON结构,将城市列表获取逻辑改为
provinceData[selectedProvince].map(item => item[0]),或在遍历城市时通过city = city[0]提取名称。
内容的提问来源于stack exchange,提问作者Oscar
相关产品推荐
相关产品推荐

