使用vue实现分页
使用vue实现分页的逻辑并不复杂,接收后端传输过来的数据,然后根据数据的总数和每一页的数据量就可以计算出一共可以分成几页
我编写了一个简单的前端页面用来查询数据,页面一共有几个逻辑
具体的效果可以看下面的演示
下面就来看一下具体的实现步骤。
首先看一下vue的代码
<script type="text/javascript">
Vue.createApp({
data() {
return {
items : [],
// 关键词
keyword : "",
// 是否没有数据
isnull : false,
// 一开始不显示上一页和下一页
isshow : false,
// 一共有多少条数据
countInfo : 0,
// 每一页显示几条数据
pageSize : 10,
// 当前是第几页
currentPage : 1,
// 一共有几页
countAll : 1,
code : 200
}
},
methods: {
search() {
// 拿到待搜索的关键词
var keyword = document.getElementById("keyword").value;
console.log(keyword);
this.keyword = keyword;
this.currentPage = 1;
var url = "http://localhost:8080/csdn/search/" + keyword + "/" + this.currentPage;
console.log(url);
axios.get(url).then((response) => {
if(response.data.msg.count==0) {
this.isnull = true;
// 将原始数据置空
this.items = [];
// 不显示上一页下一页按钮
this.isshow = false;
} else {
this.isnull = false;
console.log(response)
this.items = response.data.msg.list;
this.countInfo = response.data.msg.count;
// 计算一共有几页
this.countAll = Math.ceil(response.data.msg.count / this.pageSize);
this.isshow = true;
}
})
.catch(function (error) {
console.log(error);
});
},
getNextPage() {
if(this.currentPage == this.countAll) {
this.currentPage = this.currentPage;
} else {
this.currentPage = this.currentPage + 1;
}
var url = "http://localhost:8080/csdn/search/" + this.keyword + "/" + this.currentPage;
axios.get(url).then((response) => {
console.log(response)
this.items = response.data.msg.list;
// 计算一共有几页
this.countAll = Math.ceil(response.data.msg.count / this.pageSize);
})
.catch(function (error) {
console.log(error);
});
},
getPrePage() {
if(this.currentPage == 1) {
this.currentPage = 1;
} else {
this.currentPage = this.currentPage - 1;
}
var url = "http://localhost:8080/csdn/search/" + this.keyword + "/" + this.currentPage;
axios.get(url).then((response) => {
console.log(response)
this.items = response.data.msg.list;
// 计算一共有几页
this.countAll = Math.ceil(response.data.msg.count / this.pageSize);
})
.catch(function (error) {
console.log(error);
});
}
},
}).mount("#app");
</script>
data()中返回了几个变量,
- items:用来存放待展示的数据项
-
keyword:记录本次查询使用的关键词
-
isnull:表示一次查询的结果数量是否为0,用来控制没有结果的显示逻辑
-
isshow:表示是否显示上一页下一页按钮,以及显示当前页数和数据总数
-
countInfo:记录一共有多少条结果
-
pageSize:记录每页显示的数据项,目前后端固定每页展示10条数据
-
currentPage:记录当前是第几页
-
countAll:记录一共有多少页数据
-
code:后端返回的一个状态码,没什么用
一共提供了三个方法进行查询
- search():进行一个新的关键词的查询
- getNextPage():查询下一页的数据,如果已经是最后一页了,则查询当前页的结果
- getPrePage():查询上一页的数据,如果已经是第一页了,则查询当前页的结果
接着我们再来看一下后端返回的数据格式
上图中方框内的数据就是后端返回的数据,msg中记录的就是我们需要用到的数据,里面有交给数据项
- count:表示数据总数,只是查询数据总数,并不会将所有的数据都返回给前端
- list:返回当前页的数据
- page:表示当前是第几页
我们具体来看一下list中数据项的内容
可以发现list中的每一项就是构成我们前端页面中一行的数据,这在vue中体现为数据的绑定,下面就来看看详细的html代码
<!DOCTYPE html>
<html lang="en" xmlns:th="http://www.w3.org/1999/xhtml">
<html lang="en">
<head>
<meta charset="UTF-8">
<title>纳米搜索</title>
<link rel="stylesheet" href="https://cdn.staticfile.org/twitter-bootstrap/4.3.1/css/bootstrap.min.css">
<script src="https://cdn.staticfile.org/jquery/3.2.1/jquery.min.js"></script>
<script src="https://cdn.staticfile.org/popper.js/1.15.0/umd/popper.min.js"></script>
<script src="https://cdn.staticfile.org/twitter-bootstrap/4.3.1/js/bootstrap.min.js"></script>
<script src="https://unpkg.com/vue@3"></script>
<script src="https://unpkg.com/axios/dist/axios.min.js"></script>
</head>
<body>
<div class="container">
<!-- 先编写一个搜索栏 -->
<div class="row" id="app">
<div class="col-md-1"></div>
<div class="col-md-10">
<!-- 这里面有两个个部分 -->
<div class="row">
<!--<div class="col-md-2"></div>-->
<div class="col-md-12">
<div style="float: left; margin-top: 20px;margin-left: 20%">
<h2 style="color:cornflowerblue">纳米搜索</h2>
</div>
<div style="float: left; margin-top: 20px; margin-left: 20px">
<div class="form-group" style="margin-right: 20px; float: left;" >
<div class="input-group" >
<input type="text" class="form-control" name="keyword" id="keyword" placeholder="请输入要搜索的关键词">
</div>
</div>
<div style="float:left">
<button id="search" type="button" class="btn btn-primary" v-on:click="search">搜索</button>
</div>
</div>
</div>
<!--<div class="col-md-2"></div>-->
</div>
<hr>
<div>
<div v-for="item of items">
<!-- 第一行是url -->
<a :href="item.url" target="_blank">
<div style="color: #0000cc">{{item.title}}</div>
</a>
<div style="color: #28a745">{{item.url}}</div>
<!-- 这一行显示文章作者 -->
<div style="color: #000000">文章作者:<span style="color: #000000; margin-left: 10px">{{item.nick_name}}</span></div>
<!-- 这一行显示标签 -->
<div style="color: #000000">文章标签:<span style="color: #000000; margin-left: 10px">{{item.tag}}</span></div>
<!-- 下面一行显示发表时间,阅读数和收藏数 -->
<div>
<div style="color: #000000">发表时间:<span style="color: #000000;margin-left: 10px">{{item.up_time}}</span></div>
<div style="color: #000000;float: left">阅读量:<span style="color: #000000;margin-left: 10px">{{item.read_volum}}</span></div>
<div style="color: #000000;float: left; margin-left: 10px">收藏量:<span style="color: #000000;margin-left: 10px">{{item.collection_volum}}</span></div>
</div>
<br>
<hr>
</div>
</div>
<!-- 当没有查询结果的时候显示 -->
<div v-if="isnull">
<span>非常抱歉,没有您想要的结果(。・_・。)ノI’m sorry~</span>
</div>
<!-- 当有数据的时候显示 -->
<div v-if="isshow">
<div style="float:left; margin-right: 20px;" >
<button type="button" class="btn btn-primary" v-on:click="getPrePage">上一页</button>
</div>
<div style="float:left; margin-right: 20px;" >
<button type="button" class="btn btn-primary" v-on:click="getNextPage" >下一页</button>
</div>
<div style="float:left; margin-right: 20px; margin-top: 5px;">
<span>第{{currentPage}}/{{countAll}}页</spa>
</div>
<div style="float:left; margin-right: 20px; margin-top: 5px;">
<span>共有{{countInfo}}条数据</spa>
</div>
</div>
</div>
<div class="col-md-1"></div>
</div>
</div>
</body>
<script type="text/javascript">
Vue.createApp({
data() {
return {
items : [],
// 关键词
keyword : "",
// 是否没有数据
isnull : false,
// 一开始不显示上一页和下一页
isshow : false,
// 一共有多少条数据
countInfo : 0,
// 每一页显示几条数据
pageSize : 10,
// 当前是第几页
currentPage : 1,
// 一共有几页
countAll : 1,
code : 200
}
},
methods: {
search() {
// 拿到待搜索的关键词
var keyword = document.getElementById("keyword").value;
console.log(keyword);
this.keyword = keyword;
this.currentPage = 1;
var url = "http://localhost:8080/csdn/search/" + keyword + "/" + this.currentPage;
console.log(url);
axios.get(url).then((response) => {
if(response.data.msg.count==0) {
this.isnull = true;
// 将原始数据置空
this.items = [];
// 不显示上一页下一页按钮
this.isshow = false;
} else {
this.isnull = false;
console.log(response)
this.items = response.data.msg.list;
this.countInfo = response.data.msg.count;
// 计算一共有几页
this.countAll = Math.ceil(response.data.msg.count / this.pageSize);
this.isshow = true;
}
})
.catch(function (error) {
console.log(error);
});
},
getNextPage() {
if(this.currentPage == this.countAll) {
this.currentPage = this.currentPage;
} else {
this.currentPage = this.currentPage + 1;
}
var url = "http://localhost:8080/csdn/search/" + this.keyword + "/" + this.currentPage;
axios.get(url).then((response) => {
console.log(response)
this.items = response.data.msg.list;
// 计算一共有几页
this.countAll = Math.ceil(response.data.msg.count / this.pageSize);
})
.catch(function (error) {
console.log(error);
});
},
getPrePage() {
if(this.currentPage == 1) {
this.currentPage = 1;
} else {
this.currentPage = this.currentPage - 1;
}
var url = "http://localhost:8080/csdn/search/" + this.keyword + "/" + this.currentPage;
axios.get(url).then((response) => {
console.log(response)
this.items = response.data.msg.list;
// 计算一共有几页
this.countAll = Math.ceil(response.data.msg.count / this.pageSize);
})
.catch(function (error) {
console.log(error);
});
}
},
}).mount("#app");
</script>
</html>
使用vue编写前端动态页面真的比原生js或者jquery要方便很多,对比theamleaf也有很多好处。
我们在使用theamleaf的时候,每次提交表单都需要刷新页面,使用vue+axios进行ajax请求则不需要刷新页面,这不仅会减轻服务端的压力,而且可以带来更好的用户体验。