Ajax学习案例——使用JSONP实现腾讯天气
注:本次案例实现较为简单,这里捋一下大致思路:
- 到腾讯天气网站,按F12切换到Network,找到common开头的一次请求,点击查看需要传递的参数,见下图
source:代表以何种方式访问 填 PC / WX
weather_type:代表天气 forecast_1h 表示未来48小时 forecast_24h 表示未来7天
province:表示省份
city:表示城市 - 调用封装好的jsonp函数,填入相关信息,此时就可以得到服务器端返回的相关内容
- 用模板引擎(这里使用的是art-template)拼接到页面上即可
个人比较容易出错的有几个地方就是:
template.defaults.imports.dataFormat = dataFormat;
在格式化时间的时候,要在模板中使用自定义的函数,此时要将函数名暴露出来,不能直接调用函数;- . 后面不能跟变量,变量应该放到 [ ] 中
代码如下:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.4.1/css/bootstrap.min.css"
integrity="sha384-Vkoo8x4CGsO3+Hhxv8T/Q5PaXtkKtu6ug5TOeNV6gBiFeWPGFN9MuhOf23Q9Ifjh" crossorigin="anonymous">
<title>Document</title>
</head>
<body>
<div class="container">
<table class="table table-striped table-hover" align="center" id="box">
</table>
</div>
<script src="./JSONP封装完成函数.js"></script>
<script src="./template-web.js"></script>
<!-- 模板 -->
<script type="text/html" id="tpl">
<tr>
<th>时间</th>
<th>温度</th>
<th>天气</th>
<th>风向</th>
<th>风力</th>
</tr>
{{each data}}
<tr>
<td>{{dataFormat($value.update_time)}}</td>
<td>{{$value.degree}}</td>
<td>{{$value.weather}}</td>
<td>{{$value.wind_direction}}</td>
<td>{{$value.wind_power}}</td>
</tr>
{{/each}}
</script>
<script>
// 获取box标签 用来显示模板数据的地方s
var box = document.getElementById('box');
// node的语法规则 将dataFormat暴露出来使模板中的数据可以调用此方法
// 第一个dataFormat表示追加的属性,模板中可以使用的属性
// 第二个dataFormat表示函数名,调用此函数方法
template.defaults.imports.dataFormat = dataFormat;
// 将返回的时间数据进行格式化
function dataFormat(data){
var year = data.substr(0,4);
var month = data.substr(4,2);
var day = data.substr(6,2);
var hour = data.substr(8,2);
var min = data.substr(10,2);
var sec = data.substr(12,2);
return year + '年' + month + '月' + day + '日' + ' ' + hour + ':' + min + ':' + sec;
}
//调用jsonp方法
jsonp({
url:'https://wis.qq.com/weather/common',
data:{
source:'pc',
weather_type:'forecast_1h',
province: '浙江省',
city: '丽水市'
},
success:function(data){
// 将模板与数据进行拼接
var html = template('tpl',{data:data.data.forecast_1h});
// 将拼接好的html显示在页面上
box.innerHTML = html;
}
});
</script>
</body>
</html>
JSONP封装的js文件如下:
function jsonp(options) {
//动态添加script标签 使发送请求这一动作变得可控,否则页面一上来就会被加载
var script = document.createElement('script');
//拼接字符串的变量
var params = '';
//遍历拿到数据
for (attr in options.data) {
params += '&' + attr + '=' + options.data[attr];
}
//函数名随机 否则如果有两个按钮同时点击响应同一个函数的话,后面函数返回结果会覆盖前面函数的返回结果
var attrName = 'script' + Math.random().toString().replace('.', '');
//它已经不是一个全局函数了
///我们要想办法让它重新变为全局函数 .后面不能是个变量哦!
window[attrName] = options.success;
//设置script标签的src属性
script.src = options.url + '?callback=' + attrName + params;
//动态添加script标签
document.body.appendChild(script);
//为script标签添加onload事件 此事件是页面全部加载完毕后才触发
script.onload = function () {
//页面加载完毕后移除script标签,因为执行完毕后此标签已没有意义
document.body.removeChild(script);
}
}