JavaWeb学习笔记(6)-B站尚硅谷

十六、书城项目第五阶段——分页

001-图书分页

A. 分页模块的分析

在这里插入图片描述

希望对上面的后台图书管理进行分页显示,就像是首页index.jsp一样
	分页要达到的效果:每页显示四条数据 和 分页条
	即如下效果:

在这里插入图片描述

首页的样子如下:

在这里插入图片描述


在这里插入图片描述


在这里插入图片描述

客户端进行传递就是下面这样:百度分页数量设置:

在这里插入图片描述

B. 分页模型 Page 的抽取(当前页数,总页数,总记录数,当前页数据,每页记录数)

在bean package中 创建Page类:
package com.atguigu.bean;

import java.util.List;

/**
 * Page 是分页的模型类(对象)
 * @param <T> 如果用户模块需要分页,那就是每页就是用户数据;如果是图书模块需要分页,那么每页就是图书数据。所以使用泛型。
 */
public class Page<T> {
    
    

    //固定设定一页4条数据,设置为常量
    public static final Integer PAGE_SIZE = 4;

    // 当前页码
    private Integer pageNo;

    // 总页码
    private Integer pageTotal;

    // 当前页显示数量(一页显示的数据条数)
    private Integer pageSize = PAGE_SIZE;

    // 总记录数
    private Integer pageTotalCount;

    // 当前页数据(当前页的所有数据对象)
    private List<T> items;

	
	public Page() {
    
    
    }

    public Page(Integer pageNo, Integer pageTotal, Integer pageSize, Integer pageTotalCount, List<T> items) {
    
    
        this.pageNo = pageNo;
        this.pageTotal = pageTotal;
        this.pageSize = pageSize;
        this.pageTotalCount = pageTotalCount;
        this.items = items;
    }

    public Integer getPageNo() {
    
    
        return pageNo;
    }

    public void setPageNo(Integer pageNo) {
    
    
        this.pageNo = pageNo;
    }

    public Integer getPageTotal() {
    
    
        return pageTotal;
    }

    public void setPageTotal(Integer pageTotal) {
    
    
        this.pageTotal = pageTotal;
    }

    public Integer getPageSize() {
    
    
        return pageSize;
    }

    public void setPageSize(Integer pageSize) {
    
    
        this.pageSize = pageSize;
    }

    public Integer getPageTotalCount() {
    
    
        return pageTotalCount;
    }

    public void setPageTotalCount(Integer pageTotalCount) {
    
    
        this.pageTotalCount = pageTotalCount;
    }

    public List<T> getItems() {
    
    
        return items;
    }

    public void setItems(List<T> items) {
    
    
        this.items = items;
    }

    @Override
    public String toString() {
    
    
        return "Page{" +
                "pageNo=" + pageNo +
                ", pageTotal=" + pageTotal +
                ", pageSize=" + pageSize +
                ", pageTotalCount=" + pageTotalCount +
                ", items=" + items +
                '}';
    }
}

C. 分页的初步实现

BookServlet中添加page()方法:
在这里插入图片描述


点击“图书管理”,就要实现上面的分页效果:
所以要将 表示“图书管理”的 a标签 的 action=list 改为action=page
即修改manager_menu.jsp:

在这里插入图片描述


修改book_manager.jsp:
将requestScope.books改为 —> requestScope.page.items
以前遍历 books ,现在遍历 page.items

在这里插入图片描述


BookService中添加page()方法:
在这里插入图片描述


BookServiceImpl中实现page()方法:

@Override
    //处理分页(给每一个Page对象设置它的五个属性)
    public Page<Book> page(int pageNo, int pageSize) {
    
    

        //五个属性:pageNo, pageTotal, pageSize, pageTotalCount, items

        Page<Book> page = new Page<Book>();

        // 设置当前页码
        page.setPageNo(pageNo);

        // 设置每页显示的数量
        page.setPageSize(pageSize);


        // 求总记录数
        Integer pageTotalCount = bookDao.queryForPageTotalCount();

        // 设置总记录数
        page.setPageTotalCount(pageTotalCount);


        // 求总页码
        Integer pageTotal = pageTotalCount / pageSize;
        if (pageTotalCount % pageSize > 0) {
    
    
            pageTotal+=1;
        }

        // 设置总页码
        page.setPageTotal(pageTotal);


        // 求当前页数据的开始索引
        int begin = (page.getPageNo() - 1) * pageSize;

        // 求当前页数据
        List<Book> items = bookDao.queryForPageItems(begin,pageSize);

        // 设置当前页数据
        page.setItems(items);

        return page;
    }

