329 lines
8.6 KiB
Vue
329 lines
8.6 KiB
Vue
<template>
|
||
<view class="bonus-page">
|
||
<view class="page-hero">
|
||
<AppNavbar title="记录" show-back/>
|
||
<view class="intro-card">
|
||
<view class="card-title">
|
||
<view class="title-bar"></view>
|
||
<text>记录</text>
|
||
</view>
|
||
<!-- <text class="intro-text">展示历史订单记录,按来源拆分提成(药动销、跑店/巡店、药分享、自主填报),保持蓝色系设计。</text>-->
|
||
<!-- <view class="hero-tags">-->
|
||
<!-- <view :class="['chip', { 'chip--active': activeFilter === 0 }]" @tap="toggleFilter(0)">药动销</view>-->
|
||
<!-- <view :class="['chip', { 'chip--active': activeFilter === 4 }]" @tap="toggleFilter(4)">跑店/巡店</view>-->
|
||
<!-- <view :class="['chip', { 'chip--active': activeFilter === 1 }]" @tap="toggleFilter(1)">药分享</view>-->
|
||
<!-- <view :class="['chip', { 'chip--active': activeFilter === 6 }]" @tap="toggleFilter(6)">自主填报</view>-->
|
||
<!-- </view>-->
|
||
</view>
|
||
</view>
|
||
|
||
<!-- <view class="card summary">-->
|
||
<!-- <view class="sum-item">-->
|
||
<!-- <view class="sum-value">¥ {{ summary.movement }}</view>-->
|
||
<!-- <view class="sum-label">药动销提成</view>-->
|
||
<!-- </view>-->
|
||
<!-- <view class="sum-item">-->
|
||
<!-- <view class="sum-value">¥ {{ summary.storeVisit }}</view>-->
|
||
<!-- <view class="sum-label">跑店/巡店提成</view>-->
|
||
<!-- </view>-->
|
||
<!-- <view class="sum-item">-->
|
||
<!-- <view class="sum-value">¥ {{ summary.share }}</view>-->
|
||
<!-- <view class="sum-label">药分享提成</view>-->
|
||
<!-- </view>-->
|
||
<!-- <view class="sum-item">-->
|
||
<!-- <view class="sum-value">¥ {{ summary.selfReport }}</view>-->
|
||
<!-- <view class="sum-label">自主填报提成</view>-->
|
||
<!-- </view>-->
|
||
<!-- </view>-->
|
||
|
||
<!-- <view class="card withdraw-entry">-->
|
||
<!-- <view>-->
|
||
<!-- <view class="withdraw-title">可提现奖金</view>-->
|
||
<!-- <view class="withdraw-amount">¥ {{ user.balance }}</view>-->
|
||
<!-- </view>-->
|
||
<!-- <view class="primary-btn withdraw-btn" @tap="goWithdraw">奖金提现</view>-->
|
||
<!-- </view>-->
|
||
|
||
<view class="card block">
|
||
<view class="section-title">历史收入记录</view>
|
||
<view v-if="loading" class="empty">加载中...</view>
|
||
<view v-else-if="filteredRecords.length === 0" class="empty">暂无记录</view>
|
||
<view v-else class="record" v-for="(item, idx) in filteredRecords" :key="idx">
|
||
<view>
|
||
<view class="record-name">{{ item.title }}</view>
|
||
<!-- <view class="record-meta">{{ item.source }} · 订单号:{{ item.orderNo }}</view>-->
|
||
<view class="record-meta">日期:{{ item.date }}</view>
|
||
</view>
|
||
<!-- <view class="record-amount">+¥{{ item.amount }}</view>-->
|
||
</view>
|
||
</view>
|
||
<Login ref="Login" @done="getUserData"/>
|
||
</view>
|
||
</template>
|
||
|
||
<script>
|
||
import {userBalanceLogListReq} from "@/api/bonus";
|
||
import {getUserInfo} from "@/util/user";
|
||
import {userInfoReq} from "@/api/user";
|
||
import Login from "@/components/Login.vue";
|
||
import AppNavbar from "@/components/AppNavbar.vue";
|
||
|
||
export default {
|
||
components: {Login, AppNavbar},
|
||
data() {
|
||
return {
|
||
summary: {
|
||
movement: '0.00',
|
||
storeVisit: '0.00',
|
||
share: '0.00',
|
||
selfReport: '0.00',
|
||
withdrawable: '0.00'
|
||
},
|
||
records: [],
|
||
loading: false,
|
||
activeFilter: null,
|
||
user: {
|
||
balance: 0
|
||
},
|
||
}
|
||
},
|
||
computed: {
|
||
filteredRecords() {
|
||
if (this.activeFilter === null || this.activeFilter === undefined) return this.records
|
||
return this.records.filter(item => Number(item.scene) === Number(this.activeFilter))
|
||
}
|
||
},
|
||
onShow() {
|
||
if (getUserInfo().token) {
|
||
this.isLoggedIn = true
|
||
this.getUserData()
|
||
this.fetchBalanceLogs()
|
||
}
|
||
},
|
||
methods: {
|
||
async getUserData(){
|
||
const {data} = await userInfoReq()
|
||
this.isLoggedIn = true
|
||
this.user = data
|
||
},
|
||
async fetchBalanceLogs() {
|
||
this.loading = true
|
||
try {
|
||
const {data} = await userBalanceLogListReq({})
|
||
const list = Array.isArray(data) ? data : (data && data.list ? data.list : [])
|
||
this.records = list.map(this.normalizeRecord)
|
||
const movementTotal = this.records
|
||
.filter(item => item.scene === 0)
|
||
.reduce((sum, item) => sum + Number(item.amount || 0), 0)
|
||
const storeVisitTotal = this.records
|
||
.filter(item => item.scene === 4)
|
||
.reduce((sum, item) => sum + Number(item.amount || 0), 0)
|
||
const shareTotal = this.records
|
||
.filter(item => item.scene === 1)
|
||
.reduce((sum, item) => sum + Number(item.amount || 0), 0)
|
||
const selfReportTotal = this.records
|
||
.filter(item => item.scene === 6)
|
||
.reduce((sum, item) => sum + Number(item.amount || 0), 0)
|
||
const withdrawable = movementTotal + storeVisitTotal + shareTotal + selfReportTotal
|
||
this.summary = {
|
||
movement: movementTotal.toFixed(2),
|
||
storeVisit: storeVisitTotal.toFixed(2),
|
||
share: shareTotal.toFixed(2),
|
||
selfReport: selfReportTotal.toFixed(2),
|
||
withdrawable: withdrawable.toFixed(2)
|
||
}
|
||
} catch (err) {
|
||
uni.showToast({
|
||
title: '加载失败',
|
||
icon: 'none'
|
||
})
|
||
} finally {
|
||
this.loading = false
|
||
}
|
||
},
|
||
normalizeRecord(item) {
|
||
const sceneValue = Number(item.scene)
|
||
const source = sceneValue === 0
|
||
? '药动销'
|
||
: (sceneValue === 4 ? '跑店/巡店' : (sceneValue === 1 ? '药分享' : (sceneValue === 6 ? '自主填报' : '其他')))
|
||
const amount = Number(item.amount || item.money || item.changeAmount || 0)
|
||
return {
|
||
scene: sceneValue,
|
||
title: item.title || item.remark || `${source}记录`,
|
||
source,
|
||
orderNo: item.orderNo || item.order_no || item.bizNo || '-',
|
||
date: item.createTime || item.createdAt || item.date || '-',
|
||
amount: amount.toFixed(2)
|
||
}
|
||
},
|
||
toggleFilter(scene) {
|
||
this.activeFilter = this.activeFilter === scene ? null : scene
|
||
},
|
||
goWithdraw() {
|
||
uni.navigateTo({
|
||
url: '/pages/bonus/withdraw'
|
||
})
|
||
}
|
||
}
|
||
}
|
||
</script>
|
||
|
||
<style lang="scss" scoped>
|
||
.bonus-page {
|
||
min-height: 100vh;
|
||
//padding: 0 20rpx 40rpx;
|
||
background: #f5f5f5;
|
||
}
|
||
|
||
.page-hero {
|
||
//padding: 30rpx 6rpx 18rpx;
|
||
background: url('https://yaodongxiao.oss-cn-guangzhou.aliyuncs.com/20260126/462bfa04cf0eff8698884c38b9d17519.png') no-repeat
|
||
top center / 100% auto;
|
||
}
|
||
|
||
.page-navbar {
|
||
padding: 0 6rpx;
|
||
}
|
||
|
||
.intro-card {
|
||
margin: 18rpx 20rpx 0;
|
||
padding: 20rpx 18rpx;
|
||
border-radius: 20rpx;
|
||
background: rgba(255, 255, 255, 0.9);
|
||
box-shadow: 0 10rpx 20rpx rgba(0, 0, 0, 0.08);
|
||
}
|
||
|
||
.card-title {
|
||
display: flex;
|
||
align-items: center;
|
||
gap: 12rpx;
|
||
font-size: 28rpx;
|
||
font-weight: 700;
|
||
color: #1f2937;
|
||
}
|
||
|
||
.title-bar {
|
||
width: 6rpx;
|
||
height: 30rpx;
|
||
border-radius: 999rpx;
|
||
background: #2fc6a7;
|
||
}
|
||
|
||
.intro-text {
|
||
margin-top: 12rpx;
|
||
font-size: 26rpx;
|
||
color: #6b7280;
|
||
line-height: 1.6;
|
||
}
|
||
|
||
.hero-tags {
|
||
display: flex;
|
||
gap: 12rpx;
|
||
margin-top: 12rpx;
|
||
}
|
||
|
||
.chip {
|
||
padding: 6rpx 16rpx;
|
||
border-radius: 999rpx;
|
||
border: 1rpx solid #c7d2fe;
|
||
color: #4f46e5;
|
||
font-size: 22rpx;
|
||
font-weight: 700;
|
||
background: #eef2ff;
|
||
}
|
||
|
||
.chip--active {
|
||
border-color: #2fc6a7;
|
||
color: #2fc6a7;
|
||
background: #e6fffa;
|
||
}
|
||
|
||
.summary {
|
||
display: grid;
|
||
grid-template-columns: repeat(2, 1fr);
|
||
gap: 12rpx;
|
||
margin: 18rpx 20rpx 0;
|
||
}
|
||
|
||
.withdraw-entry {
|
||
margin: 18rpx 20rpx 0;
|
||
display: flex;
|
||
justify-content: space-between;
|
||
align-items: center;
|
||
}
|
||
|
||
.withdraw-title {
|
||
color: var(--text-sub);
|
||
font-size: 24rpx;
|
||
}
|
||
|
||
.withdraw-amount {
|
||
color: var(--brand-primary);
|
||
font-size: 32rpx;
|
||
font-weight: 800;
|
||
margin-top: 4rpx;
|
||
}
|
||
|
||
.withdraw-btn {
|
||
padding: 10rpx 18rpx;
|
||
height: 56rpx;
|
||
font-size: 24rpx;
|
||
}
|
||
|
||
.sum-item {
|
||
background: linear-gradient(135deg, #f0f5ff, #ffffff);
|
||
border-radius: 14rpx;
|
||
padding: 16rpx;
|
||
border: 1rpx solid #e7eef8;
|
||
}
|
||
|
||
.sum-value {
|
||
font-size: 32rpx;
|
||
font-weight: 800;
|
||
color: var(--brand-primary);
|
||
}
|
||
|
||
.sum-label {
|
||
color: var(--text-sub);
|
||
font-size: 24rpx;
|
||
margin-top: 4rpx;
|
||
}
|
||
|
||
.block {
|
||
margin: 18rpx 20rpx 0;
|
||
}
|
||
|
||
.record {
|
||
display: flex;
|
||
justify-content: space-between;
|
||
padding: 12rpx 0;
|
||
border-bottom: 1rpx solid #edf1f7;
|
||
}
|
||
|
||
.record:last-child {
|
||
border-bottom: none;
|
||
}
|
||
|
||
.record-name {
|
||
font-size: 26rpx;
|
||
color: var(--text-main);
|
||
}
|
||
|
||
.record-meta {
|
||
color: var(--text-sub);
|
||
font-size: 24rpx;
|
||
margin-top: 2rpx;
|
||
}
|
||
|
||
.record-amount {
|
||
color: #ff3b30;
|
||
font-weight: 800;
|
||
}
|
||
|
||
.empty {
|
||
color: var(--text-sub);
|
||
text-align: center;
|
||
padding: 16rpx 0;
|
||
}
|
||
</style>
|