Java Web实现分页功能
后端开发
-
JavaBean(该JavaBean对象是可复用的)
import java.util.List; /** 该Bean对象主要用来装载分页数据,为了更好的通用性,设计成了泛型类 */ public class PageBean<T> { private int thisPage; //当前页的页码 private int totalRecords; //总的记录数(通过从数据库中查询得到) private int everyPage; //每个页面显示的记录数(自己定义) private int previousPage; //上一页的页码 private int nextPage; //下一页的页码 private List<T> records; //查询到的实体类的集合 private int totalPage; //总的页数(只有get方法,没有set方法,通过计算得到) public int getThisPage() { return thisPage; } public void setThisPage(int thisPage) { this.thisPage = thisPage; } public int getTotalRecords() { return totalRecords; } public void setTotalRecords(int totalRecords) { this.totalRecords = totalRecords; } public int getEveryPage() { return everyPage; } public void setEveryPage(int everyPage) { this.everyPage = everyPage; } public int getPreviousPage() { return previousPage; } public void setPreviousPage(int previousPage) { this.previousPage = previousPage; } public int getNextPage() { return nextPage; } public void setNextPage(int nextPage) { this.nextPage = nextPage; } public List<T> getRecords() { return records; } public void setRecords(List<T> records) { this.records = records; } public int getTotalPage() { //总页数=总的记录数/每页显示的记录数,如果可以整除就直接返回,否则就加一后返回 totalPage=totalRecords/everyPage; return totalRecords%everyPage==0 ? totalPage:totalPage+1; } }
-
数据库操作(dbutils版本)
//总共需要两个参数,看情况而定,当前页数是必须要的 public PageBean<Book> findBookByCode(int pageCode, String cid) { int everyPage=3; //这里的cid是指图书种类,这句sql是指查询同一分类图书的总数量 String sql="select count(*) from book where cid= ? "; //这句sql是主要的业务逻辑,limit后面的两个数可以通过计算得到,第一个=(当前页码-1)*每页数量,第二个是每页的数量 String sql2="select book.*,cname from book,category where book.cid = ? and book.cid=category.cid limit ?,?"; try { Number number=qr.query(sql,new ScalarHandler<>(),cid); int totalPage=number.intValue(); PageBean<Book> pageBean=new PageBean<>(); pageBean.setEveryPage(3); pageBean.setNextPage(pageCode+1); pageBean.setPreviousPage(pageCode-1); pageBean.setTotalRecords(totalPage); pageBean.setThisPage(pageCode); List<Book> books = qr.query(sql2, new BeanListHandler<>(Book.class), cid, (pageCode - 1) * everyPage, everyPage); pageBean.setRecords(books); return pageBean; } catch (SQLException e) { throw new RuntimeException(e); } }
-
总结
-
关于JavaBean对象
JavaBean对象里有下列成员变量
private int thisPage; //当前页的页码 private int totalRecords; //总的记录数(通过从数据库中查询得到) private int everyPage; //每个页面显示的记录数(自己定义) private int previousPage; //上一页的页码 private int nextPage; //下一页的页码 private List<T> records; //查询到的实体类的集合 private int totalPage; //总的页数(只有get方法,没有set方法,通过计算得到)
其中,前端必须传递当前页,如果没有传递,后端需要设置默认值或者返回错误信息。而previousPage以及nextPage是根据thisPage计算得到的。everyPage是自己设置的。totalPage可以根据公式
totalPage = totalRecords / everyPage
计算得到。但是也要注意特殊情况,比如说总记录数是10,而每页计划显示3个,这时就要判断totalRecords % everyPage == 0
是否成立,如果不成立,那么totalPage要加一。//总页数=总的记录数/每页显示的记录数,如果可以整除就直接返回,否则就加一后返回 totalPage=totalRecords/everyPage; return totalRecords%everyPage==0 ? totalPage:totalPage+1;
totalPage需要从数据库中进行查找,一般使用聚合函数进行查找。
-
关于搜索
对搜索结果进行分页流程是和上面的一样的,但是要注意,前端除了当前页码外还需要传递搜索条件。
-
在jsp页面中实现分页功能(计算页码)
实现
<c:choose>
<%--这里用到了两个变量,分别为begin和end,都是Page域中的对象--%>
<%--如果总页数<=10(因为按需求是显示十个页码按钮)则Page域中的begin变量为1,end变量为总页数--%>
<c:when test="${requestScope.pages.totalPage <= 10}">
<c:set var="begin" value="1"/>
<c:set var="end" value="${requestScope.pages.totalPage}"/>
</c:when>
<c:otherwise>
<%--如果总页数 > 10,则设置begin变量为当前页-5,end变量为当前页+4,如果下面运算得到begin大于1,则从这里设置的页码显示--%>
<c:set var="begin" value="${requestScope.pages.thisPage-5}"/>
<c:set var="end" value="${requestScope.pages.thisPage+4}"/>
<%--如果经过上述运算,begin< 1 则说明总页数大于10,但是当前查询页并未超过10,那么页面上还应该显示从1到10的页码--%>
<c:if test="${begin<1}">
<c:set var="begin" value="1"/>
<c:set var="end" value="${begin+9}"/>
</c:if>
<%--如果end变量的值大于了总页数,则按下面的显示--%>
<c:if test="${end>requestScope.pages.totalPage}">
<c:set var="end" value="${requestScope.pages.totalPage}"/>
<c:set var="begin" value="${end-9}"/>
</c:if>
</c:otherwise>
</c:choose>
总结
基本的思路是这样的:
<%
1.确定在界面上要显示多少页码,比如要显示的为1~10
2.确定两个变量,begin和end,用来存放开始页码和结束页码
3.确定之后就要判断,totalPage是不是小于10,如果小于10,那么begin = 1,end = totalPage
%>
<c:when test="${requestScope.pages.totalPage <= 10}">
<c:set var="begin" value="1"/>
<c:set var="end" value="${requestScope.pages.totalPage}"/>
</c:when>
<%
4.如果totalPage > 10,那么可以使用公式进行计算起始页(设置begin变量为当前页-5,end变量为当前页+4)
5.如果begin-5 < 0,则设置begin = 1,end = 10
6.如果end > totalPage,则设置 end = totalPage,begin = currentPage - 9;(begin和end之间相差9)
%>
在jsp页面中实现分页功能(UI展示)
在使用时,需要和上面的计算结合使用,上面的用来计算起始页码,下面的主要用来进行ui展示。
<%--使用bootstarp实现的分页ui,排版较差--%>
<c:if test="${sessionScope.pageInfo.totalPage > 1}">
<div class="container">
<nav class="page pull-right pagination pagination-lg">
<ul class="pagination">
<li>
<c:choose>
<c:when test="${sessionScope.pageInfo.thisPage > 1}">
<a href="${pageContext.request.contextPath}/book/cateGoryServlet?method=paging&cname=${requestScope.cname}&thisPage=${sessionScope.pageInfo.previousPage}&cid=${sessionScope.pageInfo.records.get(0).cid}"
aria-label="Previous">
<span aria-hidden="true">«</span>
</a>
</c:when>
<c:otherwise>
<a href="#" aria-label="Previous" class="disabled">
<span aria-hidden="true">«</span>
</a>
</c:otherwise>
</c:choose>
</li>
<c:forEach var="i" begin="${begin}" end="${end}">
<c:choose>
<c:when test="${i eq sessionScope.pageInfo.thisPage}">
<li class="active">
<a href="#">${i}</a>
</li>
</c:when>
<c:otherwise>
<li class="">
<a href="${pageContext.request.contextPath}/book/cateGoryServlet?method=paging&cname=${requestScope.cname}&thisPage=${i}&cid=${sessionScope.pageInfo.records.get(0).cid}">${i}</a>
</li>
</c:otherwise>
</c:choose>
</c:forEach>
<li>
<c:if test="${sessionScope.pageInfo.thisPage < sessionScope.pageInfo.totalPage}">
<a href="${pageContext.request.contextPath}/book/cateGoryServlet?method=paging&cname=${requestScope.cname}&thisPage=${sessionScope.pageInfo.nextPage}&cid=${sessionScope.pageInfo.records.get(0).cid}"
aria-label="Next">
<span aria-hidden="true">»</span>
</a>
</c:if>
<c:if test="${sessionScope.pageInfo.thisPage >= sessionScope.pageInfo.totalPage}">
<a href="#" aria-label="Next" class="disabled">
<span aria-hidden="true">»</span>
</a>
</c:if>
</li>
</ul>
</nav>
</div>
</c:if>