22-ajax

ajax介绍和快速入门

1.Ajax概念

AJAX(Asynchronous JavaScript And XML):异步的 JavaScript 和 XML。AJAX 通过浏览器与服务器进行少量数据交换,就可以使网页实现异步更新。也就是在不重新加载整个页 面的情况下,对网页的部分内容进行局部更新

在这里插入图片描述

2.原生js实现ajax

后端代码实现

@WebServlet("/userServlet")
public class UserServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //设置编码
        req.setCharacterEncoding("utf-8");
        resp.setContentType("text/html;charset=utf-8");
        //获取请求参数
        String username = req.getParameter("username");
        //判断
        if ("zhangsan".equals(username)){
            resp.getWriter().write("<font color='red'>该用户已经注册</font>");
        }else {
            resp.getWriter().write("<font color='blue'>用户可用</font>");
        }
    }
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        doGet(req, resp);
    }
}

前端代码实现

<body>
    <form autocomplete="off">
        姓名:<input type="text" id="username">
        <span id="uSpan"></span>
        <br>
        密码:<input type="password" id="password">
        <br>
        <input type="submit" value="注册">
    </form>
</body>
<script>
    //1.为姓名绑定失去焦点的事件
    document.getElementById("username").onblur = function () {
        //2.创建XMLHttpRequest核心对象
        let xmlHttp = new XMLHttpRequest();
        //3.打开链接
        let username = document.getElementById("username").value;
        xmlHttp.open("GET","userServlet?username="+username,true);
        //4.发送请求
        xmlHttp.send();
        //5.处理响应
        xmlHttp.onreadystatechange = function () {
            //判断请求和响应是否成功
            if (xmlHttp.readyState == 4 && xmlHttp.status == 200){
                //将响应的数据显示到span标签
                document.getElementById("uSpan").innerHTML = xmlHttp.responseText;
            }
        }

    }
</script>

原生js实现ajax步骤详解

-1 为姓名绑定失去焦点事件
    
-2 创建XMLHttpRequest核心对象
    XMLHttpRequest:用户后台与服务器交换数据,可以在不重新加载整个网页的情况下,对网页的某部分进行更新
    
-3 打开链接open(method,url,async)
    method:请求的类型GET或者POST
    url:请求资源的路径
    async:true(异步)false(同步)    
    
-4 发送请求send(String params)
    params:请求的参数(POSt专用)
            
-5 处理响应onreadyStatechange
    readyState:0-请求未初始化,1-服务器连接已建立,3-请求处理中,4-请求已完成,且响应已就绪
    status:200-响应已全部OK    

3.jquery的通用方法实现ajax(重点)

3.1 $.ajax()语法
$.ajax({
	url:"",//请求路径
	async:,/异步请求,true-是,false-(默认true)
	data:"", //请求参数,写法1:“name=value&name=value...”,写法2:{name:value,name:value}
	type:"", //请求方式,常用的是get和post(默认get方式)
	dataType:"",  //响应的数据格式
	success:function(msg){  //响应成功要执行的函数,msg是响应回来的数据
			//处理msg数据
	},
	error:function(){
	
	}
});
3.2 演示-后台UserServlet代码
@WebServlet("/userServlet")
public class UserServlet extends HttpServlet {
    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //设置编码
        req.setCharacterEncoding("utf-8");
        resp.setContentType("text/html;charset=utf-8");
        //获取请求参数
        String username = req.getParameter("username");
        //判断
        if ("zhangsan".equals(username)){
            resp.getWriter().write("<font color='red'>该用户已经注册</font>");
        }else {
            resp.getWriter().write("<font color='blue'>用户可用</font>");
        }
    }
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        doGet(req, resp);
    }
}
3.3 演示-前端页面发送ajax请求
<script src="js/jquery-3.3.1.min.js"></script>
<body>
    <form action="#" autocomplete="off">
        姓名:<input type="text" id="username">
        <span id="uSpan"></span>
        <br>
        密码:<input type="password" id="password">
        <br>
        <input type="submit" value="注册">
    </form>
<script>
    //1.为用户绑定失去焦点事件
    $("#username").blur(function () {
        //获取表单填写的用户名
        let username = $("#username").val();
        //2.用jq的方式实现ajax
      $.ajax({
          //请求路径
          url:"userServlet",
          //是否异步
          async:true,
          //请求参数
          data:"username="+username,
          //请求方式
          type:"get",
          //数据形式
          dataType:"text",
          //请求成功后调用回调函数
          success:function (data) {
              //将响应的数据显示到span标签
              $("#uSpan").html(data);
          },
          error:function () {
              alert("操作有误");
          }
      });
    });
