1、达到目的:
与具体ORM实现无关的分页参数及查询结果封装.
另:js分页中url可以不传入。
与具体ORM实现无关的分页参数及查询结果封装.
2、分页代码封装:
public class Page<T> implements Iterable<T> {
//-- 公共变量 --//
public static final String ASC = "asc";
public static final String DESC = "desc";
//-- 分页查询参数 --//
public int pageNo = 1;
public int pageSize = -1;
public int totalPage = 1;
public boolean autoCount = true;
public String orderBy = null;
public String order = null;
//-- 返回结果 --//
public List<T> result = Lists.newArrayList();
public Integer totalItems = -1;
@SuppressWarnings("rawtypes")
public Map returnMap;
//-- 构造函数 --//
public Page() {
}
public Page(int pageSize) {
setPageSize(pageSize);
}
public Page(int pageNo, int pageSize) {
setPageNo(pageNo);
setPageSize(pageSize);
}
//-- 分页参数访问函数 --//
/**
* 获得当前页的页号,序号从1开始,默认为1.
*/
public int getPageNo() {
return pageNo;
}
/**
* 设置当前页的页号,序号从1开始,低于1时自动调整为1.
*/
public void setPageNo(final int pageNo) {
this.pageNo = pageNo;
if (pageNo < 1) {
this.pageNo = 1;
}
}
/**
* 获得每页的记录数量, 默认为-1.
*/
public int getPageSize() {
return pageSize;
}
/**
* 设置每页的记录数量.
*/
public void setPageSize(final int pageSize) {
this.pageSize = pageSize;
}
/**
* 获得排序字段,无默认值. 多个排序字段时用','分隔.
*/
public String getOrderBy() {
return orderBy;
}
/**
* 设置排序字段,多个排序字段时用','分隔.
*/
public void setOrderBy(final String orderBy) {
this.orderBy = orderBy;
}
/**
* 获得排序方向, 无默认值.
*/
public String getOrder() {
return order;
}
/**
* 设置排序方式向.
*
* @param order 可选值为desc或asc,多个排序字段时用','分隔.
*/
public void setOrder(final String order) {
String lowcaseOrder = StringUtils.lowerCase(order);
//检查order字符串的合法值
String[] orders = StringUtils.split(lowcaseOrder, ',');
for (String orderStr : orders) {
if (!StringUtils.equals(DESC, orderStr) && !StringUtils.equals(ASC, orderStr)) {
throw new IllegalArgumentException("排序方向" + orderStr + "不是合法值");
}
}
this.order = lowcaseOrder;
}
/**
* 是否已设置排序字段,无默认值.
*/
public boolean isOrderBySetted() {
return (StringUtils.isNotBlank(orderBy) && StringUtils.isNotBlank(order));
}
/**
* 根据pageNo和pageSize计算当前页第一条记录在总结果集中的位置,序号从0开始.
* 用于Mysql,Hibernate.
*/
public int getOffset() {
pageNo = pageNo > getTotalPages() ? getTotalPages() : pageNo;
return ((pageNo - 1) * pageSize);
}
/**
* 根据pageNo和pageSize计算当前页第一条记录在总结果集中的位置,序号从1开始.
* 用于Oracle.
*/
public int getStartRow() {
return getOffset() + 1;
}
/**
* 根据pageNo和pageSize计算当前页最后一条记录在总结果集中的位置, 序号从1开始.
* 用于Oracle.
*/
public int getEndRow() {
return pageSize * pageNo;
}
//-- 访问查询结果函数 --//
/**
* 获得页内的记录列表.
*/
public List<T> getResult() {
return result;
}
/**
* 设置页内的记录列表.
*/
public void setResult(final List<T> result) {
this.result = result;
}
/**
* 实现Iterable接口,可以for(Object item : page)遍历使用
*/
@SuppressWarnings("unchecked")
public Iterator<T> iterator() {
return result == null ? IteratorUtils.EMPTY_ITERATOR : result.iterator();
}
/**
* 获得总记录数, 默认值为-1.
*/
public long getTotalItems() {
return totalItems;
}
/**
* 设置总记录数.
*/
public void setTotalItems(final Integer totalItems) {
this.totalItems = totalItems;
getTotalPages();
}
/**
* 是否最后一页.
*/
public boolean isLastPage() {
return pageNo == getTotalPages();
}
/**
* 是否还有下一页.
*/
public boolean isHasNextPage() {
return (pageNo + 1 <= getTotalPages());
}
/**
* 取得下页的页号, 序号从1开始.
* 当前页为尾页时仍返回尾页序号.
*/
public int getNextPage() {
if (isHasNextPage()) {
return pageNo + 1;
} else {
return pageNo;
}
}
/**
* 是否第一页.
*/
public boolean isFirstPage() {
return pageNo == 1;
}
/**
* 是否还有上一页.
*/
public boolean isHasPrePage() {
return (pageNo - 1 >= 1);
}
/**
* 取得上页的页号, 序号从1开始.
* 当前页为首页时返回首页序号.
*/
public int getPrePage() {
if (isHasPrePage()) {
return pageNo - 1;
} else {
return pageNo;
}
}
/**
* 根据pageSize与totalItems计算总页数, 默认值为-1.
*/
public Integer getTotalPages() {
if (totalItems % pageSize == 0) {
totalPage = totalItems / pageSize == 0 ? 1 : totalItems / pageSize;
} else {
totalPage = totalItems / pageSize + 1;
}
return totalPage;
}
/**
* 计算以当前页为中心的页面列表,如"首页,23,24,25,26,27,末页"
* @param count 需要计算的列表大小
* @return pageNo列表
*/
public List<Long> getSlider(int count) {
int halfSize = count / 2;
long totalPage = getTotalPages();
long startPageNumber = Math.max(pageNo - halfSize, 1);
long endPageNumber = Math.min(startPageNumber + count - 1, totalPage);
if (endPageNumber - startPageNumber < count) {
startPageNumber = Math.max(endPageNumber - count, 1);
}
List<Long> result = Lists.newArrayList();
for (long i = startPageNumber; i <= endPageNumber; i++) {
result.add(new Long(i));
}
return result;
}
public String paging(String url ,int count) {
boolean hasHtml = url.indexOf(".do")!=-1;
if(hasHtml) {
url = (url.indexOf("?")!=-1)?url+"&":url+"?";
}
long currentPage = getPageNo()>getTotalPages()?getTotalPages():getPageNo();
StringBuilder sb = new StringBuilder();
if(getTotalPages() > 1) {
sb.append("<div class='pageleft'><div class='morepage-div'><div class='result'>共有 <b>");
sb.append(getTotalItems()+"</b> 条");
sb.append(currentPage+"/"+getTotalPages());
sb.append("</div><div class='contain'><div class='morepage'>");
if(isHasPrePage()) {
//sb.append("<a href='"+url+(hasHtml?"page=1":"&page=1")+"' >首页</a>");
sb.append("<a href='javascript:void(0);' onclick=\"goToPage('1');\" >首页</a>");
//sb.append("<a href='"+url+(hasHtml?"page="+getPrePage():"&page="+getPrePage())+"' class='prexpage'>上一页</a>");
sb.append("<a href='javascript:void(0);' onclick=\"goToPage('"+ getPrePage() +"');\" class='prexpage'>上一页</a>");
} else {
sb.append("<span class='pagenolink'>首页</span> <span class='prenolink'>上一页</span>");
}
for(Long page : getSlider(count)) {
if(currentPage == page) {
sb.append("<span class='current'>"+page+"</span>");
} else {
//sb.append("<a href='"+url+(hasHtml?"page="+page:"&page="+page+".htm")+"'>"+page+"</a>");
sb.append("<a href='javascript:void(0);' onclick=\"goToPage('"+page+"');\">"+page+"</a>");
}
}
if(isHasNextPage()) {
//sb.append("<a href='"+url+(hasHtml?"page="+getNextPage():"&page="+getNextPage())+"' class='nextpage'>下一页</a>");
//sb.append("<a href='"+url+(hasHtml?"page="+getTotalPages():"&page="+getTotalPages())+"' class='nextpage'>尾页</a>");
sb.append("<a href='javascript:void(0);' onclick=\"goToPage('"+ getNextPage() +"');\" class='nextpage'>下一页</a>");
sb.append("<a href='javascript:void(0);' onclick=\"goToPage('"+ getTotalPages() +"');\" class='nextpage'>尾页</a>");
} else {
sb.append("<span class='nextnolink'>下一页</span>");
sb.append("<span class='pagenolink'>尾页</span>");
}
url =url+(hasHtml?"page=":"&page=");
sb.append(" <input type='text' style='width:25px;height:16px;' id='pageno''/> <input type='button' style='font-size:8pt' onclick=\"pageSubmint('"+url+"',"+getTotalPages()+")\" value='GO' /> ");
sb.append("</div></div></div></div>");
sb.append("<script>");
sb.append(" function pageSubmint(url,pageno){");
sb.append("var value = document.getElementById('pageno').value;");
sb.append(" if(!/^\\d+$/.test(value)){alert('请输入整数');return false;} ");
sb.append(" if(value>pageno||value<1){alert('请输入正确的页码'); return false;}");
//sb.append(" location.href=url+value;");
sb.append(" goToPage(value);");
sb.append(" }");
sb.append(" </script>");
}
return StringUtils.isNotBlank(sb.toString())?sb.toString():"";
}
@SuppressWarnings({ "rawtypes", "unchecked" })
public static void main(String[] args) {
Page page = new Page(2, 10);
page.setTotalItems(22);
List<Long> silders = page.getSlider(10);
for (Long pageNo : silders) {
System.out.print(pageNo + " ");
}
}
@SuppressWarnings("rawtypes")
public Map getReturnMap() {
return returnMap;
}
@SuppressWarnings("rawtypes")
public void setReturnMap(Map returnMap) {
this.returnMap = returnMap;
}
public int getTotalPage() {
return totalPage;
}
public void setTotalPage(int totalPage) {
this.totalPage = totalPage;
}
}
3、css样式代码:
@CHARSET "UTF-8";
div.pageleft {
float:left;
position:relative;
width:100%;
}
div.pageleft a, .pageleft a:link, .pagelefta:visited {
color:#2754BB;
text-decoration:none;
}
div.pageleft a:hover {
color:#FF6600;
border:1px solid #006699;
}
div.pageleft .morepage-div {
height:30px;
margin-top:10px;
width:100%;
}
div.pageleft .morepage-div .result{padding-left:20px;float:left;margin:2 2px;}
div.pageleft .morepage-div .result b{color:#EB6100;}
div.pageleft .morepage-div .contain{float:right;}
div.morepage{position:relative;}
div.morepage a {
height:20px;
border:1px solid #CCCCCC;
padding:2px 6px;
margin:2px;
text-decoration:none;
}
div.morepage .prexpage{
background:transparent url(../images/jiantou.gif) no-repeat scroll 3px -28px;
left:0;
padding:2px 12px;
}
div.morepage .nextpage{
background:transparent url(../images/jiantou.gif) no-repeat scroll 46px 6px;
right:0;
padding:2px 12px;
}
div.morepage .current{
height:18px;
padding-right:4px;
padding-left:6px;
background-color:#fff;
color:#eb6100;
border:none;
font-weight:bold;
cursor:default;
}
div .pagenolink{
left:0;
color:#ccc;
height:20px;
padding:2px 12px;
background-color:#FFF;
border:1px solid #ccc;
margin:2px;
text-decoration:none;
cursor:default;
}
div.morepage .prenolink{
background:transparent url(../images/jiantou.gif) no-repeat scroll 3px -45px;
left:0;
color:#ccc;
height:20px;
padding:2px 12px;
background-color:#FFF;
border:1px solid #ccc;
margin:2px;
text-decoration:none;
cursor:default;
}
div.morepage .nextnolink{
background:transparent url(../images/jiantou.gif) no-repeat scroll 46px -11px;
left:0;
color:#ccc;
height:20px;
padding:2px 12px;
margin:2px;
background-color:#FFF;
border:1px solid #ccc;
cursor:default;
}
4、调用实例代码:
Page<MerchantAccountDTO> page = new Page<MerchantAccountDTO>(pageNo, req.getPageSize());
page.setResult(accountList);
page.setTotalItems(respDto.getTotaltotalItems());
json.put("accountList", accountList);
json.put("paging", page.paging("accountlist.do", req.getPageSize()));
另:js分页中url可以不传入。