

统一声明:
1.本站联系方式QQ:709466365 TG:@UXWNET 官方TG频道:@UXW_NET 如果有其他人通过本站链接联系您导致被骗,本站一律不负责! 2.需要付费搭建请联系站长QQ:709466365 TG:@UXWNET 3.免实名域名注册购买- 游侠云域名 4.免实名国外服务器购买- 游侠网云服务
先把基础逻辑搞懂:Ajax三级联动到底是怎么回事?
其实三级联动的核心简单到像点奶茶——选奶茶(省份)→店员给你拿对应的配料(城市)→选配料再给你加对应的小料(区/县),全程不用等整个菜单重新做。放到网页里,就是选省份→用Ajax拿对应城市数据→填充城市下拉框;选城市→再用Ajax拿对应区/县数据→填充区/县下拉框。
你可能听过“异步请求”这个词,其实就是“你先忙你的,我做完了告诉你”。比如你发消息问朋友“吃了吗”,不用一直盯着手机等回复,该干嘛干嘛,他回复了你再看——这就是异步。Ajax就是干这个的:发请求给后端拿数据,不用刷新整个页面,数据来了再更新需要的下拉框,用户体验更流畅。
再说说数据格式——后端通常会返回JSON(JavaScript Object Notation),它像带标签的储物盒,每个数据都有明确的“名字”。比如省份数据可能长这样:
[{"id":1,"name":"广东省"},{"id":2,"name":"广西壮族自治区"},{"id":3,"name":"湖南省"}]
你拿到后,直接用name
显示省份名称,用id
作为后续请求的“钥匙”——比如选了广东省(id=1),就发请求要city_1.json
(对应广东省的城市数据),逻辑就顺起来了。
我之前踩过一个坑:朋友给我的数据是XML格式,我费了半天劲解析,后来换成JSON才发现——哦,原来JSON能直接用JavaScript读,不用写复杂的解析代码。所以如果后端问你要什么格式,优先选JSON,新手友好度拉满。
超详细步骤:从0到1实现三级联动(附源码)
接下来直接上硬货——分5步走,每一步都能跟着操作,最后附可运行的源码。
你需要三个标签(下拉框),分别对应省、市、区。结构不用复杂,id一定要写对(后面要靠id找元素):
我 给外层加个类名(比如linkage-box
),方便后续加样式——比如让三个下拉框排成一行,加个 margin,看起来更整齐。
如果后端还没给接口,先自己写JSON文件模拟数据(避免后端问题干扰)。比如:
province.json
:全国省份数据(id+name);city_1.json
:广东省的城市数据(id+name,对应省份id=1);district_11.json
:广州市的区/县数据(id+name,对应城市id=11)。 我把模拟数据的结构整理成了表格,你可以直接抄:
文件名 | 对应数据 | 示例内容 |
---|---|---|
province.json | 全国省份 | [{“id”:1,”name”:”广东省”},{“id”:2,”name”:”广西壮族自治区”}] |
city_1.json | 广东省的城市 | [{“id”:11,”name”:”广州市”},{“id”:12,”name”:”深圳市”}] |
district_11.json | 广州市的区/县 | [{“id”:111,”name”:”天河区”},{“id”:112,”name”:”越秀区”}] |
你可以把这些文件存在同一个文件夹里,后续直接用相对路径请求(比如./province.json
)。
因为要发三次请求(省份→城市→区/县),我 把Ajax封装成一个函数——写一次,用三次,减少重复劳动。函数逻辑很简单:
XMLHttpRequest
对象(Ajax的“信使”);GET
和url);代码长这样(不用怕,复制就能用):
function getAjaxData(url, callback) {
//
新建“信使”
var xhr = new XMLHttpRequest();
//
打开请求:方法是GET,url是要请求的文件/接口地址,第三个参数true表示“异步”
xhr.open('GET', url, true);
//
监听状态:当请求完成且成功时,调用callback函数
xhr.onreadystatechange = function() {
// readyState=4表示请求完成,status=200表示成功
if (xhr.readyState === 4 && xhr.status === 200) {
// 把JSON字符串转成JavaScript对象
var data = JSON.parse(xhr.responseText);
// 调用callback,把数据传进去
callback(data);
}
};
//
发送请求
xhr.send();
}
解释一下:url
是你要请求的文件(比如./province.json
),callback
是“拿到数据后要做的事”——比如填充省份下拉框。
用上面的函数请求province.json
,填充省份下拉框。代码:
// 页面加载完成后执行
window.onload = function() {
var provinceSelect = document.getElementById('province');
var citySelect = document.getElementById('city');
var districtSelect = document.getElementById('district');
//
填充省份下拉框
getAjaxData('./province.json', function(provinceData) {
// 先加一个默认选项:“请选择省份”
var defaultOption = document.createElement('option');
defaultOption.value = '';
defaultOption.textContent = '请选择省份';
provinceSelect.appendChild(defaultOption);
// 遍历省份数据,添加选项
provinceData.forEach(function(province) {
var option = document.createElement('option');
option.value = province.id; // 选项的值是省份id
option.textContent = province.name; // 选项的显示文字是省份名称
provinceSelect.appendChild(option);
});
});
};
我之前犯过一个错:没加默认选项,用户打开页面直接看到一堆省份,不知道选哪个——后来加了“请选择省份”,朋友说“这样才像话”。
现在省份有了,接下来要让“选省份→填充城市”“选城市→填充区/县”生效,核心是给下拉框绑change
事件(当选项改变时触发)。
(1)省份改变→填充城市
给provinceSelect
绑change
事件:
// 省份改变时,填充城市
provinceSelect.addEventListener('change', function() {
var provinceId = this.value; // 拿到选中的省份id
if (provinceId === '') {
// 如果选了“请选择省份”,清空城市和区
citySelect.innerHTML = '请选择城市';
districtSelect.innerHTML = '请选择区/县';
return;
}
// 发请求拿城市数据:url是./city_${provinceId}.json
(比如city_1.json)
getAjaxData('./city_' + provinceId + '.json', function(cityData) {
// 先清空城市下拉框的旧数据
citySelect.innerHTML = '请选择城市';
// 填充新城市数据
cityData.forEach(function(city) {
var option = document.createElement('option');
option.value = city.id;
option.textContent = city.name;
citySelect.appendChild(option);
});
// 清空区/县下拉框(换省份了,旧区数据没用了)
districtSelect.innerHTML = '请选择区/县';
});
});
(2)城市改变→填充区/县
同理,给citySelect
绑change
事件:
// 城市改变时,填充区/县
citySelect.addEventListener('change', function() {
var cityId = this.value;
if (cityId === '') {
districtSelect.innerHTML = '请选择区/县';
return;
}
// 发请求拿区数据:url是./district_${cityId}.json
(比如district_11.json)
getAjaxData('./district_' + cityId + '.json', function(districtData) {
districtSelect.innerHTML = '请选择区/县';
districtData.forEach(function(district) {
var option = document.createElement('option');
option.value = district.id;
option.textContent = district.name;
districtSelect.appendChild(option);
});
});
});
我帮朋友做的时候,踩过的坑能写满一张纸,整理了最常见的3个,你可以对照着避坑:
问题 | 原因 | 解决办法 |
---|---|---|
选省份后城市没反应 | 请求url错了(比如city_1.json 写成city1.json ) |
打开浏览器控制台(F12→Network),看请求的url是不是正确,status是不是200 |
城市下拉框有重复数据 | 填充前没清空旧选项 | 每次填充前加citySelect.innerHTML = '请选择城市'
|
换省份后区还是旧数据 | 没清空区下拉框 | 选省份时,不仅要清空城市,还要清空区:districtSelect.innerHTML = '...'
|
到这里,功能已经实现了,但可以加几个小细节,让体验更流畅:
javascript
citySelect.innerHTML = ‘加载中…’;
css
select:disabled {
background-color: #f2f2f2;
color: #999;
}
然后在填充省份前,禁用城市和区:
javascript
citySelect.disabled = true;
districtSelect.disabled = true;
选了省份后,启用城市:
javascript
citySelect.disabled = false;
最后:给你现成的源码,直接运行
我把完整的代码放在GitHub上(链接,加nofollow),你可以下载下来直接运行——里面包含:
:页面结构;
:所有JS代码;
文件夹:
province.json、
city_1.json、
district_11.json模拟数据;
:简单样式。
下载后,用浏览器打开index.html,就能看到效果:选省份→城市跟着变→区跟着变,全程不用刷新页面。
我当初帮朋友做的时候,花了3天踩坑,后来整理成这套步骤,朋友用了1小时就搞定了。你如果按这些方法试了,不管成功还是遇到问题,欢迎回来告诉我——比如“我加了加载状态,用户说比之前好用多了”或者“请求url总是错,怎么办?”,我会帮你看看。
最后提醒一句:如果后端给的是接口(比如https://your-api.com/getProvince),只需要把
getAjaxData的
url换成接口地址就行,逻辑是一样的。
试试吧,你会发现——原来Ajax三级联动,没想象中那么难。
本文常见问题(FAQ)
Ajax实现城市三级联动的核心逻辑是什么?
其实核心像点奶茶:选奶茶(省份)→店员拿对应配料(城市)→选配料再加对应小料(区/县),全程不用等整个菜单重做。放到网页里就是,选省份后用Ajax拿对应城市数据填充城市下拉框;选城市后再用Ajax拿对应区/县数据填充区/县下拉框,全程不用刷新页面,用户体验更流畅。
这里的关键是“异步请求”,就像发消息问朋友“吃了吗”,不用一直盯着手机等回复,他回复了你再看——Ajax就是发请求拿数据,数据来了再更新下拉框,不影响用户做其他操作。
为什么后端返回数据 用JSON格式?
因为JSON(JavaScript Object Notation)像带标签的储物盒,每个数据都有明确“名字”,比如省份数据可能是[{“id”:1,”name”:”广东省”}…],拿到后能直接用JavaScript读,不用写复杂的解析代码。
我之前踩过坑,朋友给的是XML格式,费了半天劲解析,换成JSON才发现效率高很多——新手不用学额外的解析知识,直接用JSON数据填充下拉框就行,友好度拉满。
选省份后城市下拉框没反应该查什么?
先打开浏览器控制台(按F12选Network),看请求的url对不对。比如选广东省(id=1),应该请求city_1.json,如果写成city1.json(少了下划线),就会找不到文件。
再看status码是不是200——200表示请求成功,要是404就是url错了,500是后端接口有问题。比如之前我把city_1.json存错文件夹,url写成./data/city_1.json才对,改完就有反应了。
换省份后区下拉框还是旧数据怎么处理?
问题出在“没清空区的旧数据”。选省份时,不仅要清空城市下拉框,还要同步清空区的。比如在省份change事件里,加一句districtSelect.innerHTML = ‘请选择区/县’,这样换省份后区就会变回默认提示,不会留旧数据。
我之前帮朋友做的时候也遇到过这问题,选了广东省再换湖南省,区还是广州市的天河区,后来加了清空区的代码,就正常了。
模拟数据的JSON文件怎么准备?
模拟数据要分三个文件:省份文件叫province.json,内容是[{“id”:1,”name”:”广东省”},{“id”:2,”name”:”广西壮族自治区”}…];城市文件对应city_省份id.json,比如广东省id=1,城市文件就是city_1.json,内容是[{“id”:11,”name”:”广州市”},{“id”:12,”name”:”深圳市”}…];区文件对应district_城市id.json,比如广州市id=11,区文件就是district_11.json,内容是[{“id”:111,”name”:”天河区”},{“id”:112,”name”:”越秀区”}…]。
把这些文件存在同一个文件夹里,比如叫data,请求时用./data/province.json这样的相对路径就行,新手直接复制这个结构,就能快速调试功能。
2. 分享目的仅供大家学习和交流,您必须在下载后24小时内删除!
3. 不得使用于非法商业用途,不得违反国家法律。否则后果自负!
4. 本站提供的源码、模板、插件等等其他资源,都不包含技术服务请大家谅解!
5. 如有链接无法下载、失效或广告,请联系管理员处理!
6. 本站资源售价只是赞助,收取费用仅维持本站的日常运营所需!
7. 如遇到加密压缩包,请使用WINRAR解压,如遇到无法解压的请联系管理员!
8. 精力有限,不少源码未能详细测试(解密),不能分辨部分源码是病毒还是误报,所以没有进行任何修改,大家使用前请进行甄别!
站长QQ:709466365 站长邮箱:709466365@qq.com