</script>
</body>    

4.jquery的get方法实现ajax

4.1 $.get()语法
语法:$.get(url, [data], [callback], [type])

参数:
    url:请求路径
	data:请求参数,写法1:“name=value&name=value...”,写法2{name:value,name:value}。
	callback:响应成功要执行的函数。
	type:响应的数据格式,xml, html, script, json, text, _default。
4.2 演示
<script>
    //1.为用户绑定失去焦点事件
    $("username").blur(function () {
        //获取表单填写的用户名
        let username = $("#username").val();
        //2.用jq的get方式实现ajax
        $.get(
            //请求的资源路径
            "userServlet",
            //请求的参数
            "username="+username,
            //回调函数
            function (data) {
                //将响应的数据显示到span标签
                $("uSpan").html(data);
            },
            //响应数据形式
            "text"
        );
    })
</script>

5.jquery的post方法实现ajax

5.1 $.post()语法
语法:$.get(url, [data], [callback], [type])

参数:
    url:请求路径
	data:请求参数,写法1:“name=value&name=value...”,写法2{name:value,name:value}。
	callback:响应成功要执行的函数。
	type:响应的数据格式,xml, html, script, json, text, _default。
5.2 演示
<script>
    //1.为用户绑定失去焦点事件
    $("#username").blur(function () {
        //获取表单填写的用户名
        let username = $("#username").val();
        //2.用jq的方式实现ajax
       $.post(
           //请求的资源路径
           "userServlet",
           //请求的参数
           "username=" + username,
           //回调函数
           function (data) {
               //将响应的数据显示到span标签
               $("#uSpan").html(data);
           },
           //响应数据形式
           "text"
       );
    });
</script>

json处理(重点)

1 json回顾介绍

  • json是一种前后端数据交换的格式,这种格式的数据传输快,解析方便,所以被广泛使用。

  • json格式分类

在这里插入图片描述

格式1:对象格式
	{name:value,name:value,...} //value可以是任意数据类型,如果value是对象,那么就是对象嵌套对象
格式2:数组格式
	[ele1,ele2,...] // ele1,ele2 可以是任意数据类型
格式3:混合类型,指的是对象嵌套数组,数组嵌套对象
	{name:value,name:[],...}[{name:value,name:value,..},{},{},...]
  • 常用方法
成员方法说明
stringify(对象)将指定对象转换为json格式的字符串
parse(字符串)将指定json格式字符串解析成对象

2 json转换工具介绍

2.1 JSON转换工具
  • 可以将java对象或者集合转换成json格式的字符串,也可以将json格式的字符串转换成java对象

  • Jackson:开源的JSON转换工具,SpringMVC转换默认使用Jackson

    • 导入jar包
    • 创建核心对象
    • 调用方法完成转换
2.2 jackson的相关API介绍

作用:可以将Java对象转换成json字符串,也可以将json字符串解析成Java对象,我们的重心“将Java对象转换成json字符串”

  • jackson涉及到的类

在这里插入图片描述

  • ObectMapper类涉及到的方法

在这里插入图片描述

  • 补充方法
- 自定义的对象,json转java对象,需要new TypeReference<>(){}
    new TypeReference<List<User>>() {}
           TypeReference是一个抽象类,没有子类,不能直接new对象,可以使用匿名内部类创建对象。
           TypeReference的泛型List<User>表示告诉jackson要将json转换的数据类型是List<User>
               
- 不是自定义的对象,写他的字节码对象
  List list1 = mapper.readValue(json, List.class); 

3 json转换练习

  • jackson使用步骤
【第一步】:导入jackson相关jar包,有三个
【第二步】:创建ObjectMapper核心对象
【第三步】:调用ObjectMapper的方法进行转换
		Java对象----->json字符串:调用writerValueAsString()或者WriterValue()
		json字符串----->Java对象:调用readValue();
  • 代码演示