BookDao中添加两个方法:
queryForPageTotalCount()
queryForPageItems(int begin, int pageSize)

在这里插入图片描述


BookDaoImpl中实现上面的两个方法:
在这里插入图片描述


测试BookDaoImpl中的
queryForPageTotalCount()和queryForPageItems(int begin, int pageSize)方法:
在BookDaoImplTest中写如下代码:

在这里插入图片描述


测试BookServiceImpl中的page()方法:
在BookServiceImplTest中写如下代码:

在这里插入图片描述


测试BookServlet中的page()方法:
在这里插入图片描述

在以上页面点击图书管理后,出现分页效果,如下图:

在这里插入图片描述
上面这个页面还缺少分页条(与主页面index.jsp中的相同),在book_manager.jsp中做如下添加:
在这里插入图片描述
在这里插入图片描述
将当前页码,总页数,总记录条数实现一下:
在这里插入图片描述
在这里插入图片描述

D. 首页、上一页、下一页、末页实现

首页:pageNo = 1
上一页:pageNo - 1
下一页:pageNo + 1
末页:pageNo = pageTotal

在book_manager.jsp中做如下修改:
在这里插入图片描述


注意:程序运行之后,点击上一页,下一页,首页,末页,控制台会出现NumberFormatException异常,但并不影响程序运行。

出现NumberFormatException异常原因:
	点击图书管理之后,最开始并没有page对象
	所以BookServlet中的page()方法的
		req.getParameter("pageNo")
		req.getParameter("pageSize")
		都获取不到参数,所以导致WebUtils.parseInt()方法的第一个参数为空
		只能取默认值
	
	点击上一页,下一页,首页,末页还是会出现这个异常是因为:
		req.getParameter("pageSize")一直获取不到,只能取默认值
	
如果不想控制台出现这个异常,可以将WebUtils的parseInt()方法改写如下(也可以不改):
	if (strInt == null){
		return defaultValue;
	}else {
		return Integer.parseInt(strInt);
	}

也可以把原来的方法中的 e.printStackTrace();注释掉

E. 分页模块中跳转到指定页数功能实现

在这里插入图片描述

实现如上图功能
给确定按钮绑上单击事件:

在这里插入图片描述


上面写的还有些问题:
	首先 location.href 中 不能使用localhost,访问的是你自己的电脑
	要改为动态的:
	在head.jsp中 加入一行代码:

在这里插入图片描述

修改 location.href :

在这里插入图片描述


第二个问题:输入的页数可能小于1,也可能大于最大页数
	先对前台的代码进行修改
	修改book_manager.jsp:

在这里插入图片描述

还要提供服务器的校验:
	因为懂行的人会在地址栏直接修改,越过前台校验。
	在BookServiceImpl的page方法中添加校验:
	因为很多功能都会用到这个校验,所以将这个校验放在Page类的setPageNo方法里:

在这里插入图片描述
注意:在BookServiceImpl中,要将page.setPageNo()方法放在page.setPageTotal()方法之后,否则会出现pageTotal为空的情况。
在这里插入图片描述

如果在输入框中输入小数,会一直跳转到第一页:
因为WebUtils的parseInt()方法中的
Integer.parseInt(参数1,参数2)方法是将字符串转换为int类型
将字符串参数1转换为十进制int类型,而参数2表示字符串参数1原本是几进制
输入小数字符串,会显示NumberFormatException,那么就会取默认值1。

F. 分页模块中,页码 1,2,【3】,4,5 的显示,要显示 5 个页码,并且页码可以点击跳转。

在这里插入图片描述

为了与上面的情况相符,t_book中只保留20条数据。
为了出现总页码数大于5的情况,每页只显示2条数据——>修改page类的PAGE_SIZE = 2;

在这里插入图片描述

修改book_manager.jsp:

在这里插入图片描述
在这里插入图片描述

G. 修改分页后,增加,删除,修改图书信息的回显页面

使用分页之后,添加图书,修改图书,删除图书都出现了一些问题,进行修改。
	
点击添加图书,提交之后,显示空白,因为此时 action=list 不是分页
所以将BookServlet中 action=list 改为 action=page

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述


点击添加图书,点击提交之后,回到图书列表页面,但是不在最后一页(看不到添加的结果)
实现 点击提交之后,直接到最后一页:

修改book_manager.jsp:

在这里插入图片描述

修改book_edit.jsp:

在这里插入图片描述

