一、计算属性
计算属性就是基于现有的数据推算出来的新属性,只要依赖的数据变化,新属性就会自动更新,而且计算属性多次调用的情况下只会计算一次,效率非常高
简化写法
const app = new Vue({ el: '#app', data: {}, methods: {//跟data平级 函数名(){ return 计算结果 } }, computed:{//跟data平级 计算属性名(){ return 计算结果 } } })
完整写法
计算属性的值默认情况下是不能直接进行修改的,如果非要修改,就必须使用计算属性的完整写法(表格全选情况会用到,下篇文章案例中会出现)
const app = new Vue({ el: '#app', data: {}, computed:{//跟data平级 计算属性名:{ get(){ 返回计算属性的值 } set(val){ 提供修改的逻辑 } } } })
二、Vue周期
三、axios发送请求
四、前后端交互案例
接口文档地址: 查询我的账单列表 - 传智教育-vue基础案例接口
功能需求:
1.基本渲染
2.合计根据页面数据变化
3. 添加功能
4. 删除功能
初始代码:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Document</title>
<!-- CSS only -->
<link href="./css/bootstrap.min.css" rel="stylesheet">
<script src="./js/vue-2.6.12.js"></script>
<script src="./js/axios-0.20.0.js"></script>
<style>
.red {
color: red !important;
}
.search {
width: 300px;
margin: 20px 0;
}
.my-form {
display: flex;
margin: 20px 0;
}
.my-form input {
flex: 1;
margin-right: 20px;
}
.table> :not(:first-child) {
border-top: none;
}
.contain {
display: flex;
padding: 10px;
}
.list-box {
flex: 1;
padding: 0 30px;
}
.list-box a {
text-decoration: none;
}
.echarts-box {
width: 600px;
height: 400px;
padding: 30px;
margin: 0 auto;
border: 1px solid #ccc;
}
tfoot {
font-weight: bold;
}
@media screen and (max-width: 1000px) {
.contain {
flex-wrap: wrap;
}
.list-box {
width: 100%;
}
.echarts-box {
margin-top: 30px;
}
}
</style>
</head>
<body>
<div id="app">
<div class="contain">
<!-- 左侧列表 -->
<div class="list-box">
<!-- 添加资产 -->
<form class="my-form">
<input type="text" class="form-control" placeholder="消费名称" />
<input type="text" class="form-control" placeholder="消费价格" />
<button type="button" class="btn btn-primary">添加账单</button>
</form>
<table class="table table-hover">
<thead>
<tr>
<th>编号</th>
<th>消费名称</th>
<th>消费价格</th>
<th>操作</th>
</tr>
</thead>
<tbody>
<tr>
<td>1</td>
<td>帽子</td>
<td>99</td>
<td><a href="javascript:;">删除</a></td>
</tr>
</tbody>
<tfoot>
<tr>
<td colspan="4">消费总计: 298.00</td>
</tr>
</tfoot>
</table>
</div>
</div>
</div>
<script>
/**
* 接口文档地址:
* https://www.apifox.cn/apidoc/shared-24459455-ebb1-4fdc-8df8-0aff8dc317a8/api-53371058
*
* 功能需求:
* 1. 基本渲染
* 2. 添加功能
* 3. 删除功能
*/
const app = new Vue({
el: '#app',
data: {
},
methods: {
},
created() {
}
})
</script>
</body>
</html>
网页初始界面如图所示:
1、基本渲染:
(1)定义一个发送请求的查询数据的方法(在vue初始化后,渲染前执行)
(2)查询句式:
axios.get("地址?Query参数变量名=参数值").then(res=>{
res.data.data
})
(3)在vue对象的data{}中,定义一个数组接收数据
(4)在html的body代码中利用v-for遍历数组数据,展现在页面上
该部分代码实现:
<tr v-for="(item,index) in orders">
<td>{{item.id}}</td>
<td>{{item.name}}</td>
<td>{{item.price}}</td>
<td><a href="javascript:;">删除</a></td>
</tr>
<script>
const app = new Vue({
el: '#app',
data: {
orders:[]
},
methods: {
//1、定义一个发送请求查询数据的方法
findAll() {
axios.get("https://applet-base-api-t.itheima.net/bill?creator=zhangsan").then(res=>{
this.orders = res.data.data
})
}
},
created() {
//vue初始化后,渲染之前执行
this.findAll()
}
})
</script>
效果图:
2、合计根据页面数据变化
(1)在vue对象中使用计算属性,实现总计效果
(2)写一个total()方法,定义sum存储结果,遍历数组,获取每条数据的价格相加,然后返回sum
(3)在html的body代码中,将写死的数据,换成插值表达式{{total}}
该部分代码实现:
<tr>
<td colspan="4">消费总计:{{total}}</td>
</tr>
<script>
const app = new Vue({
el: '#app',
data: {
orders:[]
},
methods: {
//1、定义一个发送请求查询数据的方法
findAll() {
axios.get("https://applet-base-api-t.itheima.net/bill?creator=zhangsan").then(res=>{
this.orders = res.data.data
})
}
},
created() {
//vue初始化后,渲染之前执行
this.findAll()
},
computed: {
total(){
let sum = 0
this.orders.forEach(element => {
sum += element.price
})
return sum
}
}
})
</script>
效果图:
3、添加功能
(1)在vue对象的data{}中,定义一个对象 saveOrder:{},用于存储要存入的数据
(2)通过v-model双向绑定输入框与vue对象
(3)给“添加账单”按钮绑定事件add()
(4)在vue对象的methods{}中实现add()方法
(a)设置账单的创建者
(b)发送请求到服务端保存
添加句式:
axios.post("地址",添加对象).then(res=>{}
(d)判断保存是否成功
(e)页面的数据列表重新加载
(f)清空输入框
该部分代码实现:
<form class="my-form">
<input type="text" class="form-control" placeholder="消费名称" v-model="saveOrder.name"/>
<input type="text" class="form-control" placeholder="消费价格" v-model="saveOrder.price"/>
<button type="button" class="btn btn-primary" @click="add()">添加账单</button>
</form>
<script>
const app = new Vue({
el: '#app',
data: {
orders:[],
saveOrder:{}
},
methods: {
//1、定义一个发送请求查询数据的方法
findAll() {
axios.get("https://applet-base-api-t.itheima.net/bill?creator=zhangsan").then(res=>{
this.orders = res.data.data
})
},
add(){
//设置账单的创建者
this.saveOrder.creator="zhangsan"
//发送请求到服务端保存
axios.post("https://applet-base-api-t.itheima.net/bill",this.saveOrder).then(res=>{
//判断保存是否成功
if(res.data.message=="ok"){
alert("添加成功")
//页面的数据列表重新加载
this.findAll()
//清空输入框
this.saveOrder={}
}
})
}
},
created() {
//vue初始化后,渲染之前执行
this.findAll()
},
computed: {
total(){
let sum = 0
this.orders.forEach(element => {
sum += element.price
})
return sum
}
}
})
</script>
效果图:
4、 删除功能
(1)给“删除”按钮绑定事件del(),需要根据id删除,所以需要传入参数item.id
(2)在vue对象的methods{}中实现del()方法
(a)发送请求,删除数据
删除句式:
axios.delete("地址" + id).then(res=>{
console.log(res)
)}
(b)判断响应的message是否ok
(d)页面的数据列表重新加载
该部分代码实现:
<td><a href="javascript:;" @click="del(item.id)">删除</a></td>
<script>
const app = new Vue({
el: '#app',
data: {
orders:[],
saveOrder:{}
},
methods: {
//1、定义一个发送请求查询数据的方法
findAll() {
axios.get("https://applet-base-api-t.itheima.net/bill?creator=zhangsan").then(res=>{
this.orders = res.data.data
})
},
add(){
//设置账单的创建者
this.saveOrder.creator="zhangsan"
//发送请求到服务端保存
axios.post("https://applet-base-api-t.itheima.net/bill",this.saveOrder).then(res=>{
//判断保存是否成功
if(res.data.message=="ok"){
alert("添加成功")
//页面的数据列表重新加载
this.findAll()
//清空输入框
this.saveOrder={}
}
})
},
del(id){//根据id删除
// 发送请求,删除数据
axios.delete("https://applet-base-api-t.itheima.net/bill/" + id).then(res=>{
console.log(res)
// 判断响应的message是否ok
if(res.data.message=="ok"){
alert("删除成功")
this.findAll()
}
})
}
},
created() {
//vue初始化后,渲染之前执行
this.findAll()
},
computed: {
total(){
let sum = 0
this.orders.forEach(element => {
sum += element.price
})
return sum
}
}
})
</script>
效果图:
完整代码:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Document</title>
<!-- CSS only -->
<link href="./css/bootstrap.min.css" rel="stylesheet">
<script src="./js/vue-2.6.12.js"></script>
<script src="./js/axios-0.20.0.js"></script>
<style>
.red {
color: red !important;
}
.search {
width: 300px;
margin: 20px 0;
}
.my-form {
display: flex;
margin: 20px 0;
}
.my-form input {
flex: 1;
margin-right: 20px;
}
.table> :not(:first-child) {
border-top: none;
}
.contain {
display: flex;
padding: 10px;
}
.list-box {
flex: 1;
padding: 0 30px;
}
.list-box a {
text-decoration: none;
}
.echarts-box {
width: 600px;
height: 400px;
padding: 30px;
margin: 0 auto;
border: 1px solid #ccc;
}
tfoot {
font-weight: bold;
}
@media screen and (max-width: 1000px) {
.contain {
flex-wrap: wrap;
}
.list-box {
width: 100%;
}
.echarts-box {
margin-top: 30px;
}
}
</style>
</head>
<body>
<div id="app">
<div class="contain">
<!-- 左侧列表 -->
<div class="list-box">
<!-- 添加资产 -->
<form class="my-form">
<input type="text" class="form-control" placeholder="消费名称" v-model="saveOrder.name"/>
<input type="text" class="form-control" placeholder="消费价格" v-model="saveOrder.price"/>
<button type="button" class="btn btn-primary" @click="add()">添加账单</button>
</form>
<table class="table table-hover">
<thead>
<tr>
<th>编号</th>
<th>消费名称</th>
<th>消费价格</th>
<th>操作</th>
</tr>
</thead>
<tbody>
<tr v-for="(item,index) in orders">
<td>{{item.id}}</td>
<td>{{item.name}}</td>
<td>{{item.price}}</td>
<td><a href="javascript:;" @click="del(item.id)">删除</a></td>
</tr>
</tbody>
<tfoot>
<tr>
<td colspan="4">消费总计:{{total}}</td>
</tr>
</tfoot>
</table>
</div>
</div>
</div>
<script>
/**
* 接口文档地址:
* https://www.apifox.cn/apidoc/shared-24459455-ebb1-4fdc-8df8-0aff8dc317a8/api-53371058
*
* 功能需求:
* 1. 基本渲染
* 2. 添加功能
* 3. 删除功能
*/
const app = new Vue({
el: '#app',
data: {
orders:[],
saveOrder:{}
},
methods: {
//1、定义一个发送请求查询数据的方法
findAll() {
axios.get("https://applet-base-api-t.itheima.net/bill?creator=zhangsan").then(res=>{
this.orders = res.data.data
})
},
add(){
//设置账单的创建者
this.saveOrder.creator="zhangsan"
//发送请求到服务端保存
axios.post("https://applet-base-api-t.itheima.net/bill",this.saveOrder).then(res=>{
//判断保存是否成功
if(res.data.message=="ok"){
alert("添加成功")
//页面的数据列表重新加载
this.findAll()
//清空输入框
this.saveOrder={}
}
})
},
del(id){//根据id删除
// 发送请求,删除数据
axios.delete("https://applet-base-api-t.itheima.net/bill/" + id).then(res=>{
console.log(res)
// 判断响应的message是否ok
if(res.data.message=="ok"){
alert("删除成功")
this.findAll()
}
})
}
},
created() {
//vue初始化后,渲染之前执行
this.findAll()
},
computed: {
total(){
let sum = 0
this.orders.forEach(element => {
sum += element.price
})
return sum
}
}
})
</script>
</body>
</html>