public class ObjectMapperTest {
    //创建ObjectMapper核心对象
    private ObjectMapper mapper = new ObjectMapper();
    /*
        1.User对象转json, json转User对象
          json字符串 = {"name":"张三","age":23}
          user对象 = User{name='张三', age=23}
     */
    @Test
    public void test01() throws Exception{
        //User对象转json
        User u1 = new User("张三", 23);
        String json = mapper.writeValueAsString(u1);
        System.out.println("json字符串:"+json);
        //json转User对象
        User u2 = mapper.readValue(json, User.class);
        System.out.println("java对象:"+u2);
    }
     /*
         2.map<String,String>转json, json转map<String,String>
          json字符串 = {"姓名":"张三","性别":"男"}
          map对象 = {姓名=张三, 性别=男}
     */
     @Test
     public void test02() throws Exception{
         //map<String,String>转json
         HashMap<String, String> hashMap = new HashMap<>();
         hashMap.put("姓名","张三");
         hashMap.put("性别","男");
         String json = mapper.writeValueAsString(hashMap);
         System.out.println("json字符串:"+json);
         //json转map<String,String>
         HashMap map = mapper.readValue(json, HashMap.class);
         System.out.println("java对象:"+map);
     }
    /*
      3.map<String,User>转json, json转map<String,User>
        json字符串 = {"黑马一班":{"name":"张三","age":23},"黑马二班":{"name":"李四","age":24}}
        map对象 = {黑马一班=User{name='张三', age=23}, 黑马二班=User{name='李四', age=24}}
   */
     @Test
    public void test03() throws Exception{
         //map<String,User>转json
         HashMap<String, User> hashMap = new HashMap<>();
         hashMap.put("黑马一班",new User("张三",23));
         hashMap.put("黑马二班",new User("李四",24));
         String json = mapper.writeValueAsString(hashMap);
         System.out.println("json字符串:"+json);
         //json转map<String,User>
         HashMap<String, User> map = mapper.readValue(json, new TypeReference<HashMap<String, User>>(){});
         System.out.println("java对象:"+map);
     }
    /*
        4.List<String>转json, json转 List<String>
          json字符串 = ["张三","李四"]
          list对象 = [张三, 李四]
     */
    @Test
    public void test04() throws Exception{
        //List<String>转json
        ArrayList<String> list = new ArrayList<>();
        list.add("张三");
        list.add("李四");
        String json = mapper.writeValueAsString(list);
        System.out.println("json字符串:"+json);
        //json转 List<String>
        List list1 = mapper.readValue(json, List.class);
        System.out.println("java对象:"+list1);
    }
    /*
        5.List<User>转json, json转List<User>
          json字符串 = [{"name":"张三","age":23},{"name":"李四","age":24}]
          list对象 = [User{name='张三', age=23}, User{name='李四', age=24}]
     */
    @Test
    public void test05() throws Exception{
        //List<User>转json
        ArrayList<User> list = new ArrayList<>();
        list.add(new User("张三",23));
        list.add(new User("李四",24));
        String json = mapper.writeValueAsString(list);
        System.out.println("json字符串:"+json);
        //json转List<User>

        ArrayList<User> list1 = mapper.readValue(json, new TypeReference<ArrayList<User>>() {});
        System.out.println("java对象:"+list1);
    }
}

注意

- 自定义的对象,json转java对象,需要new TypeReference<>(){}
    new TypeReference<List<User>>() {}
           TypeReference是一个抽象类,没有子类,不能直接new对象,可以使用匿名内部类创建对象。
           TypeReference的泛型List<User>表示告诉jackson要将json转换的数据类型是List<User>
               
- 不是自定义的对象,写他的字节码对象
  List list1 = mapper.readValue(json, List.class);             

综合案例-搜索提示(重要)

使用异步前后端 交互 流程

在这里插入图片描述

1 案例展示

在这里插入图片描述

2 功能分析

在这里插入图片描述

3 代码实现

3.1 后台代码实现
  • UserServlet代码
@WebServlet("/userServlet")
public class UserServlet extends HttpServlet {
    private UserService userService = new UserServiceImpl();
    //创建ObjectMapper核心对象
    private ObjectMapper mapper = new ObjectMapper();
    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        //设置请求和响应的编码
        req.setCharacterEncoding("UTF-8");
        resp.setContentType("text/html;charset=UTF-8");

        //1.获取请求参数
        String username = req.getParameter("username");

        //2.调用业务层的模糊查询方法得到数据
        List<User> users = userService.selectLike(username);

        //3.将数据转成json,响应到客户端
        String json = mapper.writeValueAsString(users);
        resp.getWriter().write(json);
    }

    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        doPost(req,resp);
    }
}
  • UserServiceImpl代码
public class UserServiceImpl implements UserService {
  @Override
  public List<User> findByUsername(String username) {
    SqlSession sqlSession = null;
    List<User> list = null;
    try {
      //1 加载资源
      InputStream is = Resources.getResourceAsStream("MyBatisConfig.xml");
      //2 获取SqlSessionFactory对象
      SqlSessionFactory factory = new SqlSessionFactoryBuilder().build(is);
      //3 获取Sqlsession对象
      sqlSession = factory.openSession(true);
      //4 获取代理对象,执行操作
      UserDao userDao = sqlSession.getMapper(UserDao.class);
      //"select * from user where name like #{username} order by search_count desc limit 0,4"
      //list = userDao.findByUsername("%"+username+"%");  //ok
      list = userDao.findByUsername(username);
    } catch (IOException e) {
      e.printStackTrace();
    } finally {
      //5 返回结果,释放资源
      if(sqlSession!=null){
        sqlSession.close();
      }
    }
    return list;
  }
}
  • UserDao代码