修改BookServlet的add方法:
	考虑到每页显示两条记录,如果共10页,再添加一条记录就到了11页的情况:
		让pageNo + 1

		假设总页数为10页,第10页只有一条数据,那么增加一条数据之后
			总页数还是10,但是BookServlet的pageNo为11,
			此时pageNo > pageTotal ---> pageNo = pageTotal
			所以虽然地址栏中pageNo=11 但是显示的是第10页
			(地址栏pageNo=11这个问题我不知道怎么解决,
			但是重新运行之后看这些页面就没有这个问题了,老师没有这个问题)
		
			再添加一条数据之后 pageNo == pageTotal 显示第11页

在这里插入图片描述


删除图书:

在这里插入图片描述
在这里插入图片描述


修改图书:

在这里插入图片描述
在这里插入图片描述

002-实现首页index.jsp的分页

实现首页index.jsp的分页
在这里插入图片描述

通过地址 http://ip:port/工程路径/ 或者 http://ip:port/工程路径/index.jsp 
	访问主页面index.jsp
	要对index.jsp实现分页,index.jsp无法处理分页,所以要创建ClientBookServlet
	这样就是要访问ClientBookServlet
	但是无法显示地访问ClientBookServlet,一定要通过访问index.jsp的地址实现分页
	怎么做?
		在web下的pages目录创建一个client目录,
		在client目录下创建一个和index.jsp一样的jsp。

在src的web package下创建 ClientBookServlet:

在ClientBookServlet中需要实现 page()分页方法,可以直接将BookServlet的page()方法复制过去。
再进行相应的修改。

在这里插入图片描述
在这里插入图片描述


在这里插入图片描述

上面这个index.jsp只负责请求转发:

在这里插入图片描述

这样就实现了
从 主页面index.jsp 到 ClientBookServlet 再到 web下的pages下的client/index.jsp


对web下的pages下的client/index.jsp进行修改:
	遍历商品(图书)

在这里插入图片描述

运行之后,发现只有两个商品,将Page类的 PAGE_SIZE 改为4即可


实现分页条:

可以将book_manager.jsp的分页条复制粘贴 替换 
	web下的pages下的client/index.jsp的分页条

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

再对其中的请求地址进行修改:
	如何快速修改请求地址?
		使用搜索替换 ctrl + r

在这里插入图片描述

003-分页条的抽取

会发现 前台 和 后台 的分页条 的实现代码都是相同的,只是请求地址不同;
将分页条的代码抽取出来。

首先:在Page类中添加一个属性 url,作为分页条的请求地址

getXXX() setXXX()方法别忘了,toString()和构造方法都要重写一下。

在这里插入图片描述


然后:
使用 ${ requestScope.page.url } —>ctrl+r 替换—> 前后台的请求地址和?action=page

前台(web下的pages/client/index.jsp):

在这里插入图片描述

后台(book_manager.jsp):

在这里插入图片描述


然后:在前后台的Servlet的page方法中设置url

前台(ClientBookServlet):

在这里插入图片描述

后台(BookServlet):

在这里插入图片描述


这样做的好处:
1、修改分页条的请求地址更加方便(不同的模块直接修改page.setUrl()即可)
2、这样写之后,前后台 实现分页条的代码都是一样的,将代码提取出来。

提取分页条代码:
	在pages/common下创建page_nav.jsp
	将分页条的代码复制过去,
	然后client/index.jsp和book_manager.jsp相关分页条代码直接静态包含就可以了。

page_nav.jsp:
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

004-首页价格搜索

在这里插入图片描述

实现以上功能,并且分页显示。

在这里插入图片描述


表单的请求地址指向ClientBookServlet:

	并加上隐藏域,调用pageByPrice()方法
	修改pages/client/index.jsp:

在这里插入图片描述


在ClientBookServlet中实现pageByPrice()方法:
在这里插入图片描述


BookService中添加如下方法:
在这里插入图片描述


BookServiceImpl中实现pageByPrice()方法:
在这里插入图片描述


BookDao中添加如下方法:
在这里插入图片描述


BookDaoImpl中实现上面两个方法:
在这里插入图片描述


在BookDaoImplTest中测试:
queryForPageTotalCountByPrice()

queryForPageItemsByPrice()

在这里插入图片描述


在BookServiceImplTest中测试pageByPrice():
在这里插入图片描述


修改细节:
在这里插入图片描述

实现 点击上方查询之后 数字保留 不消失:
添加pages/client/index.jsp 中的两个value值:

在这里插入图片描述

但是点击下一页,数字还是会消失,并且分页条发生了变化。
解决方法:
在ClientBookServlet的pageByPrice()方法中的
	setUrl()中添加&min=...&max=...
	如下:

在这里插入图片描述

猜你喜欢

转载自blog.csdn.net/m0_52041525/article/details/124469248