feat(rental): 新增我的柜子页面及相关功能
- 添加我的柜子页面路由和导航入口 - 实现用户租赁柜子列表展示功能 - 优化订单列表样式和商品信息展示 - 在用户信息中增加ab98User字段支持 - 统一订单获取接口参数格式
This commit is contained in:
parent
7ab5130cff
commit
32f90300c8
|
@ -163,6 +163,7 @@ export interface GetBalanceResponse {
|
|||
useBalance: number
|
||||
/** 借呗总额 */
|
||||
balanceLimit: number
|
||||
ab98User: ab98UserDTO;
|
||||
}
|
||||
|
||||
export interface QyLoginDTO {
|
||||
|
|
|
@ -126,7 +126,7 @@ const handleSubmit = async () => {
|
|||
const { code, data } = await submitApprovalApi(formData.value)
|
||||
|
||||
if (code === 0) {
|
||||
orderStore.getOrders(wxStore.corpid, wxStore.openid, wxStore.qyUserId);
|
||||
orderStore.getOrders(wxStore.corpid, wxStore.openid, wxStore.qyUserId, 0);
|
||||
|
||||
try {
|
||||
await showConfirmDialog({
|
||||
|
|
|
@ -90,6 +90,12 @@ wxStore.refreshBalance();
|
|||
<span>订单列表</span>
|
||||
</div>
|
||||
</van-col>
|
||||
<van-col span="8">
|
||||
<div class="custom-btn" @click="router.push('/rental-list')">
|
||||
<van-icon name="orders-o" size="20px" />
|
||||
<span>我的柜子</span>
|
||||
</div>
|
||||
</van-col>
|
||||
<!-- <van-col span="6">
|
||||
<div v-if="wxStore.isCabinetAdmin" class="custom-btn" @click="router.push('/manage/goods')">
|
||||
<van-icon name="comment-o" size="20px" />
|
||||
|
@ -115,7 +121,6 @@ wxStore.refreshBalance();
|
|||
</div>
|
||||
</van-col>
|
||||
<van-col span="8"></van-col>
|
||||
<van-col span="8"></van-col>
|
||||
</van-row>
|
||||
</div>
|
||||
</template>
|
||||
|
|
|
@ -50,7 +50,7 @@ function backToHome() {
|
|||
}
|
||||
|
||||
watch(() => orderId.value, async (newVal) => {
|
||||
await orderStore.getOrders(wxStore.corpid, wxStore.openid, wxStore.qyUserId)
|
||||
await orderStore.getOrders(wxStore.corpid, wxStore.openid, wxStore.qyUserId, 0)
|
||||
currentOrder.value = orderStore.orders.find(o => o.orderId === newVal)
|
||||
}, { immediate: true })
|
||||
</script>
|
||||
|
|
|
@ -41,7 +41,7 @@ const getStatusText = (status: number) => {
|
|||
<template>
|
||||
<div class="order-list">
|
||||
<!-- 状态切换标签页 -->
|
||||
<van-tabs v-model:active="activeTab" @change="handleTabChange">
|
||||
<van-tabs v-model:active="activeTab" @change="handleTabChange" style="margin-bottom: 8px;">
|
||||
<van-tab title="未退还"></van-tab>
|
||||
<van-tab title="已退还"></van-tab>
|
||||
</van-tabs>
|
||||
|
@ -72,7 +72,7 @@ const getStatusText = (status: number) => {
|
|||
>
|
||||
<template #icon>
|
||||
<van-image
|
||||
:src="goods.goodsInfo.coverImg"
|
||||
:src="goods.goodsInfo?.coverImg"
|
||||
width="80"
|
||||
height="80"
|
||||
class="product-image"
|
||||
|
@ -80,7 +80,7 @@ const getStatusText = (status: number) => {
|
|||
</template>
|
||||
<div class="product-info">
|
||||
<div class="product-name van-ellipsis">
|
||||
{{ goods.goodsInfo.goodsName }}
|
||||
{{ goods.goodsInfo?.goodsName }}
|
||||
</div>
|
||||
<div class="product-meta">
|
||||
<span class="status">状态: {{ getStatusText(order.status) }}</span>
|
||||
|
@ -109,7 +109,7 @@ const getStatusText = (status: number) => {
|
|||
}
|
||||
|
||||
.order-item {
|
||||
margin-bottom: 20px;
|
||||
margin-bottom: 8px;
|
||||
border: 1px solid #eee;
|
||||
border-radius: 8px;
|
||||
overflow: hidden;
|
||||
|
@ -118,7 +118,7 @@ const getStatusText = (status: number) => {
|
|||
.order-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
padding: 10px 15px;
|
||||
padding: 10px 15px 5px 15px;
|
||||
background-color: #f5f5f5;
|
||||
border-bottom: 1px solid #eee;
|
||||
}
|
||||
|
@ -130,7 +130,6 @@ const getStatusText = (status: number) => {
|
|||
.goods-item {
|
||||
display: flex;
|
||||
padding: 10px 0;
|
||||
border-bottom: 1px solid #f5f5f5;
|
||||
}
|
||||
|
||||
goods-item:last-child {
|
||||
|
|
|
@ -97,8 +97,7 @@ async function handleOpenCabinet(item: OrderGoods) {
|
|||
|
||||
<template>
|
||||
<div class="order-detail" v-if="order">
|
||||
<h2>订单详情</h2>
|
||||
|
||||
|
||||
<div class="order-info">
|
||||
<p>订单号: {{ order.orderId }}</p>
|
||||
<p>状态: {{ getStatusText(order.status) }}</p>
|
||||
|
|
|
@ -1,24 +1,6 @@
|
|||
<template>
|
||||
<div v-if="showShopList" class="shop-list">
|
||||
<div class="shop-prompt">
|
||||
<van-cell title="请选择机柜地址:" center />
|
||||
</div>
|
||||
<van-row :gutter="[10, 10]" class="shop-row" justify="start">
|
||||
<van-col v-for="shop in shopList" :key="shop.shopId" span="12" class="shop-col">
|
||||
<div class="shop-item" @click="handleShopSelect(shop.shopId)">
|
||||
<van-image :src="shop.coverImg || `${publicPath}product-image.png`" class="shop-cover-img" fit="cover" />
|
||||
<div class="shop-info">
|
||||
<van-icon name="shop-o" size="20" class="shop-icon" />
|
||||
<div class="shop-name van-ellipsis">{{ shop.shopName }}</div>
|
||||
</div>
|
||||
</div>
|
||||
</van-col>
|
||||
<van-col v-if="shopList.length % 2 === 0" span="12" class="shop-col"></van-col>
|
||||
</van-row>
|
||||
</div>
|
||||
<div v-else class="cabinet-container van-safe-area-bottom">
|
||||
<div class="cabinet-container van-safe-area-bottom">
|
||||
<div class="left-container">
|
||||
<van-button icon="revoke" type="default" class="showShopListBtn" @click="handleBackToShopList">重选地址</van-button>
|
||||
<van-sidebar v-model="activeCabinet" class="cabinet-sidebar" @change="onCabinetChange">
|
||||
<van-sidebar-item v-for="cabinet in cabinetList" :key="cabinet.cabinetId" :title="cabinet.cabinetName" />
|
||||
</van-sidebar>
|
||||
|
@ -37,25 +19,18 @@
|
|||
</template>
|
||||
<div class="product-info">
|
||||
<div class="goods-info">
|
||||
<div v-if="locker.goodsName">
|
||||
<div>
|
||||
<div class="info-row">
|
||||
<div class="locker-number">格口 {{ locker.cellNo }}</div>
|
||||
<div class="goods-price">¥{{ (locker.price || 0).toFixed(2) }}</div>
|
||||
</div>
|
||||
<div class="goods-name">{{ locker.goodsName }}</div>
|
||||
</div>
|
||||
<div v-else>
|
||||
<div class="info-row">
|
||||
<div class="locker-number">格口 {{ locker.cellNo }}</div>
|
||||
<div class="goods-price">¥0.00</div>
|
||||
</div>
|
||||
<div class="goods-name">空闲</div>
|
||||
<div class="goods-name"></div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="button-group">
|
||||
<van-button size="small" plain hairline :loading="openingLockerId === locker.lockerId"
|
||||
@click="handleOpenLocker(locker)">
|
||||
立即开启
|
||||
开启格口
|
||||
</van-button>
|
||||
</div>
|
||||
</div>
|
||||
|
@ -74,9 +49,10 @@ import type { RentingCabinetDetailDTO, CabinetCellEntity } from '@/common/apis/c
|
|||
import { useWxStore } from '@/pinia/stores/wx';
|
||||
import { publicPath } from "@/common/utils/path";
|
||||
import { showDialog, showToast } from 'vant';
|
||||
import { useAb98UserStore } from '@/pinia/stores/ab98-user';
|
||||
|
||||
const wxStore = useWxStore();
|
||||
const { userid: qyUserid, name: qyName, corpid } = storeToRefs(wxStore);
|
||||
const { userid: userid, qyUserId: qyUserId, name: qyName, corpid, ab98User } = storeToRefs(wxStore);
|
||||
|
||||
const activeCabinet = ref(0)
|
||||
const cabinetList = ref<CabinetItem[]>([])
|
||||
|
@ -85,11 +61,6 @@ const openingLockerId = ref<number | null>(null)
|
|||
const showBindGoodsPopup = ref(false)
|
||||
const currentLocker = ref<LockerItem | null>(null)
|
||||
const cabinetData = ref<RentingCabinetDetailDTO[]>([]);
|
||||
// 机柜地址选择相关状态
|
||||
const showShopList = ref(true);
|
||||
const shopList = ref<ShopEntity[]>([]);
|
||||
const shopId = ref<number>(0);
|
||||
const selectedShop = ref<ShopEntity | null>(null);
|
||||
let scrollListener: any[] = [];
|
||||
|
||||
interface CabinetItem {
|
||||
|
@ -111,11 +82,12 @@ interface LockerItem {
|
|||
}
|
||||
|
||||
// 获取用户租用的机柜列表
|
||||
const loadUserRentedCabinetDetail = async (selectedShopId?: number) => {
|
||||
const targetShopId = selectedShopId || shopId.value;
|
||||
if (!targetShopId || !corpid.value || !qyUserid.value) return;
|
||||
const loadUserRentedCabinetDetail = async () => {
|
||||
if (!ab98User.value || !ab98User.value.ab98UserId) {
|
||||
return;
|
||||
}
|
||||
try {
|
||||
const { data } = await getUserRentedCabinetListApi(corpid.value, Number(qyUserid.value));
|
||||
const { data } = await getUserRentedCabinetListApi(corpid.value, ab98User.value.ab98UserId);
|
||||
cabinetData.value = data || [];
|
||||
cabinetList.value = cabinetData.value.map(cabinet => ({
|
||||
cabinetId: cabinet.cabinetId,
|
||||
|
@ -142,7 +114,7 @@ const updateLockerList = (cabinet: RentingCabinetDetailDTO) => {
|
|||
status: cell.isRented ? 1 : 0,
|
||||
statusClass: cell.isRented ? 'occupied' : 'available',
|
||||
// 这里假设商品信息可能在其他字段中,根据实际情况调整
|
||||
goodsName: '已租用商品',
|
||||
goodsName: '',
|
||||
price: cell.cellPrice,
|
||||
coverImg: `${publicPath}img/product-image.svg`
|
||||
}))
|
||||
|
@ -162,7 +134,7 @@ const handleOpenLocker = async (locker: LockerItem) => {
|
|||
// 调用打开柜口接口
|
||||
await openCabinet(cabinetList.value[activeCabinet.value].cabinetId, locker.lockerNumber, {
|
||||
cellId: locker.lockerId,
|
||||
userid: qyUserid.value,
|
||||
userid: userid.value,
|
||||
isInternal: 2,
|
||||
name: qyName.value,
|
||||
mobile: '',
|
||||
|
@ -177,40 +149,7 @@ const handleOpenLocker = async (locker: LockerItem) => {
|
|||
|
||||
// 初始化方法
|
||||
const init = async () => {
|
||||
if (showShopList.value) {
|
||||
await getShopList();
|
||||
} else if (shopId.value) {
|
||||
await loadUserRentedCabinetDetail();
|
||||
}
|
||||
};
|
||||
|
||||
// 获取商店列表
|
||||
const getShopList = async () => {
|
||||
try {
|
||||
const res = await getShopListApi(wxStore.corpid, -1);
|
||||
if (res?.code === 0 && res?.data?.length > 0) {
|
||||
shopList.value = res.data;
|
||||
}
|
||||
} catch (error) {
|
||||
console.error('获取商店列表失败:', error);
|
||||
}
|
||||
};
|
||||
|
||||
// 选择商店
|
||||
const handleShopSelect = (selectedShopId: number) => {
|
||||
const shop = shopList.value.find(s => s.shopId === selectedShopId);
|
||||
if (shop) {
|
||||
selectedShop.value = shop;
|
||||
shopId.value = selectedShopId;
|
||||
}
|
||||
showShopList.value = false;
|
||||
loadUserRentedCabinetDetail(selectedShopId);
|
||||
};
|
||||
|
||||
// 返回商店列表
|
||||
const handleBackToShopList = () => {
|
||||
showShopList.value = true;
|
||||
shopId.value = 0;
|
||||
await loadUserRentedCabinetDetail();
|
||||
};
|
||||
|
||||
onMounted(() => {
|
||||
|
|
|
@ -120,6 +120,9 @@ export const useWxStore = defineStore("wx", () => {
|
|||
if (!userid.value) {
|
||||
userid.value = balanceRes.data.userid;
|
||||
}
|
||||
if (!ab98User.value && balanceRes.data.ab98User) {
|
||||
setAb98User(balanceRes.data.ab98User);
|
||||
}
|
||||
/* if (!corpid.value) {
|
||||
corpid.value = balanceRes.data.corpid;
|
||||
} */
|
||||
|
|
|
@ -73,6 +73,27 @@ export const routes: RouteRecordRaw[] = [
|
|||
component: () => import('@/pages/order/index.vue'),
|
||||
meta: {
|
||||
title: '订单详情',
|
||||
layout: {
|
||||
navBar: {
|
||||
showNavBar: true,
|
||||
showLeftArrow: true
|
||||
}
|
||||
},
|
||||
requiresAuth: true
|
||||
}
|
||||
},
|
||||
{
|
||||
path: '/rental-list',
|
||||
name: 'RentalList',
|
||||
component: () => import('@/pages/rental/index.vue'),
|
||||
meta: {
|
||||
title: '我的柜子',
|
||||
layout: {
|
||||
navBar: {
|
||||
showNavBar: true,
|
||||
showLeftArrow: true
|
||||
}
|
||||
},
|
||||
requiresAuth: true
|
||||
}
|
||||
},
|
||||
|
|
Loading…
Reference in New Issue