样式很简单,主要练习父子间传值。
在components文件夹中新建popup.vue文件,里面写的是弹窗的。。emm就是弹窗。之后作为组件引入进购物车页面。
逻辑:(为了方便,接下来的弹窗用 “子”来表示,购物车用“父”来表示)
①先将子组件引入到父中,不过v-if初始定义为dialogShow,值为false,先不显示;
②点击父中的“删除”按钮,子才显示,并且存储一个index值cancelsureidx;
③在子组件中点击“取消”按钮,将一个false作为值传入到父中,更改dialogShow的值,弹窗消失;
④子组件中点击“确定”按钮,将父中的cartData数组splice掉cancelsureidx那一条,之后弹窗消失。
先写弹窗页面 ↓
<template>
<div>
<div class="popup">
<!-- content为从父组件中接收的提示信息的值 -->
<p class="info">{{content}}</p>
<div class="btn">
<el-button type="info" size="mini" class="cancel" @click="close"
>取消</el-button
>
<el-button type="primary" size="mini" class="forsure" @click="forsure">确定</el-button>
</div>
<el-button class="close" @click="close">X</el-button>
</div>
<div class="mask"></div>
</div>
</template>
<script>
export default {
//从cart中传过来的提示内容,用props接收
props:["content"],
data() {
return {
ifShow: true,
};
},
methods: {
close() {
//通过子传父修改cart里的dialogShow的值
this.$emit("close",false);
},
forsure(){
this.$emit("sure");
}
},
};
</script>
<style lang="scss" scoped>
//这个公共文件只是用了一下primary的颜色
@import "../assets/css/common.scss";
.container_cart {
height: 100%;
}
.mask {
width: 100%;
height: 100%;
background: rgba(0, 0, 0, 0.2);
position: absolute;
top: 0;
left: 0;
}
.popup {
width: 400px;
height: 150px;
background: white;
box-shadow: 0 0 10px 2px rgba(0, 0, 0, 0.2);
padding: 40px;
position: fixed;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
z-index:1;
.info {
text-align: center;
color: grey;
}
.btn {
position: absolute;
bottom: 10px;
right: 20px;
}
.close {
font-size: 15px;
position: absolute;
right: 8px;
top: 8px;
}
}
</style>
购物车页面:↓
<template>
<div class="container_cart">
<h2 class="text-center">购物车</h2>
<table class="table table-bordered table-hover table_width">
<thead>
<tr>
<td>
全选
<input type="checkbox" v-model="allC" @click="allCheck" />
</td>
<td>商品</td>
<td>单价</td>
<td>数量</td>
<td>小计</td>
<td>操作</td>
</tr>
</thead>
<tbody>
<tr v-for="(good, index) in cartData" :key="good.name">
<td>
<input
type="checkbox"
v-model="good.check"
@click="smallCheck(index)"
/>
</td>
<td>{{ good.name }}</td>
<td>{{ good.price }}</td>
<td>
<button class="btn" @click="subtract(index)">-</button>
{{ good.num }}
<button class="btn" @click="add(index)">+</button>
</td>
<td>{{ good.num * good.price }}</td>
<td>
<button class="btn btn-danger btn-sm" @click="del(index)">
删除
</button>
</td>
</tr>
<tr>
<td colspan="6">合计金额:¥{{ allPrice }}</td>
</tr>
</tbody>
</table>
<!--
子组件 Popup
close和 sure都是子组件根据取消或确定传回来的值
设置一个动态变量向子组件中传输提示的内容
-->
<Popup v-if="dialogShow" @close="close" @sure="sure" :content="content" />
</div>
</template>
<script>
import Popup from "../components/popup";
export default {
components: {
Popup,
},
data() {
return {
//content中数据为提示内容
content:"您确定将该商品移出购物车吗?",
cartData: [
{
name: "手机1",
price: 100,
num: 1,
check: true,
},
{
name: "手机2",
price: 2000,
num: 2,
check: true,
},
{
name: "手机3",
price: 3000,
num: 1,
check: true,
},
{
name: "手机4",
price: 1000,
num: 1,
check: true,
},
],
allC: true,
dialogShow: false,
cancelsureidx:null,
};
},
computed: {
allPrice() {
let n = 0;
this.cartData.map((item) => {
if (item.check) {
n += item.price * item.num;
}
});
return n;
},
},
methods: {
allCheck() {
this.cartData.map((item) => {
item.check = !this.allC;
});
},
smallCheck(i) {
this.cartData[i].check = !this.cartData[i].check;
this.allC = this.cartData.every((item) => {
return item.check;
});
},
subtract(i) {
if (this.cartData[i].num > 1) {
this.cartData[i].num--;
}
},
add(i) {
this.cartData[i].num++;
},
del(i) {
//先让dialog显示
this.dialogShow = true;
//弹窗中点击“确定”后需要的index值
this.cancelsureidx = i;
},
close(e){ //弹窗中点击“取消”按钮
//子传父 ==== 点击子组件中的关闭弹窗,更改父中dialogShow的值为false
this.dialogShow = e;
},
sure(){ //弹窗中点击“确定”按钮
//删除cartData中的那一项
this.cartData.splice(this.cancelsureidx,1);
//操作完删除后让弹窗消失
this.dialogShow = false;
}
},
};
</script>
<style lang="scss" scoped>
.el-table {
margin: 0 auto;
}
.table {
width: 60%;
margin: 0 auto;
}
h2 {
margin: 20px 0;
}
</style>
网友评论