vue实现购物车功能

实现功能

CSS部分

   <style>.tr {display: flex;}.th {margin: 10px;width: 20%;height: 50%;}.td {display: flex;margin: 10px;width: 20%;height: 100px;align-items: center;}.app-container .banner-box {border-radius: 20px;overflow: hidden;margin-bottom: 10px;}.app-container .banner-box img {width: 100%;}.app-container .nav-box {background: #ddedec;height: 60px;border-radius: 10px;padding-left: 20px;display: flex;align-items: center;}.app-container .nav-box .my-nav {display: inline-block;background: #5fca71;border-radius: 5px;width: 90px;height: 35px;color: white;text-align: center;line-height: 35px;margin-right: 10px;}.breadcrumb {font-size: 16px;color: gray;}.table {width: 100%;text-align: left;border-radius: 2px 2px 0 0;border-collapse: separate;border-spacing: 0;}.table img {width: 100px;height: 100px;}button {outline: 0;box-shadow: none;color: #fff;background: #d9363e;border-color: #d9363e;color: #fff;background: #d9363e;border-color: #d9363e;line-height: 1.5715;position: relative;display: inline-block;font-weight: 400;white-space: nowrap;text-align: center;background-image: none;border: 1px solid transparent;box-shadow: 0 2px 0 rgb(0 0 0 / 2%);cursor: pointer;transition: all 0.3s cubic-bezier(0.645, 0.045, 0.355, 1);-webkit-user-select: none;-moz-user-select: none;-ms-user-select: none;user-select: none;touch-action: manipulation;height: 32px;padding: 4px 15px;font-size: 14px;border-radius: 2px;}button.pay {background-color: #3f85ed;margin-left: 20px;}.bottom {height: 60px;display: flex;align-items: center;justify-content: space-between;padding-right: 20px;border: 1px solid #f0f0f0;border-top: none;padding-left: 20px;}.right-box {display: flex;align-items: center;}.empty {text-align: center;font-size: 30px;}/* 选中时颜色是灰色 */.tr.active {background-color: #f5f7fa;}</style>

HTML

<body>
<div class="app-container" id="app"><!-- 顶部banner --><div class="banner-box"><img src="./fruitPot/封面.png" alt=""/></div><!-- 面包屑 --><div class="breadcrumb"><span>🏠</span><span>购物车</span></div><!-- 购物车主体 --><div class="main" v-if="fruitlist.length>0"><div class="table"><!-- 头部 --><div class="thead"><div class="tr"><div class="th">选中</div><div class="th th-pic">图片</div><div class="th">单价</div><div class="th num-th">个数</div><div class="th">小计</div><div class="th">操作</div></div></div><!-- 身体 --><div class="tbody"><div class="tr" :class="{active:item.isChecked}" v-for="(item) in fruitlist" :key="item.id"><div class="td"><input type="checkbox" v-model="item.isChecked"/></div><div class="td pot"><img :src="item.icon" alt=""/></div><div class="td">{{ item.price }}</div><div class="td"><div class="my-input-number"><!--disabled:禁用  --><button :disabled="item.num <=0 " class="decrease" @click="sub(item.id)"> -</button><span class="my-input__inner">{{ item.num }}</span><button class="increase" @click="add(item.id)"> +</button></div></div><div class="td">{{item.price * item.num}}</div><!-- 删除filter --><div class="td"><button @click="del(item.id)">删除</button></div></div></div></div><!-- 底部 --><div class="bottom"><!-- 全选 --><label class="check-all"><input type="checkbox" v-model="isAll"/>全选</label><div class="right-box"><!-- 所有商品总价 --><span class="price-box">总价&nbsp;&nbsp;:&nbsp;&nbsp;¥&nbsp;<span class="price">{{totalPrice()}}</span></span><!-- 结算按钮 --><button class="pay">结算( {{totalNum()}} )</button></div></div></div><!-- 空车 --><div class="empty" v-else>🛒空空如也</div>
</div>

JS

<script><!--    初始化-->// const defaultArr =[ ]const app = new Vue({el: '#app',data: {// // 水果列表从本地读取// // JSON.parse将本地JSON格式转回去// 加||defaultArr是怕用户删除完,下次刷新后只剩下空空如也// fruitlist: JSON.parse(localStorage.getItem('list'))||defaultArr,fruitlist: [{id: 1,icon: './fruitPot/苹果.png',isChecked: true,num: 2,price: 6,},{id: 2,icon: './fruitPot/苹果.png',isChecked: false,num: 7,price: 20,},{id: 3,icon: './fruitPot/鸭梨.png',isChecked: true,num: 2,price: 6,},],},// 计算属性computed: {isAll:{// isAll:  对象// get()   方法get(){// 必须所有的小选框都选中,全选按钮才选中--every// 此时的item与上面的item没关联,只是一个形参return this.fruitlist.every(item => {return  item.isChecked===true})},// value是复选框的布尔值set(value){//console.log(value)  ture/false//基于拿到的布尔值,要让所有的小选框同步状态this.fruitlist.forEach(item =>item.isChecked = value)}}},methods: {del(id) {this.fruitlist = this.fruitlist.filter(item => item.id !== id)},add(id) {// 1.根据id 找到数组中的对应项 --findconst fruit = this.fruitlist.find(item => item.id === id)// 2.操作num数量fruit.num++},sub(id) {const fruit = this.fruitlist.find(item => item.id === id)fruit.num--},//     总数量  reducetotalNum(){return this.fruitlist.reduce((sum, item) => {if (item.isChecked) {// 选中 → 需要累加return sum + item.num} else {// 没选中 → 不需要累加return sum}}, 0)},// 总价totalPrice(){return this.fruitlist.reduce((sum, item) => {if (item.isChecked) {return sum + item.num * item.price} else {return sum}}, 0)},},//     监视数据变化watch:{fruitlist:{deep:true,handler(newValue){console.log(newValue)//     需要将变化后的newValue存入本地(转JSON)localStorage.setItem('list',JSON.stringify(newValue))}}}})
</script>

全部代码

<!-- 标签\watch\methods -->
<!DOCTYPE html>
<html>
<head><meta charset="utf-8"><title>水果购物车</title><style>.tr {display: flex;}.th {margin: 10px;width: 20%;height: 50%;}.td {display: flex;margin: 10px;width: 20%;height: 100px;align-items: center;}.app-container .banner-box {border-radius: 20px;overflow: hidden;margin-bottom: 10px;}.app-container .banner-box img {width: 100%;}.app-container .nav-box {background: #ddedec;height: 60px;border-radius: 10px;padding-left: 20px;display: flex;align-items: center;}.app-container .nav-box .my-nav {display: inline-block;background: #5fca71;border-radius: 5px;width: 90px;height: 35px;color: white;text-align: center;line-height: 35px;margin-right: 10px;}.breadcrumb {font-size: 16px;color: gray;}.table {width: 100%;text-align: left;border-radius: 2px 2px 0 0;border-collapse: separate;border-spacing: 0;}.table img {width: 100px;height: 100px;}button {outline: 0;box-shadow: none;color: #fff;background: #d9363e;border-color: #d9363e;color: #fff;background: #d9363e;border-color: #d9363e;line-height: 1.5715;position: relative;display: inline-block;font-weight: 400;white-space: nowrap;text-align: center;background-image: none;border: 1px solid transparent;box-shadow: 0 2px 0 rgb(0 0 0 / 2%);cursor: pointer;transition: all 0.3s cubic-bezier(0.645, 0.045, 0.355, 1);-webkit-user-select: none;-moz-user-select: none;-ms-user-select: none;user-select: none;touch-action: manipulation;height: 32px;padding: 4px 15px;font-size: 14px;border-radius: 2px;}button.pay {background-color: #3f85ed;margin-left: 20px;}.bottom {height: 60px;display: flex;align-items: center;justify-content: space-between;padding-right: 20px;border: 1px solid #f0f0f0;border-top: none;padding-left: 20px;}.right-box {display: flex;align-items: center;}.empty {text-align: center;font-size: 30px;}/* 选中时颜色是灰色 */.tr.active {background-color: #f5f7fa;}</style>
</head>
<body>
<div class="app-container" id="app"><!-- 顶部banner --><div class="banner-box"><img src="./fruitPot/封面.png" alt=""/></div><!-- 面包屑 --><div class="breadcrumb"><span>🏠</span><span>购物车</span></div><!-- 购物车主体 --><div class="main" v-if="fruitlist.length>0"><div class="table"><!-- 头部 --><div class="thead"><div class="tr"><div class="th">选中</div><div class="th th-pic">图片</div><div class="th">单价</div><div class="th num-th">个数</div><div class="th">小计</div><div class="th">操作</div></div></div><!-- 身体 --><div class="tbody"><div class="tr" :class="{active:item.isChecked}" v-for="(item) in fruitlist" :key="item.id"><div class="td"><input type="checkbox" v-model="item.isChecked"/></div><div class="td pot"><img :src="item.icon" alt=""/></div><div class="td">{{ item.price }}</div><div class="td"><div class="my-input-number"><!--disabled:禁用  --><button :disabled="item.num <=0 " class="decrease" @click="sub(item.id)"> -</button><span class="my-input__inner">{{ item.num }}</span><button class="increase" @click="add(item.id)"> +</button></div></div><div class="td">{{item.price * item.num}}</div><!-- 删除filter --><div class="td"><button @click="del(item.id)">删除</button></div></div></div></div><!-- 底部 --><div class="bottom"><!-- 全选 --><label class="check-all"><input type="checkbox" v-model="isAll"/>全选</label><div class="right-box"><!-- 所有商品总价 --><span class="price-box">总价&nbsp;&nbsp;:&nbsp;&nbsp;¥&nbsp;<span class="price">{{totalPrice()}}</span></span><!-- 结算按钮 --><button class="pay">结算( {{totalNum()}} )</button></div></div></div><!-- 空车 --><div class="empty" v-else>🛒空空如也</div>
</div><script src="https://cdn.jsdelivr.net/npm/vue@2.7.10/dist/vue.js"></script><script><!--    初始化-->// const defaultArr =[ ]const app = new Vue({el: '#app',data: {// // 水果列表从本地读取// // JSON.parse将本地JSON格式转回去// 加||defaultArr是怕用户删除完,下次刷新后只剩下空空如也// fruitlist: JSON.parse(localStorage.getItem('list'))||defaultArr,fruitlist: [{id: 1,icon: './fruitPot/苹果.png',isChecked: true,num: 2,price: 6,},{id: 2,icon: './fruitPot/苹果.png',isChecked: false,num: 7,price: 20,},{id: 3,icon: './fruitPot/鸭梨.png',isChecked: true,num: 2,price: 6,},],},// 计算属性computed: {isAll:{// isAll:  对象// get()   方法get(){// 必须所有的小选框都选中,全选按钮才选中--every// 此时的item与上面的item没关联,只是一个形参return this.fruitlist.every(item => {return  item.isChecked===true})},// value是复选框的布尔值set(value){//console.log(value)  ture/false//基于拿到的布尔值,要让所有的小选框同步状态this.fruitlist.forEach(item =>item.isChecked = value)}}},methods: {del(id) {this.fruitlist = this.fruitlist.filter(item => item.id !== id)},add(id) {// 1.根据id 找到数组中的对应项 --findconst fruit = this.fruitlist.find(item => item.id === id)// 2.操作num数量fruit.num++},sub(id) {const fruit = this.fruitlist.find(item => item.id === id)fruit.num--},//     总数量  reducetotalNum(){return this.fruitlist.reduce((sum, item) => {if (item.isChecked) {// 选中 → 需要累加return sum + item.num} else {// 没选中 → 不需要累加return sum}}, 0)},// 总价totalPrice(){return this.fruitlist.reduce((sum, item) => {if (item.isChecked) {return sum + item.num * item.price} else {return sum}}, 0)},},//     监视数据变化watch:{fruitlist:{deep:true,handler(newValue){console.log(newValue)//     需要将变化后的newValue存入本地(转JSON)localStorage.setItem('list',JSON.stringify(newValue))}}}})
</script>
</body>
</html>

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/526890.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

初识C语言—初识C语言

前言 C语言全面了解&#xff0c;全貌认识 细致的学习&#xff0c;细枝末节 什么是C语言 维基百科 C 语言是一种通用的高级语言&#xff0c;最初是由丹尼斯里奇在贝尔实验室为开发 UNIX 操作系统而设计的。C 语言最开始是于 1972 年在 DEC PDP-11 计算机上被首次实现。 在 1978 …

智慧安防视频远程监控平台EasyCVR集成后播放只有一帧画面是什么原因?

智慧安防视频监控平台EasyCVR能在复杂的网络环境中&#xff08;专网、局域网、广域网、VPN、公网等&#xff09;将前端海量的设备进行统一集中接入与视频汇聚管理&#xff0c;平台可支持的接入协议包括&#xff1a;国标GB28181、RTSP/Onvif、RTMP&#xff0c;以及厂家的私有协议…

基于springboot+layui仓库管理系统设计和实现

基于 java springbootlayui仓库管理系统设计和实现 博主介绍&#xff1a;多年java开发经验&#xff0c;专注Java开发、定制、远程、文档编写指导等,csdn特邀作者、专注于Java技术领域 作者主页 央顺技术团队 Java毕设项目精品实战案例《1000套》 欢迎点赞 收藏 ⭐留言 文末获取…

【Attribute】Inspector视图可视不可编辑字段特性

简介 在Unity开发中&#xff0c;有时候我们存在这种需求&#xff0c;需要在Inspector视图中可以查看字段信息但是无法对字段进行赋值&#xff0c;那么我们也可以像Unity内置的[SerializeField]、[Tooltip]等特性那样自定义一个特性&#xff0c;用于满足这个需求。 代码示例(C#…

intel realsense D405 在 ROS2 使用示例

1.点云示例 此示例演示如何启动相机节点并使其使用点云选项发布点云。 ros2 launch realsense2_camera rs_launch.py pointcloud.enable:true 以下示例启动相机并同时打开 RViz GUI 以可视化发布的点云。它执行上面的 2 个示例。 ros2 launch realsense2_camera rs_pointcl…

华为OD机试C卷“跳步-数组”Java解答

描述 示例 算法思路1 不断移动数组将元素删去&#xff08;并未彻底删除&#xff0c;而是将数字元素前移实现“伪删除”&#xff09;这样删除元素的位置就呈现一定规律&#xff0c;详细见下图&#xff08;潦草的画&#xff09; 答案1 import java.util.*;public class Main {…

RabbitMQ - 03 - Work消息模型

目录 部署demo项目 什么是Work消息模型 实现Work消息模型 1.创建队列 2.生产者代码 3.消费者代码 4.配置yml 部署demo项目 通过消息队列demo项目进行练习 相关配置看此贴 http://t.csdnimg.cn/hPk2T 注意 生产者消费者的yml文件也要配置好 什么是Work消息模型 工作…

Java对接腾讯云直播示例

首先是官网的文档地址 云直播 新手指南 可以发现它这个主要是按流量和功能收费的 价格总览 流量这里还只收下行的费用&#xff0c;就是只收观看消耗的流量费 其它的收费就是一些增值业务费 &#xff08;包括直播转码、直播录制、直播截图、直播审核、智能鉴黄、实时监播、移动直…

解决阿里云服务器开启frp服务端,内网服务器开启frp客户端却连接不上的问题

解决方法&#xff1a; 把阿里云自带的Alibabxxxxxxxlinux系统 换成centos 7系统&#xff01;&#xff01;&#xff01;&#xff01; 说一下我的过程和问题&#xff1a;由于我们内网的服务器在校外是不能连接的&#xff0c;因此我弄了个阿里云服务器做内网穿透&#xff0c;所谓…

Sora盈利新路径:基于技术创新与跨界融合

在数字化时代&#xff0c;技术的飞速进步为企业带来了前所未有的盈利机会。Sora作为一款前沿的AI视频生成工具&#xff0c;其盈利新路径可以基于技术创新与跨界融合两个核心策略来探索。 一、技术创新&#xff1a;持续引领行业前沿 Sora学习资料&#xff1a;使用方式完整文档…

安装及管理docker

文章目录 1.Docker介绍2.Docker安装3.免sudo设置4. 使用docker命令5.Images6.运行docker容器7. 管理docker容器8.创建image9.Push Image 1.Docker介绍 Docker 是一个简化在容器中管理应用程序进程的应用程序。容器让你在资源隔离的进程中运行你的应用程序。类似于虚拟机&#…