public interface UserDao {

  @Select("select * from user where name like concat('%',#{username},'%') order by search_count desc limit 0,4")
  public List<User> findByUsername(String username);
}
3.2 前台代码实现
<script>
    //1.为用户名输入框绑定鼠标点击事件
    $("#username").mousedown(function () {
        //2.获取输入的用户名数据
        let username = $("#username").val();
        //3.判断用户名是否为空
        if (username==null || username == ""){
            //4.如果为空,则将联想提示框隐藏
            $("#show").hide();
            return;
        }
        //5.如果不为空,则发送ajax请求,并将响应的数据显示到联想框
        $.ajax({
            //请求的资源路径
            url:"userServlet",
            //请求参数
            data:{username:username},
            //请求方式
            type:"POST",
            //响应的数据格式
            dataType:"json",
            //请求成功后的回调函数
            success:function (data) {
                //将放回的数据显示到show的div中
                let names = "";
                for (let i = 0; i < data.length; i++) {
                    names += "<div>"+data[i].name+"</div>";
                }
                $("#show").html(names).show();
            }
        });
    });
</script>

综合案例-分页查询-了解

1 效果展示

  • 分页效果1:下方有加载动画

在这里插入图片描述

  • 分析效果2:下方带有分页条

在这里插入图片描述

  • 案例分析

在这里插入图片描述

2 后台的分页知识点回顾【重点

【第一步】:导入开发jar包:jsqlparser-3.1.jar,pagehelper-5.1.10.jar
【第二步】:在mybatisConfig.xml核心配置文件中配置分页助手
	<!--集成分页助手插件-->
    <plugins>
        <plugin interceptor="com.github.pagehelper.PageInterceptor" />
    </plugins>
【第三步】:在执行查询所有之前设置开始查询的页数和每页查询的条数
		 //5.封装Page对象   start:当前页码   pageSize:每页显示的条数
     PageHelper.startPage(start,pageSize);
      //6.调用实现类对象的查询全部方法,此时底层执行的就是MySQL的limit分页查询语句
      List<News> list=mapper.selectAll();
【第四步】:在查询所有之后,封装分页信息
		//6.调用实现类对象的查询全部方法,此时底层执行的就是MySQL的limit分页查询语句
    List<News> list=mapper.selectAll();
    //7.封装分页数据
    info=new PageInfo<>(list);

3 滑动分页前端代码【了解】

//1.定义发送请求标记
let send = true;

//2.定义当前页码和每页显示的条数
let start = 1;
let pageSize = 10;

//3.定义滚动条距底部的距离
let bottom = 1;

//4.设置页面加载事件
$(function () {
	//5.为当前窗口绑定滚动条滚动事件
	$(window).scroll(function () {
		//6.获取必要信息,用于计算当前展示数据是否浏览完毕
		//当前窗口的高度
		let windowHeight = $(window).height();

		//滚动条从上到下滚动距离
		let scrollTop = $(window).scrollTop();

		//当前文档的高度
		let docHeight = $(document).height();

		//7.计算当前展示数据是否浏览完毕
		//当 滚动条距底部的距离 + 当前滚动条滚动的距离 + 当前窗口的高度 >= 当前文档的高度
		if((bottom + scrollTop + windowHeight) >= docHeight) {
			//8.判断请求标记是否为true
			if(send == true) {
				//9.将请求标记置为false,当前异步操作完成前,不能重新发起请求。
				send = false;
				//10.根据当前页和每页显示的条数来 请求查询分页数据
				queryByPage(start,pageSize);
				//11.当前页码+1
				start++;
			}
		}
	});
});

