json
json是JavaScript Object Notation 的首字母缩写,单词的意思是JavaScript对象表示法,这里说的json指的是类似于JavaScript对象的一种数据格式,目前这种数据格式比较流行,逐渐换掉了传统的xml数据模式。
- JavaScript自定义对象
//javascript自定义对象
var oMan = {
'name':'jack',
'age':18,
'talk':function(){
alert("I'm ok!");
}
}
- json数据格式
//json格式的数据
{
"name":"jack",
"age":18
}
注:与json数据对象不同的是,json数据格式的属性名称和字符串值需要用双引号引起来,用单引号或者不用引号会导致读取数据错误。
- json的另外一个数据格式是数组,和JavaScript中的数组子民啊量相同
["tom",18]
ajax
Ajax技术的目的是让JavaScript发生http请求,与后台通信,获取数据和信息。ajax技术的原理是实例化xmlhttp对象,使用此对象与后台通信。ajax通信的过程不会影响后续JavaScript的执行,从而实现异步。
异步和同步
现实生活中,同步指的是同时做几件事情,异步指的是做完一件事后再做另外一件事,程序中的同步和异步是把现实生活中的概念对调,也就是程序中的异步指的事现实生活中的同步,程序中的同步指的是现实生活中的异步。
局部刷新和无刷新
ajax可以实现局部刷新,也叫做无刷新,无刷新指的是整个网页不刷新,只是局部刷新,Ajax可以自己发送http请求,不通过浏览器的地址栏,所以整个页面整体不会刷新,ajax获取到后台数据,更新页面显示数据的部分,就做到了局部刷新。
同源策略
Ajax请求的页面或资源只能是同一个域下面的资源,不能是其他域的资源,这是在设计Ajax是基于安全的考虑。特征报错提示:
XMLHttpRequest cannot load http://xxxxxxNo 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'http://xxxxxxx' is therefore not allowed access.
jQuery里使用ajax
写法
- 以前的写法
$(function(){
// jQuery里使用ajax
$.ajax({
url:"/js/data.json",
type:'GET',
dataType:'json',
data:{'aa':1},
})
success:(function(dat){
console.log(dat);
})
error:(function(dat){
console.log('no!');
})
})
- 新的写法(推荐)
$(function(){
// jQuery里使用ajax
$.ajax({
url:"/js/data.json",
type:'GET',
dataType:'json',
data:{'aa':1},
})
//设置请求成功后的回调函数
.done(function(dat){
console.log(dat);
})
//设置请求失败后的回调函数和
.fail(function(dat){
console.log('no!');
})
})
$.ajax使用方法
- 常用参数
- url 请求的数据文件地址
- type 请求方式,默认是‘GET’,常用的还有’POST’
- datatype 设置返回的数据格式,常用的是’json‘格式,也可以设置为’html’
- data 设置发送给服务器的数据
- success 设置请求成功后的回调函数
- error 设置请求失败后的回调函数
- async 设置是否异步,默认值是‘true’,表示异步
遇到的头疼问题
这里用的是配置了的ajax服务器环境,网上可以搜到配置教程。打开了服务器之后,他会在服务器配置文件下查找index.html文件,然后服务器就链接到这个文件上。
在网上查找了很多办法都不管用,最后经过修改jQuery文件的路径得到了解决办法,有一下两种:
- 把放在根目录下或其他目录的jQuery文件,放在你执行的index.html文件的目录下,在输入服务器地址就可以了,我的index.html文件是放在了安装node.js服务器所产生的文件目录下。
- 不更改原来jQuery文件目录,在vscode里打开这个index.html文件
注:这两种方式地址的端口不一样,服务器的是3000,vscode打开的是5500,我觉得这可能就是导致错误的原因,原因是jQuery文件存放在5500端口下,在3000找不到。这是我个人认为的原因
如果有哪位大佬能看到这,麻烦看一下我这理解对不对,有问题还望提出修改。
jsonp
ajax只能请求同一个域下的资源或数据,有时候需要跨域请求数据,就需要用到jsonp技术,jsonp可以跨域请求数据,他的原理主要是利用script 标签可以跨域链接资源的特性。jsonp和ajax原理完全不一样,不过jQuery将他们封成同一个函数。
$(function(){
$.ajax({
url:'js/data.js',
type:"get",
dataType:'jsonp',
jsonpCallback:'fnBack'//传一个函数名给它,这个函数里面填写的是数据
})
.done(function(data){
console.log(data);
})
.fail(function(){
alert('请求服务超时!');
});
//data.js里面的数据:fnBack({"name":"mike","age":18});
})
练习
首页登录用户信息读取
html代码
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
<script type="text/javascript" src="/js/jquery-1.9.0.js"></script>
<script>
$(function(){
var $li_list = $('ul li .login');
$.ajax({
url:'/js/data.json',
type:'GET',
dataType:'json',
})
.done(function(data){
console.log(data);
//点击登录后登录位置变成欢迎信息
$li_list.click(function(){
//隐藏登录,显示欢迎信息,将读取的json数据放到欢迎信息里去
$li_list.hide().next().show().children().html(data.name);
})
})
.fail(function(){
alert('请求服务超时!');
})
})
</script>
<style>
header{
width: 100%;
height: 50px;
background-color: #eee;
text-align: right;
line-height: 50px;
}
ul{
list-style: none;
margin-right: 30px;
}
ul>li{
display: inline-block;
margin-right: 10px;
cursor: pointer;
}
ul>li em{
color: lightcoral;
}
ul>li .has_login{
display: none;
}
</style>
</head>
<body>
<header>
<ul>
<li>
<span class="login">登录</span>
<span class="has_login">欢迎您:<em></em></span>
</li>
<li>注册</li>
</ul>
</header>
</body>
</html>
效果演示
获取百度联想词
HTML代码
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document
</title>
<script type="text/javascript" src="/js/jquery-1.9.0.js"></script>
<script>
$(function(){
var result_list = null;
var sWord = null;
var $inp = $('.inp');
$ul = $('ul');
var i = 0;
//实时获取文本框的内容
$inp.keyup(function(){
sWord = $inp.val();
if(sWord != ""){
$.ajax({
//百度联想词api接口
url:"https://www.baidu.com/sugrec?prod=pc",
type:"get",
dataType:'jsonp',
data:{'wd':sWord}
})
.done(function(dat){
//关键一步,每请求一次就清除上一次请求的ul内容,实现内容实时更新
$ul.empty();
console.log(dat.g);
if(dat.g == undefined){
return;
}
var $len = dat.g.length;
//给显示联想词的ul添加li
for(i=0;i<$len;i++){
$ul.append('<li> <a>' + dat.g[i]['q'] + '</a></li>').show();
$('ul li a').css('cursor','pointer');
}
})
}
else{
//文本框内容为空清除ul内容
$ul.empty();
}
});
//文本框失去焦点,ul隐藏
$inp.blur(function(){
$ul.hide()
})
//文本框获得焦点,ul显示
$inp.focus(function(){
$ul.css('border-top','none').show();
})
});
</script>
<style>
body{
margin: 0;
}
input:focus{
outline: none;
outline-offset: 0;
border: 2px solid lightskyblue;
border-bottom-left-radius: 0;
border-bottom-right-radius:0 ;
}
.container{
margin: 0 auto;
text-align: center;
width: 500px;
height: 300px;
}
form{
margin: 200px auto;
margin-bottom: 0;
width: 500px;
height: 34px;
}
.inp{
width: 300px;
height: 34px;
text-indent: 1em;
box-sizing: border-box;
border: 1px solid #ccc;
border-radius: 3px;
}
input[type="button"]{
font-size: 20px;
vertical-align: middle;
border: 1px solid #aaa;
border-radius: 3px;
}
ul{
list-style: none;
margin-top: -2px;
width: 299px;
margin-left: 71px;
box-sizing: border-box;
border: 2px solid lightskyblue;
display: none;
padding-left: 1em ;
border-bottom-left-radius: 3px;
border-bottom-right-radius:3px ;
text-align: left;
}
</style>
</head>
<body>
<div class="container">
<form action="">
<input type="text" name="" class="inp" autocomplete="off">
<input type="button" value="搜索">
</form>
<ul></ul>
</div>
</body>
</html>
效果演示
总结
1. 跨域获取资源遇到了不少问题,具体问题,单拉出一篇文章,以便查阅
2. 实时获取文本框内容很重要,用到了keyup()
方法
3. 每个浏览器的搜索联想词获取的api不同,我是慢慢试出来的,实际可以上网上搜索
4. 每次一点文本框,输入内容后,ajax会请求两次,导致ul里的内容每次都重复一遍,因此我在请求成功的回调函数开头,放置一个$ul.empty();
来解决这个问题