@[toc]
登录页面
存入vuex
1.新建 vuex user 模块 store/modules/user.js
export default {
namespaced: true,//开启命名空间
state () {
return {
userInfo: {
token: '',
userId: ''
},
}
},
mutations: {
},
actions: {
}
}
2.挂载到 vuex 上
import Vue from 'vue'
import Vuex from 'vuex'
import user from './modules/user'
Vue.use(Vuex)
export default new Vuex.Store({
modules: {
user,
}
})
3.提供 mutations
mutations: {
setUserInfo (state, obj) {
state.userInfo = obj
},
},
4.页面中 commit 调用
// 登录按钮(校验 & 提交)
async login () {
if (!this.validFn()) {
return
}
...
const res = await codeLogin(this.mobile, this.msgCode)
this.$store.commit('user/setUserInfo', res.data)
this.$router.push('/')
this.$toast('登录成功')
}
持久化处理
1.新建 utils/storage.js
封装方法
const INFO_KEY = 'hm_shopping_info'
// 获取个人信息
export const getInfo = () => {
const result = localStorage.getItem(INFO_KEY)
return result ? JSON.parse(result) : {
token: '',
userId: ''
}
}
// 设置个人信息
export const setInfo = (info) => {
localStorage.setItem(INFO_KEY, JSON.stringify(info))
}
// 移除个人信息
export const removeInfo = () => {
localStorage.removeItem(INFO_KEY)
}
2.vuex user 模块持久化处理
import {
getInfo, setInfo } from '@/utils/storage'
export default {
namespaced: true,
state () {
return {
userInfo: getInfo()
}
},
mutations: {
setUserInfo (state, obj) {
state.userInfo = obj
setInfo(obj)
}
},
actions: {
}
}
购物车
1.新建 modules/cart.js
模块
export default {
namespaced: true,
state () {
return {
cartList: []
}
},
mutations: {
},
actions: {
},
getters: {
}
}
2.挂载到 store 上面
import Vue from 'vue'
import Vuex from 'vuex'
import user from './modules/user'
import cart from './modules/cart'
Vue.use(Vuex)
export default new Vuex.Store({
getters: {
token: state => state.user.userInfo.token
},
modules: {
user,
cart
}
})
3.封装 action 和 mutation
mutations: {
setCartList (state, newList) {
state.cartList = newList
},
},
actions: {
async getCartAction (context) {
const {
data } = await getCartList()
data.list.forEach(item => {
item.isChecked = true
})
// 后台返回的数据中,不包含复选框的选中状态,为了实现将来的功能
// 需要手动维护数据,给每一项,添加一个 isChecked 状态 (标记当前商品是否选中)
context.commit('setCartList', data.list)
}
},
5.页面中 dispatch 调用
computed: {
isLogin () {
return this.$store.getters.token
}
},
created () {
if (this.isLogin) {
this.$store.dispatch('cart/getCartAction')
}
},
mapState - 渲染购物车列表
1.将数据映射到页面
import {
mapState } from 'vuex'
computed: {
...mapState('cart', ['cartList'])
}
2.动态渲染
<!-- 购物车列表 -->
<div class="cart-list">
<div class="cart-item" v-for="item in cartList" :key="item.goods_id">
<van-checkbox icon-size="18" :value="item.isChecked"></van-checkbox>
<div class="show" @click="$router.push(`/prodetail/${item.goods_id}`)">
<img :src="item.goods.goods_image" alt="">
</div>
<div class="info">
<span class="tit text-ellipsis-2">{
{
item.goods.goods_name }}</span>
<span class="bottom">
<div class="price">¥ <span>{
{
item.goods.goods_price_min }}</span></div>
<CountBox :value="item.goods_num"></CountBox>
</span>
</div>
</div>
</div>
封装 getters - 动态计算展示
1.封装 getters:商品总数 / 选中的商品列表 / 选中的商品总数 / 选中的商品总价
getters: {
cartTotal (state) {
return state.cartList.reduce((sum, item, index) => sum + item.goods_num, 0)
},
selCartList (state) {
return state.cartList.filter(item => item.isChecked)
},
selCount (state, getters) {
return getters.selCartList.reduce((sum, item, index) => sum + item.goods_num, 0)
},
selPrice (state, getters) {
return getters.selCartList.reduce((sum, item, index) => {
return sum + item.goods_num * item.goods.goods_price_min
}, 0).toFixed(2)
}
}
全选反选功能
1.全选 getters
getters: {
isAllChecked (state) {
return state.cartList.every(item => item.isChecked)
}
}
...mapGetters('cart', ['isAllChecked']),
<div class="all-check">
<van-checkbox :value="isAllChecked" icon-size="18"></van-checkbox>
全选
</div>
2.点击小选,修改状态
<van-checkbox @click="toggleCheck(item.goods_id)" ...></van-checkbox>
toggleCheck (goodsId) {
this.$store.commit('cart/toggleCheck', goodsId)
},
mutations: {
toggleCheck (state, goodsId) {
const goods = state.cartList.find(item => item.goods_id === goodsId)
goods.isChecked = !goods.isChecked
},
}
3.点击全选,重置状态
<div @click="toggleAllCheck" class="all-check">
<van-checkbox :value="isAllChecked" icon-size="18"></van-checkbox>
全选
</div>
toggleAllCheck () {
this.$store.commit('cart/toggleAllCheck', !this.isAllChecked)
},
mutations: {
toggleAllCheck (state, flag) {
state.cartList.forEach(item => {
item.isChecked = flag
})
},
}