//定义查询分页数据的函数
function queryByPage(start,pageSize){
	//加载动图显示
	$(".loading").show();
	//发起AJAX请求
	$.ajax({
		//请求的资源路径
		url:"newsServlet",
		//请求的参数
		data:{"start":start,"pageSize":pageSize},
		//请求的方式
		type:"POST",
		//响应数据形式
		dataType:"json",
		//请求成功后的回调函数
		success:function (data) {
			if(data.length == 0) {
				$(".loading").hide();
				$("#no").html("我也是有底线的...");
				return;
			}
			//加载动图隐藏
			$(".loading").hide();
			//将数据显示
			let titles = "";
			for(let i = 0; i < data.length; i++) {
				titles += "<li>\n" +
					"                <div class=\"title-box\">\n" +
					"                    <a href=\"#\" class=\"link\">\n" +
												data[i].title +
					"                        <hr>\n" +
					"                    </a>\n" +
					"                </div>\n" +
					"            </li>";
			}

			//显示到页面
			$(".news_list").append(titles);
			//将请求标记设置为true
			send = true;
		}
	});
}

4 带分页条前端代码

//pageQuery方法分页查询
function pageQuery(currPage,pageSize){
  $.ajax({
    url:"newsServlet",
    data:{currentPage:currPage,pageSize:pageSize},
    type:"get",
    dataType:"json",
    success:function (info) { //info就是pageInfo
      //展示新闻条目(新闻数据)------------
      let lis=``;
      for (let news of info.list) {
        lis+=`<li>
                  <div class="title-box">
                      <a href="#" class="link">
                          ${news.title}
                          <hr>
                      </a>
                  </div>
            </li>`;
       }
      $(".news_list").html(lis);
      //展示分页条信息--------------------
      $(".pagination").pagination({
        css: 'css-5',
        pageSizeOpt: [
          {'value': 5, 'text': '5条/页', 'selected': true},
          {'value': 10, 'text': '10条/页'},
          {'value': 15, 'text': '15条/页'},
          {'value': 20, 'text': '20条/页'}
        ],
        showPageNum: 8,  //显示几个页码
        firstPage: '首页',
        previousPage: '上一页',
        nextPage: '下一页',
        lastPage: '尾页',
        skip: '跳至',
        confirm: '确认',
        refresh: '刷新',
        totalPageText: '共{}页',
        isShowFL: true,
        isShowPageSizeOpt: true,
        isShowSkip: true,
        isShowRefresh: true,
        isShowTotalPage: true,
        isResetPage: false,
        totalPage: info.pages,
        callBack: function (currPage, pageSize) {
          console.log('currPage:' + currPage + '     pageSize:' + pageSize);
          //调用pageQuery方法
          pageQuery(currPage,pageSize);
        }
      });
    }
  });
}
//当页面加载完成之后向服务器发送请求,获取第一页数据
$(function () {
  pageQuery(1,5);
})

page数据

[{"id":21,"title":"奥巴马罕见介入美国2020大选,警告民主党参选人须“基于现实”21"},{"id":22,"title":"奥巴马罕见介入美国2020大选,警告民主党参选人须“基于现实”22"},{"id":23,"title":"奥巴马罕见介入美国2020大选,警告民主党参选人须“基于现实”23"},{"id":24,"title":"奥巴马罕见介入美国2020大选,警告民主党参选人须“基于现实”24"},{"id":25,"title":"奥巴马罕见介入美国2020大选,警告民主党参选人须“基于现实”25"},{"id":26,"title":"奥巴马罕见介入美国2020大选,警告民主党参选人须“基于现实”26"},{"id":27,"title":"奥巴马罕见介入美国2020大选,警告民主党参选人须“基于现实”27"},{"id":28,"title":"奥巴马罕见介入美国2020大选,警告民主党参选人须“基于现实”28"},{"id":29,"title":"奥巴马罕见介入美国2020大选,警告民主党参选人须“基于现实”29"},{"id":30,"title":"奥巴马罕见介入美国2020大选,警告民主党参选人须“基于现实”30"}]

pageInfo数据

PageInfo{pageNum=4, pageSize=10, size=10, startRow=31, endRow=40, total=100, pages=10, list=Page{count=true, pageNum=4, pageSize=10, startRow=30, endRow=40, total=100, pages=10, reasonable=false, pageSizeZero=false}[com.itheima.bean.News@2ba8b0fe, com.itheima.bean.News@3f653868, com.itheima.bean.News@2632e0a6, com.itheima.bean.News@67a6bec4, com.itheima.bean.News@967cd8e, com.itheima.bean.News@1fd712b2, com.itheima.bean.News@2e51f63e, com.itheima.bean.News@7cd32dae, com.itheima.bean.News@4bef9407, com.itheima.bean.News@6c0a5d4a], prePage=3, nextPage=5, isFirstPage=false, isLastPage=false, hasPreviousPage=true, hasNextPage=true, navigatePages=8, navigateFirstPage=1, navigateLastPage=8, navigatepageNums=[1, 2, 3, 4, 5, 6, 7, 8]}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值