feat:save

This commit is contained in:
chenhao 2026-05-18 11:39:48 +08:00
parent e48a3ffcac
commit 88d41de408
68 changed files with 2977 additions and 1955 deletions

View File

@ -1,2 +1,2 @@
VITE_API_URL = "http://m.taigurun.cn" VITE_API_URL = "https://m.taigurun.cn"
VITE_OSS_URL = "http://m.taigurun.cn" VITE_OSS_URL = "https://m.taigurun.cn"

View File

@ -1,2 +1,2 @@
VITE_API_URL = "http://m.taigurun.cn" VITE_API_URL = "https://m.taigurun.cn"
VITE_OSS_URL = "http://m.taigurun.cn" VITE_OSS_URL = "https://m.taigurun.cn"

View File

@ -11,6 +11,7 @@
<body> <body>
<div id="app" v-cloak></div> <div id="app" v-cloak></div>
<script src="/js/echarts.min.js"></script>
<script src="/js/html2canvas.min.js"></script> <script src="/js/html2canvas.min.js"></script>
<script type="module" src="/src/main.js"></script> <script type="module" src="/src/main.js"></script>
<style> <style>

BIN
public/img/b_logo.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 13 KiB

BIN
public/img/buybill.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.7 KiB

BIN
public/img/checked.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.8 KiB

BIN
public/img/copy_b.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 388 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 233 B

After

Width:  |  Height:  |  Size: 350 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.1 MiB

After

Width:  |  Height:  |  Size: 476 KiB

BIN
public/img/gift_bg1.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1024 KiB

BIN
public/img/gift_bg2.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 114 KiB

BIN
public/img/gift_bg3.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 324 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 52 KiB

BIN
public/img/gift_qy.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 18 KiB

BIN
public/img/gift_title.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 37 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 22 KiB

After

Width:  |  Height:  |  Size: 141 KiB

BIN
public/img/op-i1.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.1 KiB

BIN
public/img/op-i2.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 3.0 KiB

BIN
public/img/op-i3.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 12 KiB

BIN
public/img/op-i4.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 12 KiB

BIN
public/img/op-i5.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 12 KiB

BIN
public/img/opera_bg.jpg Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 30 KiB

BIN
public/img/phone.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 521 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 548 B

After

Width:  |  Height:  |  Size: 627 B

1
public/js/echarts.min.js vendored Normal file

File diff suppressed because one or more lines are too long

View File

@ -1,35 +1,3 @@
<template> <template>
<router-view /> <router-view />
<ManagerPopup v-model="managerPopupVisible" />
</template> </template>
<script>
import { ref, watch } from 'vue'
import ManagerPopup from "./components/ManagerPopup.vue";
export default {
name: 'App',
components: { ManagerPopup },
data() {
return {
managerPopupVisible: false
}
},
mounted() {
window.addEventListener('showManagerPopup', this.onShowManagerPopup)
window.addEventListener('closeManagerPopup', this.onCloseManagerPopup)
},
beforeUnmount() {
window.removeEventListener('showManagerPopup', this.onShowManagerPopup)
window.removeEventListener('closeManagerPopup', this.onCloseManagerPopup)
},
methods: {
onShowManagerPopup() {
this.managerPopupVisible = true
},
onCloseManagerPopup() {
this.managerPopupVisible = false
}
}
}
</script>

View File

@ -59,20 +59,21 @@ export default {
if (currentRequestId !== this.requestId) return if (currentRequestId !== this.requestId) return
const data = this.parseData(res) const data = this.parseData(res)
console.log(data); console.log(data);
const safeData = data || []
if (this.page === 1) { if (this.page === 1) {
this.list = data this.list = safeData
} else { } else {
this.list.push(...data) this.list.push(...safeData)
} }
this.page++ this.page++
this.finished = data.length < this.pageSize this.finished = safeData.length < this.pageSize
this.$emit('update:list', this.list) this.$emit('update:list', this.list)
this.$emit('load', this.list) this.$emit('load', this.list)
}) })
.catch(err => { .catch(err => {
if (currentRequestId !== this.requestId) return if (currentRequestId !== this.requestId) return
this.$showFailToast(err.errmsg || '加载失败') this.$showFailToast(err.message || '加载失败')
}) })
.finally(() => { this.loading = false }) .finally(() => { this.loading = false })
}, },
@ -83,13 +84,10 @@ export default {
this.finished = false this.finished = false
this.loading = false this.loading = false
this._skipWatch = true this._skipWatch = true
this._skipNextWatch = true
this.loadMore() this.loadMore()
this.$emit('refresh', this.list) this.$emit('refresh', this.list)
this.$nextTick(() => { // $nextTick
this._skipWatch = false this._skipWatch = false
this._skipNextWatch = false
})
}, },
}, },
} }

View File

@ -1,7 +1,7 @@
<template> <template>
<van-nav-bar fixed :title="$isWechat() ? '' : title || $route.meta.title" :safe-area-inset-top="true" placeholder <!-- $isWechat() ? '' : title || -->
left-arrow left-text="返回" @click-left="back ? back() : $router.back();" <van-nav-bar fixed :title="$route.meta.title" :safe-area-inset-top="true" placeholder left-arrow left-text="返回"
:class="$isWechat() ? 'wechat-nav' : ''"> @click-left="back ? back() : $router.back();" :class="$isWechat() ? 'wechat-nav' : ''">
<template #right> <template #right>
<slot v-if="$slots.right" name="right" /> <slot v-if="$slots.right" name="right" />
<van-icon v-else-if="!hideHome" name="wap-home-o" size="18" @click="$router.replace('/')" /> <van-icon v-else-if="!hideHome" name="wap-home-o" size="18" @click="$router.replace('/')" />

View File

@ -7,14 +7,14 @@
<span>个人管理中心</span> <span>个人管理中心</span>
<van-icon class="r" name="arrow"></van-icon> <van-icon class="r" name="arrow"></van-icon>
</div> </div>
<!-- v-if="c" -->
<div @click="navigateAndClose('Merchant')"> <div @click="navigateAndClose(`Merchant?id=${PermissionsData.id}`)" v-show="PermissionsData.isshop">
<img src="/img/my_u2.png" alt=""> <img src="/img/my_u2.png" alt="">
<span>商家管理中心</span> <span>商家管理中心</span>
<van-icon class="r" name="arrow"></van-icon> <van-icon class="r" name="arrow"></van-icon>
</div> </div>
<div> <div @click="navigateAndClose('Operations')" v-if="PermissionsData.iscenter">
<img src="/img/my_u3.png" alt=""> <img src="/img/my_u3.png" alt="">
<span>运营管理中心</span> <span>运营管理中心</span>
<van-icon class="r" name="arrow"></van-icon> <van-icon class="r" name="arrow"></van-icon>
@ -63,8 +63,12 @@ export default {
showInfo: false, showInfo: false,
saving: false, saving: false,
tempData: {}, tempData: {},
PermissionsData: {},
} }
}, },
mounted() {
this.getPermissions()
},
computed: { computed: {
visible: { visible: {
get() { get() {
@ -82,6 +86,17 @@ export default {
this.$navigate(route) this.$navigate(route)
}) })
}, },
getPermissions() {
this.$get('/v1/client/DUsersClient').then(res => {
this.PermissionsData = {
id: res.data.id,
isshop: res.data.isshop,
iscenter: res.data.col2,
}
// console.log(this.PermissionsData);
}).catch(() => { })
},
loginout() { loginout() {
this.$showConfirmDialog({ this.$showConfirmDialog({
title: "确认退出?", title: "确认退出?",

View File

@ -20,6 +20,7 @@ import "vant/es/notify/style";
import "vant/es/dialog/style"; import "vant/es/dialog/style";
import "vant/es/toast/style"; import "vant/es/toast/style";
import "vant/es/image-preview/style"; import "vant/es/image-preview/style";
import "vant/es/calendar/style";
const app = createApp(App); const app = createApp(App);
@ -222,7 +223,7 @@ app.config.globalProperties.$uploadFiles = (files, uploadUrl) => {
resolve(data); resolve(data);
} }
}).catch(err => { }).catch(err => {
reject({ errmsg: '上传失败' }); reject({ message: '上传失败' });
}); });
}).catch(err => { }).catch(err => {
reject(err); reject(err);
@ -324,6 +325,10 @@ app.config.globalProperties.$del = del;
app.config.globalProperties.$request = request; app.config.globalProperties.$request = request;
app.config.globalProperties.$isLogin = isLogin; app.config.globalProperties.$isLogin = isLogin;
app.config.globalProperties.$formatGMT = formatGMT; app.config.globalProperties.$formatGMT = formatGMT;
app.config.globalProperties.$formatCellphone = (e) => {
if (!e || e.length !== 11) return e;
return e.replace(/(\d{3})\d{4}(\d{4})/, '$1****$2');
};
// ManagerPopup 通过 window 事件触发 // ManagerPopup 通过 window 事件触发
app.config.globalProperties.$showManagerPopup = () => { window.dispatchEvent(new Event('showManagerPopup')) } app.config.globalProperties.$showManagerPopup = () => { window.dispatchEvent(new Event('showManagerPopup')) }

View File

@ -57,7 +57,7 @@ const routes = [
{ {
path: '/Balance', path: '/Balance',
name: 'Balance', name: 'Balance',
component: () => import('./views/User/Balance.vue'), component: () => import('./views/User/Wallet/Balance.vue'),
meta: { meta: {
title: '余额', title: '余额',
} }
@ -65,7 +65,7 @@ const routes = [
{ {
path: '/CV', path: '/CV',
name: 'CV', name: 'CV',
component: () => import('./views/User/CV.vue'), component: () => import('./views/User/Wallet/CV.vue'),
meta: { meta: {
title: '会员卡额度', title: '会员卡额度',
} }
@ -73,7 +73,7 @@ const routes = [
{ {
path: '/Point', path: '/Point',
name: 'Point', name: 'Point',
component: () => import('./views/User/Point.vue'), component: () => import('./views/User/Wallet/Point.vue'),
meta: { meta: {
title: '积分', title: '积分',
} }
@ -81,7 +81,7 @@ const routes = [
{ {
path: '/Allow', path: '/Allow',
name: 'Allow', name: 'Allow',
component: () => import('./views/User/Allow.vue'), component: () => import('./views/User/Wallet/Allow.vue'),
meta: { meta: {
title: '业绩统计', title: '业绩统计',
} }
@ -89,7 +89,7 @@ const routes = [
{ {
path: '/Certificate', path: '/Certificate',
name: 'Certificate', name: 'Certificate',
component: () => import('./views/User/Certificate.vue'), component: () => import('./views/User/Wallet/Certificate.vue'),
meta: { meta: {
title: '礼品券', title: '礼品券',
} }
@ -97,7 +97,7 @@ const routes = [
{ {
path: '/Transfer', path: '/Transfer',
name: 'Transfer', name: 'Transfer',
component: () => import('./views/User/Transfer.vue'), component: () => import('./views/User/Wallet/Transfer.vue'),
meta: { meta: {
title: '互转', title: '互转',
} }
@ -105,7 +105,7 @@ const routes = [
{ {
path: '/CashoutRecord', path: '/CashoutRecord',
name: 'CashoutRecord', name: 'CashoutRecord',
component: () => import('./views/User/CashoutRecord.vue'), component: () => import('./views/Cashout/CashoutRecord.vue'),
meta: { meta: {
title: '提现记录', title: '提现记录',
} }
@ -113,7 +113,7 @@ const routes = [
{ {
path: '/Cashout', path: '/Cashout',
name: 'Cashout', name: 'Cashout',
component: () => import('./views/User/Cashout.vue'), component: () => import('./views/Cashout/Cashout.vue'),
meta: { meta: {
title: '提现', title: '提现',
} }
@ -145,7 +145,7 @@ const routes = [
{ {
path: '/CashoutAccount', path: '/CashoutAccount',
name: 'CashoutAccount', name: 'CashoutAccount',
component: () => import('./views/User/CashoutAccount.vue'), component: () => import('./views/Cashout/CashoutAccount.vue'),
meta: { title: '提现账号' } meta: { title: '提现账号' }
}, },
{ {
@ -163,7 +163,7 @@ const routes = [
{ {
path: '/TradeList', path: '/TradeList',
name: 'TradeList', name: 'TradeList',
component: () => import('./views/Trade/NTradeList.vue'), component: () => import('./views/Trade/TradeList.vue'),
meta: { title: '订单列表' } meta: { title: '订单列表' }
}, },
{ {
@ -214,6 +214,18 @@ const routes = [
component: () => import('./views/Goods/Category.vue'), component: () => import('./views/Goods/Category.vue'),
meta: { title: '全部分类' } meta: { title: '全部分类' }
}, },
{
path: '/Operations',
name: 'Operations',
component: () => import('./views/Operations/Operations.vue'),
meta: { title: '运营中心' }
},
{
path: '/CertificateRecord',
name: 'CertificateRecord',
component: () => import('./views/User/Wallet/CertificateRecord.vue'),
meta: { title: '核销记录' }
},
{ {
path: '/Merchant', path: '/Merchant',
name: 'Merchant', name: 'Merchant',
@ -226,6 +238,12 @@ const routes = [
component: () => import('./views/Merchant/MerchantIncome.vue'), component: () => import('./views/Merchant/MerchantIncome.vue'),
meta: { title: '营业收入' } meta: { title: '营业收入' }
}, },
{
path: '/MerchantCashout',
name: 'MerchantCashout',
component: () => import('./views/Merchant/MerchantCashout.vue'),
meta: { title: '提现记录' }
},
{ {
path: '/Statistics', path: '/Statistics',
name: 'Statistics', name: 'Statistics',
@ -245,10 +263,22 @@ const routes = [
meta: { title: '订单详情' } meta: { title: '订单详情' }
}, },
{ {
path: '/MerchantProduct', path: '/MerchantIntroduction',
name: 'MerchantProduct', name: 'MerchantIntroduction',
component: () => import('./views/Merchant/MerchantProduct.vue'), component: () => import('./views/Merchant/MerchantIntroduction.vue'),
meta: { title: '商家产品' } meta: { title: '商家资料' }
},
{
path: '/Checkout',
name: 'Checkout',
component: () => import('./views/User/Checkout/Checkout.vue'),
meta: { title: '买单' }
},
{
path: '/CheckoutTrade',
name: 'CheckoutTrade',
component: () => import('./views/User/Checkout/CheckoutTrade.vue'),
meta: { title: '订单详情' }
}, },
{ {
path: '/Refresh', path: '/Refresh',

File diff suppressed because it is too large Load Diff

View File

@ -609,21 +609,27 @@ img {
} }
.transfer { .transfer {
.b_l_w; .f5;
padding: 4vw;
>div {
.b_l_w;
}
.top { .top {
.box; .box;
.box-tb; .box-tb;
background: #fff;
border-radius: 2vw;
padding: 3.33vw; padding: 3.33vw;
border-bottom: 2vw solid #f5f5f5; border-bottom: 2vw solid #f5f5f5;
input { .tit {
padding: 0 1.2vw;
font-size: 3.73vw; font-size: 3.73vw;
font-weight: bold;
color: #1b1b1b;
margin-bottom: 3.33vw;
}
input {
// padding: 0 1.2vw;
font-size: 4vw;
color: #222; color: #222;
height: 10vw; height: 10vw;
line-height: 10vw; line-height: 10vw;
@ -693,15 +699,21 @@ img {
.quota_box { .quota_box {
padding: 5.07vw 4.67vw 0; padding: 5.07vw 4.67vw 0;
background: #fff;
border-radius: 2vw;
// border-bottom: 2vw solid #f5f5f5; // border-bottom: 2vw solid #f5f5f5;
padding-bottom: 1.2vw; padding-bottom: 1.2vw;
.title { .title {
font-size: 4vw; b {
font-size: 4vw;
}
.box;
} }
input { input {
padding: 0 1.2vw; // padding: 0 1.2vw;
font-size: 6.13vw; font-size: 6.13vw;
color: #222; color: #222;
height: 15vw; height: 15vw;
@ -711,6 +723,21 @@ img {
border-bottom: solid 1px #f5f5f580; border-bottom: solid 1px #f5f5f580;
} }
.nums {
font-size: 6.67vw;
color: #1f1f1f;
margin-top: 5.2vw;
display: block;
}
hr {
border: none;
height: 1px;
width: 100%;
background: #f5f5f580;
margin: 2vw;
}
input::placeholder { input::placeholder {
font-size: 4.67vw; font-size: 4.67vw;
color: #999; color: #999;
@ -783,230 +810,162 @@ img {
} }
.list { .list {
.b_l_w; padding: 4.8vw 3.73vw;
.b_k; background-color: #ffffff;
border-radius: 2vw; border-radius: 1.6vw;
padding: 4vw;
margin-bottom: 4vw; margin-bottom: 4vw;
position: relative;
>div { .merchant_info {
.b_l_w;
}
.t {
.box;
height: 13.333vw;
img {
border-radius: 1vw;
width: 13.333vw;
height: 13.333vw;
margin-right: 3.333vw;
}
>div {
.box;
.box-pack-center;
.box-tb;
.name {
margin-bottom: 1.5vw;
b {
font-size: 3.867vw;
color: #1b1b1b;
margin-right: 3.2vw;
}
span {
color: #7d7d7d;
}
}
.label {
.box;
.box-align-center;
color: #434343;
span {
width: 1px;
height: 3.6vw;
background: #434343;
margin: 0 3.2vw;
}
}
}
}
.code {
.box; .box;
.box-align-center; .box-align-center;
height: 4vw;
margin-bottom: 2vw;
&::before { .icon {
content: ''; width: 10.67vw;
position: absolute; height: 10.67vw;
left: 0; background-color: #cccccc;
width: 1vw; border-radius: 1.6vw;
height: 4vw; margin-right: 4vw;
background: #333;
} }
img { .inf {
height: 3vw; .box;
margin-left: 2vw; .box-tb;
} .box-pack-between;
} height: 10.67vw;
width: 100%;
.content { span {
width: 100%; font-size: 3.47vw;
height: 22vw; color: #303030;
overflow-x: scroll;
overflow-y: hidden;
white-space: nowrap;
padding-right: 15vw;
margin: 2vw 0;
.l {
display: inline-block;
width: 20vw;
.center;
margin-right: 2vw;
img {
width: 20vw;
height: 15vw;
object-fit: contain;
} }
p { p {
margin: 1vw 0; font-size: 3.47vw;
width: 100%; color: #333333;
white-space: nowrap; }
overflow: hidden;
text-overflow: ellipsis; >div {
display: block; .box;
.box-align-center;
.dr {
.r;
font-size: 3.2vw;
color: #ea3e23;
}
} }
} }
} }
._info { .detail_box {
width: 100%;
.box; .box;
margin: 1vw 0 3vw; .box-tb;
padding: 3vw 0;
border-top: 1px solid #f5f5f5;
border-bottom: 1px solid #f5f5f5;
>img { >div {
width: 22vw; .box;
height: 22vw; margin-top: 2.53vw;
border-radius: 1.333vw;
margin-right: 3.333vw; span {
.box;
.box-align-center;
img {
width: 3.2vw;
height: 3.2vw;
margin-left: 1.2vw;
}
}
}
}
.order_box {
.box;
.box-align-center;
padding-bottom: 2.53vw;
border-bottom: 1px solid #f5f5f580;
img {
width: 3.2vw;
height: 3.2vw;
margin-left: 1.2vw;
}
}
.goods_box {
.box;
margin-top: 2.8vw;
img {
width: 21.33vw;
height: 21.33vw;
margin-right: 4vw;
} }
._c { .goods_info {
.w;
.box; .box;
.box-tb; .box-tb;
.box-pack-around; .box-pack-around;
width: 100%;
height: 21.33vw;
._name {
>div {
.box; .box;
.box-align-center; .box-align-center;
font-size: 3.467vw;
line-height: 4.8vw;
div {
padding: 0 1vw;
height: 4vw;
line-height: 4vw;
.bs;
border-radius: 1vw;
margin: -.4vw 2vw 0 0;
white-space: nowrap;
font-size: 2.8vw;
}
.n1 {
background: rgb(49, 128, 247);
}
.n2 {
background: red;
}
.n3 {
background: #f7ba31;
}
span {
.text-hide(1);
}
} }
._spec { .tit {
.box; font-size: 3.47vw;
.box-pack-between; color: #303030;
color: #999; .text-hide(1);
span {
max-width: 50vw;
}
}
._price {
.box;
.box-pack-between;
span {
color: #333333;
}
b {
color: #ca2904;
font-size: 4vw;
span {
font-size: 2.8vw;
color: #ca2904;
}
}
} }
} }
.spec {
color: #999999;
p {
.r;
color: #999999;
}
}
.concession {
font-size: 3.47vw;
color: #333333;
p {
.r;
font-size: 3.2vw;
color: #ea3e23;
}
}
} }
.price { .price {
position: absolute;
right: 0;
height: 22vw;
background: rgba(255, 255, 255, .7);
.box; .box;
.box-tb;
.box-align-center; .box-align-center;
.box-pack-center; .box-pack-end;
padding: 0 3.333vw; margin-top: 2.2vw;
width: 100%;
color: #333333;
border-bottom: 1px solid #f5f5f580;
padding-bottom: 2.4vw;
b { span {
font-size: 3.467vw; color: #ca2904;
}
p { b {
color: #999; font-size: 4vw;
}
} }
} }
.state { .state_box {
height: 8vw;
.box; .box;
.box-align-center; .box-align-center;
margin-top: 3.33vw;
b {
font-size: 3.467vw;
}
.b0 { .b0 {
color: #ea3e23; color: #ea3e23;
@ -1016,10 +975,6 @@ img {
color: #2e9940; color: #2e9940;
} }
.b2 {
color: #e54545;
}
.b3 { .b3 {
color: #e57042; color: #e57042;
} }
@ -1028,31 +983,16 @@ img {
color: #333333; color: #333333;
} }
.btn { .btn_box {
.r; .r;
.box;
a { button {
.center; border: none;
font-size: 3.467vw; height: 6.93vw;
height: 7vw; padding: 0 2.4vw;
line-height: 7vw; margin-left: 2.4vw;
border-radius: 1vw; background-color: #efefef;
margin-left: 3.333vw; border-radius: 1.33vw;
padding: 0 2vw;
color: #fff;
}
.a0 {
background: #f00;
}
.a1 {
background: #000;
}
.a2 {
background: #53CCE0;
} }
} }
} }

View File

@ -1,96 +0,0 @@
const tt = (e) => {
return new Promise((resolve, reject) => {
setTimeout(() => {
resolve({ timeout: e });
}, e);
});
};
const api = {
get(url, data, timeout = 60000) {
return new Promise((resolve, reject) => {
const controller = new AbortController();
const { signal } = controller;
const param = Object.keys(data).map(x => `${x}=${encodeURIComponent(data[x])}`).join('&');
Promise.race([tt(timeout), fetch(`${import.meta.env.VITE_API_URL}${url}?${param}`, {
headers: {
'token': localStorage.getItem('token') || '',
},
signal: signal,
})]).then(rep => {
if (rep.timeout) {
controller.abort();
reject({ errcode: -1, errmsg: '网络超时' });
}
else if (rep.status == 404)
reject({ errcode: -1, errmsg: '接口不存在' });
rep.json().then(data => {
if (data.errcode) {
if ([41001, 40001, 40002].includes(data.errcode)) {
localStorage.removeItem('token');
location.replace('#/Login');
location.reload();
}
reject(data);
}
else
resolve(data.data);
}).catch(err => {
reject({ errcode: -1, errmsg: '网络异常' });
});
}).catch(err => {
reject({ errcode: -1, errmsg: '网络异常' });
});
});
},
post(url, data, index, size, timeout = 60000) {
return new Promise((resolve, reject) => {
const controller = new AbortController();
const { signal } = controller;
const postData = {
data: data,
ts: new Date() - 0,
};
if (index)
postData.PageIndex = index;
if (size)
postData.PageSize = size;
Promise.race([tt(timeout), fetch(`${import.meta.env.VITE_API_URL}${url}`, {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'Accept': 'application/json',
'token': localStorage.getItem('token') || '',
},
body: JSON.stringify(postData),
signal: signal,
})]).then(rep => {
if (rep.timeout) {
controller.abort();
reject({ errcode: -1, errmsg: '网络超时' });
}
else if (rep.status == 404)
reject({ errcode: -1, errmsg: '接口不存在' });
rep.json().then(data => {
if (data.errcode) {
if ([41001, 40001, 40002].includes(data.errcode)) {
localStorage.removeItem('token');
location.replace('#/Login');
location.reload();
}
reject(data);
}
else
resolve(data.data);
}).catch(err => {
reject({ errcode: -1, errmsg: '网络异常' });
});
}).catch(err => {
reject({ errcode: -1, errmsg: '网络异常' });
});
});
},
}
export default api;

1
src/utils/echarts.min.js vendored Normal file

File diff suppressed because one or more lines are too long

View File

@ -205,7 +205,10 @@ export default {
} }
}, 1000) }, 1000)
this.$post('/v1/client/AuthClient/sendcode', this.formData.Phone).then(data => { this.$post('/v1/client/AuthClient/sendcode', {
"purpose": this.isReg ? "register" : "login",
"cellphone": this.formData.Phone
}).then(data => {
if (data.status === 200) { if (data.status === 200) {
this.$showSuccessToast?.('发送成功') this.$showSuccessToast?.('发送成功')
this.smsCode = data.data // this.smsCode = data.data //

View File

@ -17,9 +17,9 @@
</div> </div>
<div class="input_box"> <div class="input_box">
<input type="phone" maxlength="11" placeholder="请输入账号(手机号)" v-model="data.UserName" <input type="phone" maxlength="11" placeholder="请输入账号(手机号)" v-model="data.cellphone"
onblur="window.scrollTo(0, 0);" /> onblur="window.scrollTo(0, 0);" />
<van-icon @click="data.UserName = ''" name="cross" size="5vw"></van-icon> <van-icon @click="data.cellphone = ''" name="cross" size="5vw"></van-icon>
</div> </div>
</div> </div>
@ -30,7 +30,7 @@
</div> </div>
<div class="input_box"> <div class="input_box">
<input type="text" placeholder="请输入验证码" v-model="data.SmsCode" maxlength="6" <input type="text" placeholder="请输入验证码" v-model="data.code" maxlength="6"
onblur="window.scrollTo(0, 0);" /> onblur="window.scrollTo(0, 0);" />
<van-button class="hqyzm" @click="sendCode" :disabled="isSend"> <van-button class="hqyzm" @click="sendCode" :disabled="isSend">
{{ isSend ? `已发送(${remainTime}s)` : "获取验证码" }} {{ isSend ? `已发送(${remainTime}s)` : "获取验证码" }}
@ -45,7 +45,7 @@
</div> </div>
<div class="input_box"> <div class="input_box">
<input :type="show1 ? 'text' : 'password'" placeholder="请输入新的登录密码" v-model="data.Password" <input :type="show1 ? 'text' : 'password'" placeholder="请输入新的登录密码" v-model="data.password"
@keydown.enter="login" onblur="window.scrollTo(0, 0);" /> @keydown.enter="login" onblur="window.scrollTo(0, 0);" />
<van-icon @click="show1 = true" name="eye-o" size="5vw" v-if="!show1"></van-icon> <van-icon @click="show1 = true" name="eye-o" size="5vw" v-if="!show1"></van-icon>
<van-icon @click="show1 = false" name="closed-eye" size="5vw" v-else></van-icon> <van-icon @click="show1 = false" name="closed-eye" size="5vw" v-else></van-icon>
@ -103,18 +103,18 @@ export default {
return true; return true;
}, },
reset() { reset() {
if (!this.valid(this.data.UserName, "请输入账号")) if (!this.valid(this.data.cellphone, "请输入账号"))
return; return;
// if (!this.valid(this.data.Phone, "")) // if (!this.valid(this.data.Phone, ""))
// return; // return;
if (!this.valid(this.data.SmsCode, '请输入验证码')) if (!this.valid(this.data.code, '请输入验证码'))
return; return;
if (!this.valid(this.data.Password, '请输入密码')) if (!this.valid(this.data.password, '请输入密码'))
return; return;
if (!this.valid(this.data.RePassword, '再输入确认密码')) if (!this.valid(this.data.RePassword, '再输入确认密码'))
return; return;
if (this.data.Password != this.data.RePassword) { if (this.data.password != this.data.RePassword) {
this.$showFailToast("两次密码输入不一致"); this.$showFailToast("两次密码输入不一致");
this.inputError.password = true; this.inputError.password = true;
return; return;
@ -123,7 +123,7 @@ export default {
this.inputError.password = false; this.inputError.password = false;
} }
this.$post('Common/ResetPassword', this.data).then(res => { this.$post('/v1/client/AuthClient/findpwd', this.data).then(res => {
this.$showDialog({ this.$showDialog({
title: '密码重置成功!', title: '密码重置成功!',
message: '点击确认登录中心重新登录', message: '点击确认登录中心重新登录',
@ -134,10 +134,12 @@ export default {
}); });
}).catch(err => { }).catch(err => {
this.$showFailToast(err.errmsg); this.$showFailToast(err.message);
}); });
}, },
sendCode() { sendCode() {
if (this.isSend) return;
// if ( // if (
// !this.data.Phone || // !this.data.Phone ||
// !/^1(3|4|5|6|7|8|9)\d{9}$/.test(this.data.Phone) // !/^1(3|4|5|6|7|8|9)\d{9}$/.test(this.data.Phone)
@ -148,7 +150,10 @@ export default {
// }); // });
// return; // return;
// } // }
this.$post('/v1/client/AuthClient/change-password', { Key: this.data.UserName }) this.$post('/v1/client/AuthClient/sendcode', {
"purpose": "findpwd",
"cellphone": this.data.cellphone
})
.then((data) => { .then((data) => {
this.$showSuccessToast('发送成功'); this.$showSuccessToast('发送成功');
this.isSend = true; this.isSend = true;
@ -162,7 +167,7 @@ export default {
}, 1000); }, 1000);
}) })
.catch((err) => { .catch((err) => {
this.$showFailToast(err.errmsg); this.$showFailToast(err.message);
}); });
}, },
} }

View File

@ -7,9 +7,9 @@
<span class="title">提现账户</span> <span class="title">提现账户</span>
<div class="account"> <div class="account">
<div v-if="card" class="card"> <div v-if="card" class="card">
<img :src="card.bankid == 91 ? '/img/aliicon.png' : '/img/bankcardicon.png'" height="24" <img :src="card.bankspname === '支付宝' ? '/img/aliicon.png' : '/img/bankcardicon.png'"
width="24" style="object-fit: cover;" /> height="24" width="24" style="object-fit: cover;" />
<span class="code">{{ card.realname }} {{ card.bankcellphone }}</span> <span class="code">{{ card.bankcardnumber }}</span>
</div> </div>
<span v-else class="card">请选择到账账户</span> <span v-else class="card">请选择到账账户</span>
</div> </div>
@ -41,13 +41,12 @@
<BaseList class="b_l_w" ref="BaseList" url="/v1/client/DUserbankcardsClient" <BaseList class="b_l_w" ref="BaseList" url="/v1/client/DUserbankcardsClient"
:parseData="res => res.data"> :parseData="res => res.data">
<template v-slot="{ item }"> <template v-slot="{ item }">
<van-cell class="cashout-card" is-link <van-cell class="cashout-card" is-link @click="selectCard(item)">
@click="selectCard(item)">
<template #title> <template #title>
<div class="card"> <div class="card">
<img :src="item.bankid == 91 ? '/img/aliicon.png' : '/img/bankcardicon.png'" <img :src="item.bankspname === '支付宝' ? '/img/aliicon.png' : '/img/bankcardicon.png'"
height="30" width="30" style="object-fit: cover;" /> height="30" width="30" style="object-fit: cover;" />
<span class="code">{{ item.realname }} {{ item.bankcellphone }}</span> <span class="code">{{ item.bankcardnumber }}</span>
</div> </div>
</template> </template>
</van-cell> </van-cell>
@ -87,7 +86,7 @@ export default {
this.$get('/v1/client/DUsersClient').then(data => { this.$get('/v1/client/DUsersClient').then(data => {
this.wallet.Balance = data.data.zijin; this.wallet.Balance = data.data.zijin;
}).catch(err => { }).catch(err => {
this.$showFailToast(err.errmsg); this.$showFailToast(err.message);
}); });
}, },
selectCard(item) { selectCard(item) {
@ -116,7 +115,7 @@ export default {
this.$showSuccessToast('提交成功'); this.$showSuccessToast('提交成功');
this.$router.replace('/CashoutRecord'); this.$router.replace('/CashoutRecord');
}).catch(err => { }).catch(err => {
this.$showFailToast(err.errmsg); this.$showFailToast(err.message);
}); });
}).catch(() => { }); }).catch(() => { });
}, },

View File

@ -8,10 +8,10 @@
<van-cell> <van-cell>
<template #title> <template #title>
<div class="item"> <div class="item">
<img :src="i.bankid === 91 ? '/img/aliicon.png' : '/img/bankcardicon.png'" alt=""> <img :src="i.bankspname === '支付宝' ? '/img/aliicon.png' : '/img/bankcardicon.png'" alt="">
<div> <div>
<span> <span>
{{ i.bankid === 91 ? '支付宝账号' : '' }}{{ i.bankcellphone }} {{ i.bankspname === '支付宝' ? '支付宝账号' : i.bankspname }}{{ i.bankcardnumber }}
</span> </span>
<p> <p>
2小时内到账 2小时内到账
@ -55,9 +55,9 @@
<div class="bankcard-edit"> <div class="bankcard-edit">
<van-form @submit="save" label-align="top"> <van-form @submit="save" label-align="top">
<van-cell-group inset> <van-cell-group inset>
<van-field v-model="tempData.Realname" label="真实姓名" placeholder="请输入支付宝账号绑定真实姓名" <van-field v-model="tempData.realname" label="真实姓名" placeholder="请输入支付宝账号绑定真实姓名"
:rules="[{ required: true, message: '请填写真实姓名' }]" clearable required /> :rules="[{ required: true, message: '请填写真实姓名' }]" clearable required />
<van-field v-model="tempData.Bankcellphone" label="支付宝账号" placeholder="请输入支付宝账号" <van-field v-model="tempData.bankcellphone" label="支付宝账号" placeholder="请输入支付宝账号"
:rules="[{ required: true, message: '请填写支付宝账号' }]" clearable required /> :rules="[{ required: true, message: '请填写支付宝账号' }]" clearable required />
<div class="w" style="position: fixed;left:0;bottom: 0;padding: 3.333vw;border-top:1px solid #f5f5f5"> <div class="w" style="position: fixed;left:0;bottom: 0;padding: 3.333vw;border-top:1px solid #f5f5f5">
<van-button color="#ea3e23" block round style="width: 100%" type="primary" native-type="save" <van-button color="#ea3e23" block round style="width: 100%" type="primary" native-type="save"
@ -133,6 +133,17 @@ export default {
name: 'CashoutAccount', name: 'CashoutAccount',
mounted() { mounted() {
this.init(); this.init();
this.getBankId()
},
watch: {
'tempData.bankname': function (newVal) {
if (newVal && this.bankidGroup.length) {
const bank = this.bankidGroup.find(item => item.name.includes(newVal) || newVal.includes(item.name))
if (bank) {
this.tempData.bankid = bank.id
}
}
}
}, },
data() { data() {
return { return {
@ -149,6 +160,7 @@ export default {
maxDate: new Date('2099/12/31'), maxDate: new Date('2099/12/31'),
regionName: '', regionName: '',
region: '', region: '',
bankidGroup: {},
areaList: useCascaderAreaData(), areaList: useCascaderAreaData(),
defaultProps: { defaultProps: {
text: 'text', text: 'text',
@ -162,12 +174,17 @@ export default {
this.$get('/v1/client/DUserbankcardsClient').then(data => { this.$get('/v1/client/DUserbankcardsClient').then(data => {
this.data = data.data; this.data = data.data;
}).catch(err => { }).catch(err => {
this.$showFailToast(err.errmsg); this.$showFailToast(err.message);
}); });
}, },
formatter(value) { formatter(value) {
return value.replace(/\s/g, ''); return value.replace(/\s/g, '');
}, },
getBankId() {
this.$get('/v1/client/DBanksClient').then(res => {
this.bankidGroup = res.data;
})
},
onChange({ selectedOptions }) { onChange({ selectedOptions }) {
this.tempData.provid = selectedOptions[0]?.value || ''; this.tempData.provid = selectedOptions[0]?.value || '';
}, },
@ -188,14 +205,14 @@ export default {
}, },
save() { save() {
this.saving = true; this.saving = true;
this.$post('/v1/client/DUserbankcardsClient', { ...this.tempData, Bankid: 91 }).then(data => { this.$post('/v1/client/DUserbankcardsClient', { ...this.tempData, bankid: 91 }).then(data => {
this.$showSuccessToast('添加成功'); this.$showSuccessToast('添加成功');
this.tempData = {}; this.tempData = {};
// this.$refs.BaseList.refresh(); // this.$refs.BaseList.refresh();
this.showAddAliPayPopup = false; this.showAddAliPayPopup = false;
this.init(); this.init();
}).catch(err => { }).catch(err => {
this.$showFailToast(err.errmsg); this.$showFailToast(err.message);
}).finally(() => { }).finally(() => {
this.saving = false; this.saving = false;
}); });
@ -213,17 +230,17 @@ export default {
this.saving = true; this.saving = true;
const params = { const params = {
realname: this.tempData.realname, realname: this.tempData.realname,
idnumber: this.tempData.idnumber, certno: this.tempData.idnumber,
bankid: this.tempData.bankid || 0, bankid: this.tempData.bankid || 0,
bankname: this.tempData.bankname || '', bankname: this.tempData.bankname || '',
bankcardnumber: this.tempData.bankcardnumber, bankcardnumber: this.tempData.bankcardnumber,
bankcellphone: this.tempData.bankcellphone, bankcellphone: this.tempData.bankcellphone,
sort: 0, sort: 0,
certtype: this.tempData.certtype || '', certtype: '身份证',
certvaliditytype: this.checked === 1 || '', certvaliditytype: this.checked === 1 ? 1 : 0,
certbegindate: this.tempData.certbegindate ? this.tempData.certbegindate.replaceAll('-', '') : '', certbegindate: this.tempData.certbegindate ? this.tempData.certbegindate.replaceAll('-', '') : '',
certenddate: this.checked === 1 ? '' : (this.tempData.certenddate ? this.tempData.certenddate.replaceAll('-', '') : ''), certenddate: this.checked === 1 ? '' : (this.tempData.certenddate ? this.tempData.certenddate.replaceAll('-', '') : ''),
cardtype: this.tempData.cardtype || '', cardtype: 1,
provid: this.tempData.provid || '', provid: this.tempData.provid || '',
areaid: this.tempData.areaid || '' areaid: this.tempData.areaid || ''
}; };
@ -234,7 +251,7 @@ export default {
this.init(); this.init();
this.showAddPopup = false; this.showAddPopup = false;
}).catch(err => { }).catch(err => {
this.$showFailToast(err.errmsg); this.$showFailToast(err.message);
}).finally(() => { }).finally(() => {
this.saving = false; this.saving = false;
}); });
@ -244,7 +261,7 @@ export default {
this.$showSuccessToast('删除成功'); this.$showSuccessToast('删除成功');
this.init(); this.init();
}).catch(err => { }).catch(err => {
this.$showFailToast(err.errmsg); this.$showFailToast(err.message);
}); });
}, },
} }

View File

@ -1,11 +1,12 @@
<template> <template>
<BasePage> <BasePage>
<ManagerPopup v-model="managerPopupVisible" />
<div class="merchant"> <div class="merchant">
<div class="shopinfo"> <div class="shopinfo">
<img class="tx" :src="$file(data.MerchantAvatar)"> <img class="tx" :src="$file(data.shopimg)">
<div class="info"> <div class="info">
<b>{{ data.MerchantName }}</b> <b>{{ truncatedShopname }}</b>
<p>账号{{ data.MerchantPhone }}</p> <p>账号{{ data.shopphone }}</p>
</div> </div>
<div class="service-box" @click="$showManagerPopup()"> <div class="service-box" @click="$showManagerPopup()">
@ -20,9 +21,10 @@
</span> </span>
<div class="line"> <div class="line">
<b @click="$navigate('MerchantIncome')"> <b @click="$navigate('MerchantIncome')">
1020.00 {{ data.shangjiashouru?.toFixed(2) }}
</b> </b>
<div> <!-- v-if="data.Income" -->
<div @click="$navigate('MerchantCashout')">
<span>提现中金额 <span>提现中金额
</span> </span>
<p>1000.00</p> <p>1000.00</p>
@ -34,13 +36,13 @@
<span> <span>
可用余额<van-icon name="arrow"></van-icon> 可用余额<van-icon name="arrow"></van-icon>
</span> </span>
<b>{{ data.Income?.toFixed(2) }}</b> <b>{{ data.keyongyue?.toFixed(2) }}</b>
</div> </div>
<div class="ll" @click="$navigate('CV')"> <div class="ll" @click="$navigate('CV')">
<span> <span>
会员卡额度<van-icon name="arrow"></van-icon> 会员卡额度<van-icon name="arrow"></van-icon>
</span> </span>
<b>{{ data.Point?.toFixed(2) }}</b> <b>{{ data.huiyuanka?.toFixed(2) }}</b>
</div> </div>
</div> </div>
</div> </div>
@ -82,7 +84,7 @@
<img src="/img/ft_i2.png" alt=""> <img src="/img/ft_i2.png" alt="">
</div> </div>
<div class="ft3"> <div class="ft3" @click="$navigate('MerchantIntroduction')">
<span>商家资料</span> <span>商家资料</span>
<img src="/img/ft_i3.png" alt=""> <img src="/img/ft_i3.png" alt="">
</div> </div>
@ -94,7 +96,7 @@
</div> </div>
<div class="box line"> <div class="box line">
<span>截止{{ data.endTimes }}</span> <span>截止{{ data.endTimes }}</span>
<p class="refresh" @click="init">刷新</p> <p class="refresh" @click="getCount">刷新</p>
<p class="cou r" @click="$navigate('Statistics')">统计<van-icon name="arrow"></van-icon></p> <p class="cou r" @click="$navigate('Statistics')">统计<van-icon name="arrow"></van-icon></p>
</div> </div>
@ -103,32 +105,32 @@
<span> <span>
今日营业额 今日营业额
</span> </span>
<b>{{ data.TodayAmount?.toFixed(2) }}</b> <b>{{ countData.todayyingyee?.toFixed(2) }}</b>
<p>昨日<span>{{ data.YesterdayAmount?.toFixed(2) }}</span></p> <p>昨日<span>{{ countData.yesterdayyingyee?.toFixed(2) }}</span></p>
</div> </div>
<div class="item"> <div class="item">
<span> <span>
今日应收 今日应收
</span> </span>
<b>{{ data.TodayDeduct?.toFixed(2) }}</b> <b>{{ countData.todayyingshou?.toFixed(2) }}</b>
<p>昨日<span>{{ data.YesterdayDeduct?.toFixed(2) }}</span></p> <p>昨日<span>{{ countData.yesterdayingshou?.toFixed(2) }}</span></p>
</div> </div>
<div class="item"> <div class="item">
<span> <span>
今日订单数 今日订单数
</span> </span>
<b>{{ data.TodayQty }}</b> <b>{{ countData.todaydingdanshu }}</b>
<p>昨日<span>{{ data.YesterdayQty }}</span></p> <p>昨日<span>{{ countData.yesterdaydingdanshu }}</span></p>
</div> </div>
<div class="item"> <div class="item">
<span> <span>
今日惠利金额 今日惠利金额
</span> </span>
<b>{{ data.MonthIncome?.toFixed(2) }}</b> <b>{{ countData.todayyouhui?.toFixed(2) }}</b>
<p>昨日<span>{{ data.PrevMonthIncome?.toFixed(2) }}</span></p> <p>昨日<span>{{ countData.yesterdayyouhui?.toFixed(2) }}</span></p>
</div> </div>
</div> </div>
</div> </div>
@ -141,10 +143,10 @@
<div class="paycode-original" ref="paycodeOriginal" v-show="!paycodeImg"> <div class="paycode-original" ref="paycodeOriginal" v-show="!paycodeImg">
<img src="/img/paycode.jpg" alt="" style="width: 100%; display: block;"> <img src="/img/paycode.jpg" alt="" style="width: 100%; display: block;">
<div class="info"> <div class="info">
<img :src="$file(data.MerchantAvatar)" alt="" style="border-radius: 50%;"> <img :src="$file(data.shopimg)" alt="" style="border-radius: 50%;">
</div> </div>
<div class="name"> <div class="name">
<span>{{ data.MerchantName }}</span> <span>{{ data.shopname }}</span>
</div> </div>
<div class="code"> <div class="code">
<vue-qr v-if="!loading" :margin="0" :text="link" backgroundColor="rgb(255,255,255)" <vue-qr v-if="!loading" :margin="0" :text="link" backgroundColor="rgb(255,255,255)"
@ -161,19 +163,30 @@
</template> </template>
<script> <script>
import { htmlToDataURL } from '@/utils/html2image' import { html2canvas } from '@/utils/html2image'
import ManagerPopup from "@/components/ManagerPopup.vue"
export default { export default {
name: 'Merchant', name: 'Merchant',
components: { ManagerPopup },
mounted() { mounted() {
this.init()
window.addEventListener('showManagerPopup', this.onShowManagerPopup)
window.addEventListener('closeManagerPopup', this.onCloseManagerPopup)
},
beforeUnmount() {
window.removeEventListener('showManagerPopup', this.onShowManagerPopup)
window.removeEventListener('closeManagerPopup', this.onCloseManagerPopup)
}, },
data() { data() {
return { return {
managerPopupVisible: false,
showInfo: false, showInfo: false,
showBottom: false, showBottom: false,
paycodeImg: '', paycodeImg: '',
isCapturing: false, isCapturing: false,
link: '', link: '',
id: this.$route.query.id,
data: { data: {
id: 'merchant_001', id: 'merchant_001',
MerchantAvatar: '', MerchantAvatar: '',
@ -189,89 +202,115 @@ export default {
YesterdayQty: 38, YesterdayQty: 38,
MonthIncome: 45600.00, MonthIncome: 45600.00,
PrevMonthIncome: 38500.00, PrevMonthIncome: 38500.00,
endTimes: '2024-04-18 10:30' endTimes: new Date().toLocaleString('zh-CN', { hour12: false })
}, },
countData: {},
States: 0, States: 0,
expiring: 3, expiring: 3,
loading: false, loading: false,
} }
}, },
computed: {
truncatedShopname() {
if (!this.data.shopname) return ''
return this.data.shopname.length > 8 ? this.data.shopname.slice(0, 8) + '...' : this.data.shopname
}
},
methods: { methods: {
onOpenBottom() { onShowManagerPopup() {
this.managerPopupVisible = true
},
onCloseManagerPopup() {
this.managerPopupVisible = false
},
init() {
Promise.all([
this.$get(`/v1/client/DShopsClient/${this.id}`).then(res => {
// console.log(res);
this.data = res.data;
this.data.endTimes = new Date().toLocaleString('zh-CN', { hour12: false });
this.$ls.set('merchant_shopname', res.data.shopname);
this.$ls.set('merchant_shopimg', res.data.shopimg);
this.$ls.set('merchant_cellphone', res.data.cellphone);
}),
this.getCount()
]
)
},
async onOpenBottom() {
this.paycodeImg = '' this.paycodeImg = ''
this.$nextTick(() => { this.$nextTick(async () => {
const el = this.$refs.paycodeOriginal const el = this.$refs.paycodeOriginal
if (!el) return if (!el) return
const scale = 2 const scale = 2
const rect = el.getBoundingClientRect()
const w = rect.width * scale
const h = rect.height * scale
const elRect = el.getBoundingClientRect() const elRect = el.getBoundingClientRect()
//
//
const canvas = document.createElement('canvas') const canvas = document.createElement('canvas')
const w = el.offsetWidth * scale
const h = el.offsetHeight * scale
canvas.width = w canvas.width = w
canvas.height = h canvas.height = h
const ctx = canvas.getContext('2d') const ctx = canvas.getContext('2d')
// // img
const bg = new Image() const bg = el.querySelector('img')
bg.src = el.querySelector('img').src const bgCanvas = await html2canvas(bg, { scale, useCORS: true, width: el.offsetWidth, height: el.offsetHeight })
bg.onload = () => { ctx.drawImage(bgCanvas, 0, 0, w, h)
ctx.drawImage(bg, 0, 0, w, h)
const infoEl = el.querySelector('.info') //
const codeEl = el.querySelector('.code') const infoEl = el.querySelector('.info')
const avatarEl = infoEl.querySelector('img')
const avatarCanvas = await html2canvas(avatarEl, { scale, useCORS: true, backgroundColor: 'transparent' })
// const infoRect = infoEl.getBoundingClientRect()
const avatarEl = infoEl.querySelector('img') const avatarSize = 30 * scale
htmlToDataURL(avatarEl, { scale: 2, useCORS: true, backgroundColor: 'transparent' }).then(avaCanvas => { const avatarX = (infoRect.left - elRect.left) * scale
const avaImg = new Image() const avatarY = (infoRect.top - elRect.top) * scale
avaImg.src = avaCanvas
avaImg.onload = () => {
const infoRect = infoEl.getBoundingClientRect()
const avaSize = infoRect.height * scale * 0.8
const avaX = (infoRect.left - elRect.left) * scale + avaSize * 0.1
const avaY = (infoRect.top - elRect.top) * scale + (infoRect.height * scale - avaSize) / 2
// ctx.save()
ctx.save() ctx.beginPath()
ctx.beginPath() ctx.arc(avatarX + avatarSize / 2, avatarY + avatarSize / 2, avatarSize / 2, 0, Math.PI * 2)
ctx.arc(avaX + avaSize / 2, avaY + avaSize / 2, avaSize / 2, 0, Math.PI * 2) ctx.clip()
ctx.clip() ctx.drawImage(avatarCanvas, avatarX, avatarY, avatarSize, avatarSize)
ctx.drawImage(avaImg, avaX, avaY, avaSize, avaSize) ctx.restore()
ctx.restore()
// //
ctx.font = `${avaSize * 0.6}px 'PingFang SC'` const codeEl = el.querySelector('.code')
ctx.fillStyle = '#333' const codeCanvas = await html2canvas(codeEl, { scale, useCORS: true, backgroundColor: '#ffffff' })
ctx.textBaseline = 'middle' const codeRect = codeEl.getBoundingClientRect()
ctx.fillText(this.data.MerchantName, avaX + avaSize + avaSize * 0.3, avaY + avaSize / 2) ctx.drawImage(
codeCanvas,
(codeRect.left - elRect.left) * scale,
(codeRect.top - elRect.top) * scale,
codeRect.width * scale,
codeRect.height * scale
)
// // (.name)
htmlToDataURL(codeEl, { scale: 2, useCORS: true, backgroundColor: '#ffffff' }).then(codeCanvas => { const nameEl = el.querySelector('.name')
const qrImg = new Image() const nameRect = nameEl.getBoundingClientRect()
qrImg.src = codeCanvas const fontSize = 20 * scale
qrImg.onload = () => { ctx.font = `${fontSize}px 'PingFang SC'`
const codeRect = codeEl.getBoundingClientRect() ctx.fillStyle = '#333'
ctx.drawImage( ctx.textBaseline = 'middle'
qrImg, if (this.data.shopname)
(codeRect.left - elRect.left) * scale, ctx.fillText(this.truncatedShopname, (nameRect.left - elRect.left) * scale, (nameRect.top - elRect.top) * scale + fontSize / 2)
(codeRect.top - elRect.top) * scale,
codeRect.width * scale, this.paycodeImg = canvas.toDataURL('image/png')
codeRect.height * scale
)
this.paycodeImg = canvas.toDataURL('image/png')
}
})
}
})
}
}) })
}, },
onCloseBottom() { onCloseBottom() {
this.showBottom = false this.showBottom = false
this.paycodeImg = '' // this.paycodeImg = ''
},
getCount() {
this.$get('/v1/client/DShopsClient/statistics').then(res => {
this.countData = res.data;
this.data.endTimes = new Date().toLocaleString('zh-CN', { hour12: false });
})
}, },
}, },
} }

View File

@ -0,0 +1,44 @@
<template>
<BasePage>
<div class="merchantcashout">
<div class="top">
<span>
提现中
<b class="red">960.00</b>
</span>
<span class="r">
累计提现
<b>5960.25</b>
</span>
</div>
<div class="list">
<div class="item">
<div class="line">
<b class="state">提现中</b>
<b class="r money red"><span>960</span>
</b>
</div>
<div class="record">
<div class="left">
提现2024.06.05 00:00:00
</div>
<div class="right">
发放:2024.06.05 05:25:35
</div>
</div>
</div>
</div>
</div>
</BasePage>
</template>
<script>
export default {
data() {
return {}
}
}
</script>

View File

@ -5,25 +5,26 @@
<div class="count_box"> <div class="count_box">
<div class="title" @click.stop="onShowTerm"> <div class="title" @click.stop="onShowTerm">
<span> <span>
当前营业收入 营业收入
</span> </span>
<van-icon @click="onShowTerm" name="question-o"></van-icon> <van-icon @click="onShowTerm" name="question-o"></van-icon>
</div> </div>
<span class="perform"> <span class="perform">
{{ data.total?.Balance.toFixed(2) }} ¥{{ data.total?.Balance.toFixed(2) }}
</span> </span>
<div class="btm"> <div class="btm">
<div> <div>
<span>昨日收入</span> <span>昨日收入</span>
<span> <span>
{{ data.total?.YesterdayAmount.toFixed(2) }} ¥{{ data.total?.YesterdayAmount.toFixed(2) }}
</span> </span>
</div> </div>
<div class="r" style="justify-content: end;"> <div class="r" style="justify-content: end;" @click="$navigate('MerchantCashout')">
<span>提现中</span> <span>提现中</span>
<span> <span>
{{ data.total?.CashAmount.toFixed(2) }} ¥{{ data.total?.CashAmount.toFixed(2) }}
<van-icon name="arrow"></van-icon>
</span> </span>
</div> </div>
</div> </div>
@ -40,17 +41,17 @@
<div class="date" @click="showDate = true"> <div class="date" @click="showDate = true">
<div> <div>
<span> <span>
{{ date[0] }} {{ date[0] }}-
</span> </span>
<span> <span>
{{ (parseInt(date[1]) < 10) ? `0${parseInt(date[1])}` : parseInt(date[1]) }} </span> {{ (parseInt(date[1]) < 10) ? `0${parseInt(date[1])}` : parseInt(date[1]) }} </span>
</div> </div>
<img src="/img/down.png"> <img src="/img/down.png">
</div> </div>
<div class="income"> <div class="income">
<span>当月收款</span> <span>当月收款</span>
<span> <span>
{{ data.total?.MonthBalance }} ¥{{ data.total?.MonthBalance?.toFixed(2) }}
</span> </span>
</div> </div>
</div> </div>
@ -62,14 +63,14 @@
<span class="type">{{ type[item.RecordSource] }}</span> <span class="type">{{ type[item.RecordSource] }}</span>
<p>剩余{{ item.CurValue }}</p> <p>剩余{{ item.CurValue }}</p>
<span :class="item.OpeType > 0 ? 'income' : 'expend'">{{ item.OpeType > 0 ? <span :class="item.OpeType > 0 ? 'income' : 'expend'">{{ item.OpeType > 0 ?
'+' : '-' }}{{ item.RecordValue }}</span> '+' : '-' }}{{ item.RecordValue?.toFixed(2) }}</span>
</div>
<div>
订单编号{{ item.TradeCode }}
</div> </div>
<div> <div>
购买时间{{ item.CTime }} 购买时间{{ item.CTime }}
</div> </div>
<div>
订单编号{{ item.TradeCode }}
</div>
</div> </div>
</div> </div>

View File

@ -0,0 +1,339 @@
<template>
<BasePage>
<div class="merchant-intro">
<div class="intro-header">
<div class="shop-avatar">
<van-uploader v-model="formData.AvatarUploader" :after-read="uploadShopImg" :max-count="1" upload-icon="plus">
<img v-if="formData.shopimg" :src="$file(formData.shopimg)" class="avatar-img" />
<div v-else class="avatar-placeholder">
<van-icon name="photograph" size="20" />
</div>
</van-uploader>
</div>
<div class="shop-info">
<div class="name">{{ formData.shopname || '店铺名称' }}</div>
<div class="phone">{{ formData.cellphone }}</div>
</div>
</div>
<van-form @submit="save">
<div class="info-section">
<div class="section-header">
<span class="section-title">店铺信息</span>
</div>
<van-cell-group inset class="info-group">
<van-field v-model="formData.shopname" label="店铺名称" placeholder="请输入店铺名称" required />
<van-field v-model="formData.huili" label="惠利比例" placeholder="请输入惠利比例" type="number" required>
<template #append>%</template>
</van-field>
<van-field v-model="formData.cellphone" label="联系电话" placeholder="请输入联系电话" type="tel" required />
</van-cell-group>
</div>
<div class="info-section">
<div class="section-header">
<span class="section-title">营业资质</span>
<span class="readonly-tag">仅展示</span>
</div>
<van-cell-group inset class="info-group">
<van-field v-model="formData.legalname" label="法人姓名" readonly />
<van-field v-model="formData.legalphone" label="法人手机号" readonly />
<van-field label="法人身份证照片" readonly>
<template #input>
<div v-if="formData.legalidimg && formData.legalidimg.length" class="img-thumb" @click="previewImage(formData.legalidimg[0].url)">
<img :src="formData.legalidimg[0].url" />
</div>
<span v-else class="empty">暂无</span>
</template>
</van-field>
<van-field label="营业执照照片" readonly>
<template #input>
<div v-if="formData.licenseimg && formData.licenseimg.length" class="img-thumb" @click="previewImage(formData.licenseimg[0].url)">
<img :src="formData.licenseimg[0].url" />
</div>
<span v-else class="empty">暂无</span>
</template>
</van-field>
<van-field v-model="formData.province" label="注册地区" readonly />
</van-cell-group>
</div>
<div class="info-section">
<div class="section-header">
<span class="section-title">结算账户</span>
<span class="readonly-tag">仅展示</span>
</div>
<van-cell-group inset class="info-group">
<van-field v-model="formData.bankname" label="账户名称" readonly />
<van-field v-model="formData.bankcard" label="银行卡号" readonly />
<van-field v-model="formData.subbank" label="支行名称" readonly />
<van-field v-model="formData.bankphone" label="银行预留手机号" readonly />
</van-cell-group>
</div>
<div class="btn-wrap">
<van-button round block type="primary" native-type="submit" :loading="saving" color="#ca2904">
保存修改
</van-button>
</div>
</van-form>
</div>
</BasePage>
</template>
<script>
import { ImagePreview } from 'vant'
export default {
name: 'MerchantIntroduction',
data() {
return {
saving: false,
formData: {
shopname: '',
shopimg: '',
AvatarUploader: [],
huili: 20,
cellphone: '',
legalname: '',
legalphone: '',
legalidimg: [],
licenseimg: [],
province: '',
bankname: '',
bankcard: '',
subbank: '',
bankphone: '',
}
}
},
mounted() {
this.init()
},
methods: {
init() {
this.$get('/v1/client/DShopsClient/my').then(res => {
const data = res.data
this.formData.shopname = data.shopname
this.formData.shopimg = data.shopimg
this.formData.huili = data.huili || 20
this.formData.cellphone = data.cellphone
this.formData.legalname = data.legalname
this.formData.legalphone = data.legalphone
this.formData.province = data.province
this.formData.bankname = data.bankname
this.formData.bankcard = data.bankcard
this.formData.subbank = data.subbank
this.formData.bankphone = data.bankphone
if (data.shopimg) {
this.formData.AvatarUploader = [{ url: this.$file(data.shopimg), isImage: true }]
}
if (data.legalidimg) {
this.formData.legalidimg = [{ url: this.$file(data.legalidimg), isImage: true }]
}
if (data.licenseimg) {
this.formData.licenseimg = [{ url: this.$file(data.licenseimg), isImage: true }]
}
})
},
uploadShopImg(file) {
this.formData.shopimg = file.file
},
previewImage(url) {
ImagePreview([url])
},
async save() {
this.saving = true
try {
if (this.formData.shopimg instanceof File) {
const url = await this.uploadFile('/v1/client/DShopsClient/shopimg', this.formData.shopimg)
this.formData.shopimg = url
}
await this.$put('/v1/client/DShopsClient', {
shopname: this.formData.shopname,
huili: this.formData.huili,
cellphone: this.formData.cellphone,
})
this.$showSuccessToast('保存成功')
} catch (err) {
this.$showFailToast(err.message || '保存失败')
} finally {
this.saving = false
}
},
uploadFile(url, file) {
const fd = new FormData()
fd.append('file', file)
return fetch(`${import.meta.env.VITE_API_URL}${url}`, {
method: 'POST',
headers: { 'Authorization': `Bearer ${localStorage.getItem('token')}` },
body: fd,
}).then(res => res.json()).then(res => {
if (res.status !== 200) throw new Error(res.message)
return res.data
})
}
},
}
</script>
<style lang="less" scoped>
.merchant-intro {
min-height: 100vh;
background: #f5f5f5;
padding-bottom: 8vw;
.intro-header {
background: linear-gradient(135deg, #ca2904 0%, #e84a2f 100%);
padding: 6vw 5.33vw;
display: flex;
align-items: center;
.shop-avatar {
flex-shrink: 0;
:deep(.van-uploader) {
.van-uploader__wrapper {
.van-uploader__upload {
width: 18vw;
height: 18vw;
background: rgba(255, 255, 255, 0.15);
border-radius: 50%;
}
}
}
.avatar-img {
width: 18vw;
height: 18vw;
border-radius: 50%;
object-fit: cover;
border: 3px solid rgba(255, 255, 255, 0.4);
}
.avatar-placeholder {
width: 18vw;
height: 18vw;
border-radius: 50%;
background: rgba(255, 255, 255, 0.15);
display: flex;
align-items: center;
justify-content: center;
color: rgba(255, 255, 255, 0.8);
}
}
.shop-info {
margin-left: 4vw;
color: #fff;
.name {
font-size: 5.33vw;
font-weight: bold;
margin-bottom: 1.5vw;
}
.phone {
font-size: 3.47vw;
opacity: 0.85;
}
}
}
.info-section {
margin-top: 4vw;
.section-header {
padding: 0 5.33vw;
height: 10vw;
display: flex;
align-items: center;
justify-content: space-between;
background: #f5f5f5;
.section-title {
font-size: 4vw;
font-weight: 600;
color: #333;
}
.readonly-tag {
font-size: 3.2vw;
color: #999;
background: #e8e8e8;
padding: 0.8vw 2vw;
border-radius: 2vw;
}
}
.info-group {
background: #fff;
:deep(.van-cell) {
padding: 0 5.33vw;
height: 12vw;
align-items: center;
&::after {
left: 5.33vw;
right: 0;
border-color: #f0f0f0;
}
}
:deep(.van-field__label) {
width: 26vw;
font-size: 3.73vw;
color: #666;
}
:deep(.van-field__control) {
font-size: 3.73vw;
color: #333;
text-align: right;
&::placeholder {
color: #ccc;
}
}
:deep(.van-field__control:disabled) {
color: #999;
background: transparent;
}
.img-thumb {
width: 14vw;
height: 10vw;
border-radius: 1.33vw;
overflow: hidden;
margin-left: auto;
img {
width: 100%;
height: 100%;
object-fit: cover;
}
}
.empty {
margin-left: auto;
color: #ccc;
font-size: 3.47vw;
}
}
}
.btn-wrap {
padding: 6vw 5.33vw;
margin-top: 6vw;
:deep(.van-button) {
height: 11.73vw;
font-size: 4.27vw;
}
}
}
</style>

View File

@ -1,123 +0,0 @@
<template>
<BasePage>
<div class="merchanttrade">
<div class="top">
<div class="line">
<!-- <van-popover v-model:show="showPopover" :actions="option" @select="onSelect">
<template #reference>
<div class="pop_box">
{{ value }}
<img src="/img/down.png" alt="">
</div>
</template></van-popover> -->
<div class="inputbox">
<input v-model="searchKey" type="text" placeholder="输入产品名搜索" @keydown.enter="filterList">
<van-icon name="search" @click="filterList"></van-icon>
</div>
</div>
<van-tabs v-model:active="searchParams.TradeStates" line-height="1.333vw" line-width="8vw" color="#22a56e"
title-active-color="#222222" title-inactive-color="#222" @change="filterList">
<van-tab title="全部" :name="99"></van-tab>
<van-tab title="待付款" :name="0"></van-tab>
<van-tab title="待处理" :name="2"></van-tab>
<van-tab title="已完成" :name="4"></van-tab>
</van-tabs>
</div>
<div class="product_list">
<div class="product_item">
<img src="" alt="">
<div>
<span class="name">测试测试测试测试测试测试测试测试测试测试测试测试测试测试测试测试测试</span>
<span class="price" v-html="$toMoney(999, 'b')"></span>
<span class="stock">销量0</span>
</div>
</div>
<div class="product_item">
<img src="" alt="">
<div>
<span class="name">测试测试测试测试测试测试测试测试测试测试测试测试测试测试测试测试测试</span>
<span class="price" v-html="$toMoney(999, 'b')"></span>
<span class="stock">销量0</span>
</div>
</div>
</div>
</div>
</BasePage>
</template>
<script>
export default {
name: 'MerchantTrade',
data() {
return {
GiftName: { 0: '待付款', 1: '待处理', 2: '待处理', 3: '已完成', 4: '已完成' },
option: [
{ text: '全部' },
{ text: '单人优享' },
{ text: '家庭尊享' },
{ text: '购机' },
],
searchParams: {
GiftArea: 'ALL',
TradeStates: 99,
GiftType: 'ALL'
},
searchKey: '',
value: '全部',
allList: [
{ TradeCode: 'T20240418001', SkuSpecName: '年卡', TradeStates: 4, Avatar: '/img/co-1.png', NickName: '张三', Phone: '13800138001', OriginAmount: 2999.00, GiftArea: 'Store' },
{ TradeCode: 'T20240418002', SkuSpecName: '月卡', TradeStates: 2, Avatar: '/img/co-2.png', NickName: '李四', Phone: '13800138002', OriginAmount: 299.00, GiftArea: 'Rent' },
{ TradeCode: 'T20240418003', SkuSpecName: '季卡', TradeStates: 0, Avatar: '/img/co-3.png', NickName: '王五', Phone: '13800138003', OriginAmount: 899.00, GiftArea: 'Store' },
{ TradeCode: 'T20240417001', SkuSpecName: '半年卡', TradeStates: 4, Avatar: '/img/co.png', NickName: '赵六', Phone: '13800138004', OriginAmount: 1699.00, GiftArea: 'Buy' },
{ TradeCode: 'T20240417002', SkuSpecName: '体验卡', TradeStates: 4, Avatar: '/img/co-1.png', NickName: '钱七', Phone: '13800138005', OriginAmount: 99.00, GiftArea: 'Rent' },
]
}
},
computed: {
filteredList() {
let result = [...this.allList];
if (this.searchParams.GiftArea !== 'ALL') {
result = result.filter(x => x.GiftArea === this.searchParams.GiftArea);
}
if (this.searchParams.TradeStates !== 99) {
result = result.filter(x => x.TradeStates === this.searchParams.TradeStates);
}
if (this.searchParams.GiftType !== 'ALL') {
// simplified filter
}
if (this.searchKey) {
result = result.filter(x => x.TradeCode.includes(this.searchKey));
}
return result;
}
},
methods: {
filterList() {
// trigger computed
},
onSelect(option) {
this.value = option.text;
},
getStateClass(state) {
switch (state) {
case 4:
return 'green';
case 3:
return 'green';
case 2:
return 'yellow';
case 1:
return 'yellow';
case 0:
return 'red';
default:
return '';
}
}
},
}
</script>

View File

@ -2,54 +2,143 @@
<BasePage> <BasePage>
<div class="merchanttrade"> <div class="merchanttrade">
<div class="top"> <div class="top">
<div class="line"> <div class="date" @click="showDate = true">
<!-- <van-popover v-model:show="showPopover" :actions="option" @select="onSelect"> <div>
<template #reference>
<div class="pop_box">
{{ value }}
<img src="/img/down.png" alt="">
</div>
</template>
</van-popover> -->
<div class="inputbox">
<input v-model="searchKey" type="text" placeholder="订单编号搜索" @keydown.enter="filterList">
<van-icon name="search" @click="filterList"></van-icon>
</div>
</div>
<van-tabs v-model:active="searchParams.TradeStates" line-height="1.333vw" line-width="8vw" color="#22a56e"
title-active-color="#222222" title-inactive-color="#222" @change="filterList">
<van-tab title="全部" :name="99"></van-tab>
<van-tab title="待付款" :name="0"></van-tab>
<van-tab title="待处理" :name="2"></van-tab>
<van-tab title="已完成" :name="4"></van-tab>
</van-tabs>
</div>
<div class="mct-list">
<div class="mct-item" v-for="item in filteredList">
<div class="mct-top">
<span class="orderNum"> 订单号{{ item.TradeCode }}</span>
<span class="state r" :class="getStateClass(item.TradeStates)"
@click="$navigate(`MerchantTradeDetail?id=${item.TradeCode}`)">
{{ GiftName[item.TradeStates] }}<van-icon name="arrow"></van-icon></span>
</div>
<div class="mct-user">
<img :src="$file(item.Avatar)">
<div>
<span class="name">{{ item.NickName }}</span>
<p>{{ item.Phone }}</p>
</div>
<span class="r">¥{{ item.OriginAmount }}</span>
</div>
<div class="_code">
<span> <span>
下单人13345678912 {{ date[0] }}-
</span> </span>
<span class="r">昵称张保保</span> <span>
{{ (parseInt(date[1]) < 10) ? `0${parseInt(date[1])}` : parseInt(date[1]) }} </span>
</div> </div>
<img src="/img/down.png">
</div>
<div class="filter" @click="showRight = true">
<span>筛选</span>
<img src="/img/down.png" alt="">
</div> </div>
</div> </div>
<BaseList ref="listRef" url="/v1/client/DShopsClient/order" class="list" :params="searchParams"
:parse-data="parseData" @load="onLoad">
<template #default="{ item }">
<div class="item" v-if="item.orders && item.orders.length">
<div class="top_line">
<span class="date">
{{ item.day }}
</span>
<div class="right_box">
<div>
<p>{{ item.orderCount }}</p>
<p>订单数</p>
</div>
<div>
<p>¥{{ item.ordermoney }}</p>
<p>营业额</p>
</div>
<div>
<p>¥{{ item.income }}</p>
<p>应收</p>
</div>
</div>
</div>
<div class="item_detail" v-for="order in item.orders" :key="order.ordernum">
<div class="line">
<span class="ordernum">
订单号{{ order.ordernum }}
</span>
<button @click="$navigate(`MerchantTradeDetail?id=${order.ordernum}`)">
{{ order.statename }} <van-icon name="arrow"></van-icon>
</button>
</div>
<div class="userinfo">
<img :src="$file(order.userimg)" class="icon" alt="">
<div class="info">
<span>{{ order.usercellphone }}</span>
<p>{{ $formatGMT(order.addtime, 'yyyy-MM-dd HH:mm:ss') }}</p>
</div>
</div>
<div class="count">
<div>
<b>{{ order.ordermoney }}</b>
<span>商品总额</span>
</div>
<div>
<b>{{ order.discount }}</b>
<span>让利金额</span>
</div>
<div class="red">
<b>{{ order.income }}</b>
<span>应收金额</span>
</div>
</div>
</div>
</div>
</template>
</BaseList>
<van-popup v-model:show="showDate" position="bottom">
<van-date-picker v-model="currentDate" title="选择年月" :columns-type="['year', 'month']" @confirm="onconfirm"
@cancel="showDate = false" />
</van-popup>
<van-popup v-model:show="showRight" position="right" :style="{ width: '80%', height: '100%' }">
<div class="filter-popup">
<div class="filter-header">
<span @click="showRight = false">取消</span>
<span>筛选</span>
<span @click="resetFilter">重置</span>
</div>
<div class="filter-content">
<div class="filter-section">
<div class="section-title">用户手机号</div>
<van-field v-model="filterForm.cellphone" placeholder="输入手机号筛选" clearable />
</div>
<div class="filter-section">
<div class="section-title">订单号</div>
<van-field v-model="filterForm.ordernum" placeholder="输入订单号筛选" clearable />
</div>
<div class="filter-section">
<div class="section-title">买单时间</div>
<div class="date-range" @click="showDateRange = true">
<span v-if="filterForm.starttime">{{ filterForm.starttime }}</span>
<span v-else class="placeholder">开始日期</span>
<span class="to"></span>
<span v-if="filterForm.endtime">{{ filterForm.endtime }}</span>
<span v-else class="placeholder">结束日期</span>
</div>
</div>
<!-- <div class="filter-section">
<div class="section-title">订单状态</div>
<van-radio-group v-model="filterForm.status" direction="horizontal">
<van-radio name="-1">全部</van-radio>
<van-radio name="0">待付款</van-radio>
<van-radio name="1">待处理</van-radio>
<van-radio name="3">已完成</van-radio>
</van-radio-group>
</div> -->
</div>
<van-action-bar>
<van-action-bar-button type="warning" text="重置" @click="resetFilter" />
<van-action-bar-button type="danger" text="确认" @click="confirmFilter" />
</van-action-bar>
</div>
</van-popup>
<!-- <van-popup v-model:show="showDateRange" position="bottom" :style="{ height: '75%' }"> -->
<van-calendar v-model:show="showDateRange" type="range" :min-date="new Date(2026, 0, 1)" @confirm="onDateRangeConfirm" />
<!-- <van-calendar type="range" v-model="selectedDateRange" :min-date="new Date(new Date().getFullYear() - 1, 0, 1)"
title="选择日期区间" show-title show-subtitle @confirm="onDateRangeConfirm" /> -->
<!-- </van-popup> -->
</div> </div>
</BasePage> </BasePage>
</template> </template>
@ -59,62 +148,85 @@ export default {
name: 'MerchantTrade', name: 'MerchantTrade',
data() { data() {
return { return {
date: [`${new Date().getFullYear()}`, `${new Date().getMonth() + 1}`],
currentDate: [`${new Date().getFullYear()}`, `${new Date().getMonth() + 1}`],
showDate: false,
showRight: false,
showDateRange: false,
filterForm: {
cellphone: '',
ordernum: '',
starttime: '',
endtime: '',
status: '-1'
},
GiftName: { 0: '待付款', 1: '待处理', 2: '待处理', 3: '已完成', 4: '已完成' }, GiftName: { 0: '待付款', 1: '待处理', 2: '待处理', 3: '已完成', 4: '已完成' },
option: [
{ text: '全部' },
{ text: '单人优享' },
{ text: '家庭尊享' },
{ text: '购机' },
],
searchParams: { searchParams: {
GiftArea: 'ALL', year: new Date().getFullYear(),
TradeStates: 99, month: new Date().getMonth() + 1,
GiftType: 'ALL' cellphone: '',
ordernum: '',
starttime: '',
endtime: ''
},
data: {
img: ''
}, },
searchKey: '', searchKey: '',
value: '全部', selectedDateRange: [new Date(), new Date()]
allList: [
{ TradeCode: 'T20240418001', SkuSpecName: '年卡', TradeStates: 4, Avatar: '/img/co-1.png', NickName: '张三', Phone: '13800138001', OriginAmount: 2999.00, GiftArea: 'Store' },
{ TradeCode: 'T20240418002', SkuSpecName: '月卡', TradeStates: 2, Avatar: '/img/co-2.png', NickName: '李四', Phone: '13800138002', OriginAmount: 299.00, GiftArea: 'Rent' },
{ TradeCode: 'T20240418003', SkuSpecName: '季卡', TradeStates: 0, Avatar: '/img/co-3.png', NickName: '王五', Phone: '13800138003', OriginAmount: 899.00, GiftArea: 'Store' },
{ TradeCode: 'T20240417001', SkuSpecName: '半年卡', TradeStates: 4, Avatar: '/img/co.png', NickName: '赵六', Phone: '13800138004', OriginAmount: 1699.00, GiftArea: 'Buy' },
{ TradeCode: 'T20240417002', SkuSpecName: '体验卡', TradeStates: 4, Avatar: '/img/co-1.png', NickName: '钱七', Phone: '13800138005', OriginAmount: 99.00, GiftArea: 'Rent' },
]
}
},
computed: {
filteredList() {
let result = [...this.allList];
if (this.searchParams.GiftArea !== 'ALL') {
result = result.filter(x => x.GiftArea === this.searchParams.GiftArea);
}
if (this.searchParams.TradeStates !== 99) {
result = result.filter(x => x.TradeStates === this.searchParams.TradeStates);
}
if (this.searchParams.GiftType !== 'ALL') {
// simplified filter
}
if (this.searchKey) {
result = result.filter(x => x.TradeCode.includes(this.searchKey));
}
return result;
} }
}, },
methods: { methods: {
filterList() { parseData(res) {
// trigger computed return res.data || []
}, },
onSelect(option) { onLoad(list) {
this.value = option.text; console.log('list loaded:', list);
},
onconfirm(value) {
this.date = this.currentDate;
this.searchParams.year = parseInt(this.currentDate[0])
this.searchParams.month = parseInt(this.currentDate[1])
this.showDate = false;
this.$refs.listRef?.refresh();
},
onDateRangeConfirm(date) {
if (Array.isArray(date) && date.length >= 2) {
this.filterForm.starttime = this.formatDate(date[0]);
this.filterForm.endtime = this.formatDate(date[date.length - 1]);
}
this.showDateRange = false;
},
formatDate(date) {
const d = new Date(date);
const year = d.getFullYear();
const month = String(d.getMonth() + 1).padStart(2, '0');
const day = String(d.getDate()).padStart(2, '0');
return `${year}-${month}-${day}`;
},
resetFilter() {
this.filterForm = {
cellphone: '',
ordernum: '',
starttime: '',
endtime: '',
status: '-1'
};
},
confirmFilter() {
this.searchParams.cellphone = this.filterForm.cellphone;
this.searchParams.ordernum = this.filterForm.ordernum;
this.searchParams.starttime = this.filterForm.starttime;
this.searchParams.endtime = this.filterForm.endtime;
this.showRight = false;
this.$refs.listRef?.refresh();
}, },
getStateClass(state) { getStateClass(state) {
switch (state) { switch (state) {
case 4: case 4:
return 'green';
case 3: case 3:
return 'green'; return 'green';
case 2: case 2:
return 'yellow';
case 1: case 1:
return 'yellow'; return 'yellow';
case 0: case 0:
@ -124,6 +236,5 @@ export default {
} }
} }
}, },
} }
</script> </script>

View File

@ -1,63 +1,63 @@
<template> <template>
<BasePage> <BasePage>
<div class="merchanttradedetail"> <div class="merchanttradedetail">
<div class="bg"></div> <div class="state" :class="getStateClass(data.state)">
<div class="line"></div> <img :src="data.state >= 3 ? '/img/checked.png' : '/img/loading.png'" alt="">
<div class="container"> <b>{{ data.statename }}</b>
<div class="orderbox"> </div>
<div class="orderheader" v-if="data.TradeStates == 0">
<img src="/img/remark-i1.png"> <div class="containar">
<span class="state" :class="getStateClass(data.TradeStates)">待付款</span> <div class="line"></div>
<div class="details_box">
<div class="detail">
<span>用户账号</span>
<p>{{ $formatCellphone(data.usercellphone) }}</p>
</div> </div>
<div class="orderheader" v-if="data.TradeStates == 1 || data.TradeStates == 2"> <div class="detail">
<img src="/img/remark-i2.png"> <span>下单时间</span>
<span class="state" :class="getStateClass(data.TradeStates)">待处理</span> <p>{{ $formatGMT(data.addtime, 'yyyy-MM-dd HH:mm:ss') }}</p>
</div> </div>
<div class="orderheader" v-if="data.TradeStates == 3 || data.TradeStates == 4"> <div class="detail">
<img src="/img/remark-i4.png "> <span>付款时间</span>
<span class="state" :class="getStateClass(data.TradeStates)">已完成</span> <p>{{ $formatGMT(data.paytime, 'yyyy-MM-dd HH:mm:ss') }}</p>
</div> </div>
<div class="ordercontent"> <div class="detail">
<div class="orderitem"> <span>交易单号</span>
<span class="label">用户账号</span> <p>{{ data.ordernum }} <van-icon name="copy" @click="copyOrdernum" /></p>
<span class="r">{{ data.Phone }}</span>
</div>
<div class="orderitem">
<span class="label">商品名称</span>
<span class="r">{{ data.SkuSpecName }}</span>
</div>
</div> </div>
<div class="ordercontent">
<div class="orderitem" @click="$copyText(data.TradeCode); $showSuccessToast('复制成功')"> <hr>
<span class="label">订单编号</span>
<span class="r box box-align-center">{{ data.TradeCode }} <div class="detail">
<img class="copy" src="/img/copy-b.png"></span> <span>买单商品总额</span>
</div> <p>¥{{ data.ordermoney }}</p>
<div class="orderitem">
<span class="label">下单时间</span>
<span class="r">{{ data.CTime }}</span>
</div>
<div class="orderitem" v-if="data.PayTime">
<span class="label">付款时间</span>
<span class="r">{{ data.PayTime }}</span>
</div>
</div> </div>
<div class="ordercontent" v-if="data.PayTime"> <div class="detail" v-if="data.payjifen">
<div class="orderitem"> <span>用户积分抵扣</span>
<span class="label">支付方式</span> <p>{{ data.payjifen }}积分</p>
<span class="r">{{ PayMethod[data.PayMethod] }}</span> </div>
</div> <div class="detail" v-if="data.payquan">
<div class="orderitem"> <span>会员卡余额抵扣</span>
<span class="label">商品总额</span> <p>¥{{ data.payquan }}</p>
<span class="r">{{ data.OriginAmount.toFixed(2) }}</span> </div>
</div> <div class="detail">
<div class="orderitem"> <span>用户实付金额</span>
<span class="label">商家实收</span> <p>¥{{ data.paymoney }}</p>
<span class="r price">{{ data.Amount.toFixed(2) }}</span> </div>
</div>
<p class="remark r" v-if="data.Deduct"> <hr>
(余额支付{{ data.Amount.toFixed(2) }}积分抵扣{{ data.Deduct.toFixed(2) }})
</p> <div class="detail" v-if="data.discountratio">
<span>商家让利比例</span>
<p>{{ data.discountratio }}%</p>
</div>
<div class="detail">
<span>商家让利金额</span>
<p>¥{{ data.discount }}</p>
</div>
<div class="detail">
<span>商家应收金额</span>
<p class="red">¥{{ data.income }}</p>
</div> </div>
</div> </div>
</div> </div>
@ -68,37 +68,36 @@
<script> <script>
export default { export default {
name: 'MerchantTradeDetail', name: 'MerchantTradeDetail',
data() {
return {
data: {}
}
},
mounted() { mounted() {
this.init(); this.init();
}, },
data() {
return {
PayMethod: { 1: '微信支付', 2: '支付宝', 3: '银行卡' },
data: {
TradeCode: 'T20240418001',
TradeStates: 4,
Phone: '13800138001',
SkuSpecName: '年卡',
CTime: '2024-04-18 10:30:00',
PayTime: '2024-04-18 10:35:00',
PayMethod: 1,
OriginAmount: 2999.00,
Amount: 2899.00,
Deduct: 100.00
},
}
},
methods: { methods: {
init() { init() {
const ordernum = this.$route.query.id;
this.$get(`/v1/client/DShopsClient/order/${ordernum}`).then(res => {
this.data = res.data || {};
}).catch(err => {
this.$showFailToast(err.message || '加载失败');
});
},
copyOrdernum() {
if (this.data.ordernum) {
this.$copyText(this.data.ordernum).then(() => {
this.$showSuccessToast('已复制');
});
}
}, },
getStateClass(state) { getStateClass(state) {
switch (state) { switch (state) {
case 4: case 4:
return 'green';
case 3: case 3:
return 'green'; return 'green';
case 2: case 2:
return 'yellow';
case 1: case 1:
return 'yellow'; return 'yellow';
case 0: case 0:
@ -108,8 +107,5 @@ export default {
} }
} }
}, },
computed: {
},
} }
</script> </script>

View File

@ -5,53 +5,52 @@
<span> <span>
截止{{ total.endTimes }} 截止{{ total.endTimes }}
</span> </span>
<p class="refresh r" @click="initTotal"><img src="/img/refresh.png">刷新</p> <p class="refresh r" @click="initTotal">刷新<img src="/img/refresh.png"></p>
</div> </div>
<div class="count-box" v-if="total"> <div class="count-box" v-if="total">
<div class="item"> <div class="item">
<div> <div>
<span>今日营业额</span> <span>今日营业额</span>
<b>{{ total.TodayAmount?.toFixed(2) }}</b> <b>{{ total.todayyingyee?.toFixed(2) }}</b>
</div> </div>
<p>{{ total.YesterdayAmount && total.YesterdayAmount != 0 <p>{{ total.yesterdayyingyee && total.yesterdayyingyee != 0
? ((total.TodayAmount - total.YesterdayAmount) / total.YesterdayAmount * 100).toFixed(2) ? ((total.todayyingyee - total.yesterdayyingyee) / total.yesterdayyingyee * 100).toFixed(2)
: (total.TodayAmount > 0 ? '100.00' : '0.00') }}%<span>较昨日</span></p> : (total.todayyingyee > 0 ? '100.00' : '0.00') }}%<span>较昨日</span></p>
</div> </div>
<div class="item"> <div class="item">
<div> <div>
<span>今日抵扣消费券</span> <span>今日应收</span>
<b>{{ total.TodayDeduct?.toFixed(2) }}</b> <b>{{ total.todayyingshou?.toFixed(2) }}</b>
</div> </div>
<p>{{ total.YesterdayDeduct && total.YesterdayDeduct != 0 <p>{{ total.yesterdayingshou && total.yesterdayingshou != 0
? ((total.TodayDeduct - total.YesterdayDeduct) / total.YesterdayDeduct * 100).toFixed(2) ? ((total.todayyingshou - total.yesterdayingshou) / total.yesterdayingshou * 100).toFixed(2)
: (total.TodayDeduct > 0 ? '100.00' : '0.00') }}%<span>较昨日</span></p> : (total.todayyingshou > 0 ? '100.00' : '0.00') }}%<span>较昨日</span></p>
</div> </div>
<div class="item"> <div class="item">
<div> <div>
<span>今日订单数</span> <span>今日订单数</span>
<b>{{ total.TodayQty }}</b> <b>{{ total.todaydingdanshu }}</b>
</div> </div>
<p>{{ total.YesterdayQty && total.YesterdayQty != 0 <p>{{ total.yesterdaydingdanshu && total.yesterdaydingdanshu != 0
? ((total.TodayQty - total.YesterdayQty) / total.YesterdayQty * 100).toFixed(2) ? ((total.todaydingdanshu - total.yesterdaydingdanshu) / total.yesterdaydingdanshu * 100).toFixed(2)
: (total.TodayQty > 0 ? '100.00' : '0.00') }}%<span>较昨日</span></p> : (total.todaydingdanshu > 0 ? '100.00' : '0.00') }}%<span>较昨日</span></p>
</div> </div>
<div class="item"> <div class="item">
<div> <div>
<span>本月收入</span> <span>今日惠利金额</span>
<b>{{ total.MonthIncome?.toFixed(2) }}</b> <b>{{ total.todayyouhui?.toFixed(2) }}</b>
</div> </div>
<p> <p>{{ total.yesterdayyouhui && total.yesterdayyouhui != 0
{{ total.PrevMonthIncome && total.PrevMonthIncome != 0 ? ((total.todayyouhui - total.yesterdayyouhui) / total.yesterdayyouhui * 100).toFixed(2)
? ((total.MonthIncome - total.PrevMonthIncome) / total.PrevMonthIncome * 100).toFixed(2) : (total.todayyouhui > 0 ? '100.00' : '0.00') }}%<span>较昨日</span></p>
: (total.MonthIncome > 0 ? '100.00' : '0.00') }}%<span>较上月</span></p>
</div> </div>
</div> </div>
<div class="report"> <div class="report">
<div class="t"> <div class="t">
<b>经营统计报表</b> <b>经营统计报表</b>
<div class="box box-align-center r" v-if="active == 0" @click="showDate = true"> <div class="box box-align-center r" v-if="active === 0" @click="showDate = true">
<img class="calendar" src="/img/calendar.png"> <img class="calendar" src="/img/calendar.png">
<span> <span>
{{ currentDate[0] }}-{{ currentDate[1] }}-{{ currentDate[2] }} {{ currentDate[0] }}-{{ currentDate[1] }}-{{ currentDate[2] }}
@ -77,25 +76,25 @@
<div class="datecount"> <div class="datecount">
<div class="dc-item"> <div class="dc-item">
<span>{{ active == 0 ? '今日' : '本月' }}营业额</span> <span>{{ active == 0 ? '今日' : '本月' }}营业额</span>
<b>{{ data.total?.Amount.toFixed(2) }}</b> <b>{{ chartData.yingyee?.toFixed(2) }}</b>
</div> </div>
<div class="dc-item"> <div class="dc-item">
<span>{{ active == 0 ? '今日' : '本月' }}抵扣积分</span> <span>{{ active == 0 ? '今日' : '本月' }}抵扣积分</span>
<b>{{ data.total?.Deduct.toFixed(2) }}</b> <b>{{ chartData.yingshou?.toFixed(2) }}</b>
</div> </div>
<div class="dc-item"> <div class="dc-item">
<span>{{ active == 0 ? '今日' : '本月' }}订单数</span> <span>{{ active == 0 ? '今日' : '本月' }}订单数</span>
<b>{{ data.total?.Qty }}</b> <b>{{ chartData.dingdanshu }}</b>
</div> </div>
<div class="dc-item"> <div class="dc-item">
<span>{{ active == 0 ? '今日' : '本月' }}收入</span> <span>{{ active == 0 ? '今日' : '本月' }}收入</span>
<b>{{ data.total?.Income.toFixed(2) }}</b> <b>{{ chartData.youhui?.toFixed(2) }}</b>
</div> </div>
</div> </div>
<b v-if="active == 0">日交易趋势图</b> <b v-if="active == 0">日交易趋势图</b>
<b v-if="active == 1">月交易趋势图</b> <b v-if="active == 1">月交易趋势图</b>
<div class="Chart" id="chartContainer" style="width: 82vw;height: 50vw;"></div> <div class="Chart" ref="chartRef" style="width: 82vw;height: 50vw;"></div>
</div> </div>
@ -114,62 +113,118 @@
</template> </template>
<script> <script>
export default { export default {
name: 'Statistics', name: 'Statistics',
data() { data() {
return { return {
data: { chartData: {
total: { yingyee: 0,
Amount: 5680.00, yingshou: 0,
Deduct: 1280.00, dingdanshu: 0,
Qty: 45, youhui: 0,
Income: 4560.00 orderchart: []
},
list: [
{ date: '2024-04-01', Amount: 3200 },
{ date: '2024-04-02', Amount: 2800 },
{ date: '2024-04-03', Amount: 3500 },
{ date: '2024-04-04', Amount: 4200 },
{ date: '2024-04-05', Amount: 3800 },
{ date: '2024-04-06', Amount: 2900 },
{ date: '2024-04-07', Amount: 5100 },
]
}, },
total: { total: {
TodayAmount: 5680.00, todayyingyee: 0,
YesterdayAmount: 4200.00, yesterdayyingyee: 0,
TodayDeduct: 1280.00, todayyingshou: 0,
YesterdayDeduct: 980.00, yesterdayingshou: 0,
TodayQty: 45, todaydingdanshu: 0,
YesterdayQty: 38, yesterdaydingdanshu: 0,
MonthIncome: 45600.00, todayyouhui: 0,
PrevMonthIncome: 38500.00, yesterdayyouhui: 0,
endTimes: '2024-04-18 10:30' endTimes: ''
}, },
showDate: false, showDate: false,
active: 0, active: 0,
showMonth: false, showMonth: false,
currentMonth: [`${new Date().getFullYear()}`, `${new Date().getMonth() + 1}`], currentMonth: [`${new Date().getFullYear()}`, `${new Date().getMonth() + 1}`],
currentDate: [`${new Date().getFullYear()}`, `${new Date().getMonth() + 1}`, `${new Date().getDate()}`], currentDate: [`${new Date().getFullYear()}`, `${new Date().getMonth() + 1}`, `${new Date().getDate()}`],
chart: null
} }
}, },
mounted() { mounted() {
this.init();
}, },
methods: { methods: {
initTotal() { initTotal() {
this.total.endTimes = new Date().toLocaleString().split('/').map((t) => t.padStart(2, '0')).join('-'); this.total.endTimes = new Date().toLocaleString('zh-CN', { hour12: false });
}, },
init() { init() {
this.showMonth = false; this.showMonth = false;
this.showDate = false; this.showDate = false;
this.getCount();
this.initTotal()
this.initChart();
}, },
initChart() { initChart() {
// chart logic simplified for static const params = this.active == 0
? { year: this.currentDate[0], month: this.currentDate[1], day: this.currentDate[2] }
: { year: this.currentMonth[0], month: this.currentMonth[1] };
this.$get('/v1/client/DShopsClient/statisticschart', params).then(res => {
this.chartData = res.data;
this.$nextTick(() => {
this.renderChart();
})
})
},
renderChart() {
if (!this.chart) {
this.chart = window.echarts.init(this.$refs.chartRef);
}
const dates = this.chartData.orderchart.map(item => item.adddate?.slice(5));
const values = this.chartData.orderchart.map(item => item.ordermoney);
this.chart.setOption({
tooltip: {
trigger: 'axis'
},
grid: {
left: '12%',
right: '8%',
bottom: '25%',
top: '20%'
},
xAxis: {
type: 'category',
data: dates,
axisLabel: {
fontSize: 10,
color: '#666'
}
},
yAxis: {
type: 'value',
axisLabel: {
fontSize: 10,
color: '#666'
}
},
series: [{
data: values,
type: 'line',
smooth: true,
lineStyle: { color: '#e4bb4e', width: 2 },
itemStyle: { color: '#e4bb4e' },
areaStyle: {
color: new window.echarts.graphic.LinearGradient(0, 0, 0, 1, [
{ offset: 0, color: 'rgba(228,187,78,0.3)' },
{ offset: 1, color: 'rgba(228,187,78,0)' }
])
}
}]
});
},
getCount() {
this.$get('/v1/client/DShopsClient/statistics').then(res => {
this.total = res.data
this.total.endTimes = new Date().toLocaleString('zh-CN', { hour12: false });
})
} }
}, },
computed: { beforeUnmount() {
}, if (this.chart) {
this.chart.dispose();
}
}
} }
</script> </script>

View File

@ -0,0 +1,117 @@
<template>
<BasePage>
<ManagerPopup v-model="managerPopupVisible" />
<div class="opera">
<div class="top">
<div class="info_box">
<img class="icon" src="" alt="">
<div class="inf">
<b>奖励一个挖野菜</b>
<div>
<img src="/img/phone.png" alt="">
12568951256
</div>
</div>
</div>
<div class="shopcenter" @click="$showManagerPopup()">
<span>
管理中心
<van-icon name="arrow" />
</span>
</div>
</div>
<div class="containar">
<div class="wallet_box">
<div class="item" @click="$navigate('Balance')">
<div class="t">
<img src="/img/op-i1.png" alt="">
<span>余额</span>
<van-icon name="arrow"></van-icon>
</div>
<b>
2565.00
</b>
</div>
<div class="item" @click="$navigate('CV')">
<div class="t">
<img src="/img/op-i2.png" alt="">
<span>会员卡</span>
<van-icon name="arrow"></van-icon>
</div>
<b>
2565.00
</b>
</div>
</div>
<div class="fun_box">
<div class="item">
<div class="left">
<b>
扫一扫
</b>
<p>核销礼品券</p>
</div>
<img src="/img/op-i3.png" alt="">
</div>
<div class="item" @click="$navigate('CertificateRecord?type=verif')">
<div class="left">
<b>
核销记录
</b>
<p>查看礼品券核销记录</p>
</div>
<img src="/img/op-i4.png" alt="">
</div>
<div class="item" @click="$navigate('Allow')">
<div class="left">
<b>
业绩统计
</b>
<p>查看业绩统计数据</p>
</div>
<img src="/img/op-i5.png" alt="">
</div>
</div>
</div>
</div>
</BasePage>
</template>
<script>
import ManagerPopup from "@/components/ManagerPopup.vue"
export default {
components: { ManagerPopup },
data() {
return {
managerPopupVisible: false
}
},
mounted() {
window.addEventListener('showManagerPopup', this.onShowManagerPopup)
window.addEventListener('closeManagerPopup', this.onCloseManagerPopup)
},
beforeUnmount() {
window.removeEventListener('showManagerPopup', this.onShowManagerPopup)
window.removeEventListener('closeManagerPopup', this.onCloseManagerPopup)
},
methods: {
onShowManagerPopup() {
this.managerPopupVisible = true
},
onCloseManagerPopup() {
this.managerPopupVisible = false
}
}
}
</script>

View File

@ -41,7 +41,7 @@ export default {
this.$get(`/v1/client/CNewsClient/${id}`).then(data => { this.$get(`/v1/client/CNewsClient/${id}`).then(data => {
this.article = data.data; this.article = data.data;
}).catch(err => { }).catch(err => {
this.$showFailToast(err.errmsg); this.$showFailToast(err.message);
}); });
}, },
setupImagePreview() { setupImagePreview() {

View File

@ -1,127 +1,134 @@
<template> <template>
<div class="gift"> <div class="gift">
<div class="logo_box">
<img src="/img/b_logo.png" alt="">
</div>
<div class="gift_box"> <div class="gift_box">
<div class="title_box"> <img class="tit_icon" src="/img/gift_title.png" alt="">
<img src="/img/more.png" alt=""> <img style="width: 81.33vw;margin-top: 8vw;" src="/img/gift_qy.png" alt="">
<b>等人已购买</b>
<!-- <div class="big_box"> -->
<div class="choose">
<img class="choose_img" :src="selected.id ? $file(selected.img) : '/img/gift_i1.png'">
<div class="choose_box">
<span class="title">
{{ selected.id ? selected.name : '泰古润报单礼包' }}
</span>
<div>
<img class="choose_icon" src="/img/fire.png" alt="">
<b>购买即可升级VIP</b>
</div>
<div class="choose_item" @click="showSelect = true">
<div class="btn1" v-if="selected.id">
<span>
<b>{{ selected.saleprice }}</b>
</span>
</div>
<div class="btn1" v-else>
<span>
<span style="font-size: 4vw;padding: 0 3vw;">待选</span>
</span>
</div>
<div class="btn2">
<span>
选择产品礼包
</span>
</div>
</div>
</div>
</div>
<!-- v-if="selected.id" -->
<div class="detail">
<!-- <div>
<span class="title">
购买产品数量
</span>
<span class="r">
<van-stepper v-model="value" />
</span>
</div> -->
<div>
<span class="title">
赠送积分
</span>
<b class="r"> 1980.00
<!-- {{
// (selected.saleprice * value || 0)?.toFixed(2)
}} -->
</b>
</div>
<div>
<span class="title">
赠送会员卡额度
</span>
<b class="r">
<!-- {{ (Number(selected.gongxianzhi) || 0)?.toFixed(2) }} -->
<span></span> 6000.00
</b>
</div>
</div> </div>
<div class="big_box"> <div class="address">
<div class="choose"> <!-- <div class="input">
<img class="choose_img" :src="selected.id ? $file(selected.img) : '/img/gift_i1.png'">
<div class="choose_box">
<span class="title">
{{ selected.id ? selected.name : '商务权益礼包' }}
</span>
<div>
<img class="choose_icon" src="/img/fire.png" alt="">
<b>购买即可参与推广活动</b>
</div>
<div class="choose_item" @click="showSelect = true">
<div class="btn1" v-if="selected.id">
<span>
<b>{{ selected.saleprice }}</b>
</span>
</div>
<div class="btn1" v-else>
<span>
<span style="font-size: 4vw;padding: 0 3vw;">待选</span>
</span>
</div>
<div class="btn2">
<span>
选择产品
</span>
</div>
</div>
</div>
</div>
<!-- v-if="selected.id" -->
<div class="detail">
<div>
<span class="title">
购买产品数量
</span>
<span class="r">
<van-stepper v-model="value" />
</span>
</div>
<div>
<span class="title">
购买金额总计
</span>
<b class="r">
{{
(selected.saleprice * value || 0)?.toFixed(2)
}}
</b>
</div>
<div>
<span class="title">
获得贡献值
</span>
<b class="r">
{{ (Number(selected.gongxianzhi) || 0)?.toFixed(2) }}
</b>
</div>
</div>
<div class="address">
<!-- <div class="input">
<div class="img"> <div class="img">
<img src="/img/gift_i2.png" alt=""> <img src="/img/gift_i2.png" alt="">
</div> </div>
<van-field v-model="address.username" placeholder="请填写报单人账号" type="phone" <van-field v-model="address.username" placeholder="请填写报单人账号" type="phone"
:rules="[{ required: true, message: '请填写报单人账号' }]" /> :rules="[{ required: true, message: '请填写报单人账号' }]" />
</div> --> </div> -->
<div class="input"> <div class="input">
<div class="img"> <div class="img">
<img src="/img/gift_i3.png" alt=""> <img src="/img/gift_i3.png" alt="">
</div>
<van-field v-model="address.ReceiveName" placeholder="请填写收货人姓名"
:rules="[{ required: true, message: '请填写收货人姓名' }]" />
<button class="btn" @click="$refs.ad_selector.showSelector()">
+ 导入已有地址
</button>
</div>
<div class="input">
<div class="img">
<img src="/img/gift_i4.png" alt="">
</div>
<van-field v-model="address.ReceivePhone" placeholder="请填写收货人电话" type="phone"
:rules="[{ required: true, message: '请填写收货人电话' }]" />
</div>
<div class="input">
<div class="img">
<img src="/img/gift_i5.png" alt="">
</div>
<van-field v-model="address.ReceiveRegionName" placeholder="请选择 / 省市 / 县" is-link
:rules="[{ required: true, message: '请选择 / 省市 / 县' }]" @click="showRegion = true" />
</div>
<div class="input">
<div class="img">
</div>
<van-field v-model="address.ReceiveAddress" placeholder="请填写收货人详细地址"
:rules="[{ required: true, message: '请填写收货人详细地址' }]" />
</div>
<div class="input">
<div class="img">
<img src="/img/gift_i6.png" alt="">
</div>
<van-field v-model="address.Remark" placeholder="备注选填,请先与商家协商一致" />
</div> </div>
<van-field v-model="address.ReceiveName" placeholder="请填写收货人姓名"
:rules="[{ required: true, message: '请填写收货人姓名' }]" />
<button class="btn" @click="$refs.ad_selector.showSelector()">
导入已有地址
</button>
</div>
<div class="input">
<div class="img">
<img src="/img/gift_i4.png" alt="">
</div>
<van-field v-model="address.ReceivePhone" placeholder="请填写收货人电话" type="phone"
:rules="[{ required: true, message: '请填写收货人电话' }]" />
</div>
<div class="input">
<div class="img">
<img src="/img/gift_i5.png" alt="">
</div>
<van-field v-model="address.ReceiveRegionName" placeholder="请选择 / 省市 / 县" is-link
:rules="[{ required: true, message: '请选择 / 省市 / 县' }]" @click="showRegion = true" />
</div>
<div class="input">
<div class="img">
</div>
<van-field v-model="address.ReceiveAddress" placeholder="请填写收货人详细地址"
:rules="[{ required: true, message: '请填写收货人详细地址' }]" />
</div>
<div class="input">
<div class="img">
<img src="/img/gift_i6.png" alt="">
</div>
<van-field v-model="address.Remark" placeholder="备注选填,请先与商家协商一致" />
</div> </div>
<button class="commit" @click="onShow()">
立即购买
</button>
<van-checkbox icon-size="2.667vw" class="agreement" v-model="checked" checked-color="#85cb58">
已阅读并同意<a @click.stop="showContract = true">保供臻选商务权益礼包电子协议</a>
</van-checkbox>
</div> </div>
<button class="commit" @click="onShow()">
立即购买
</button>
<span class="toList" @click="$navigate('TradeList?TradeArea=1')">
购买记录
</span>
<!-- <van-checkbox icon-size="2.667vw" class="agreement" v-model="checked" checked-color="#85cb58">
已阅读并同意<a @click.stop="showContract = true">保供臻选商务权益礼包电子协议</a>
</van-checkbox> -->
</div> </div>
</div> </div>
<!-- </div> -->
<van-action-sheet v-model:show="showSelect" class="popup-tuoke" safe-area-inset-bottom title=" " closeable <van-action-sheet v-model:show="showSelect" class="popup-tuoke" safe-area-inset-bottom title=" " closeable
style="padding: 0 0 0; min-height: 60%"> style="padding: 0 0 0; min-height: 60%">
@ -132,6 +139,9 @@
<div style="line-height: 10.267vw;"> <div style="line-height: 10.267vw;">
请选择礼包产品 请选择礼包产品
</div> </div>
<b style="color: #f00;font-size: 3.2vw;">
礼包产品一经售出概不退还
</b>
</div> </div>
</div> </div>
<div class="l" style="height: 85vw"> <div class="l" style="height: 85vw">
@ -171,7 +181,7 @@
</div> </div>
</div> </div>
<van-action-bar safe-area-inset-bottom style="border-top: solid 1px #f1f1f1;"> <van-action-bar safe-area-inset-bottom style="border-top: solid 1px #f1f1f1;">
<van-action-bar-button color="#19954d" :disabled="active == 0" text="确 定" <van-action-bar-button color="#ca2904" :disabled="active == 0" text="确 定"
@click="onSelectGoods"></van-action-bar-button> @click="onSelectGoods"></van-action-bar-button>
</van-action-bar> </van-action-bar>
</van-action-sheet> </van-action-sheet>
@ -266,10 +276,10 @@ export default {
return; return;
if (!this.$valid(this.address.ReceiveAddress, '请输入详细地址')) if (!this.$valid(this.address.ReceiveAddress, '请输入详细地址'))
return; return;
if (!this.checked) { // if (!this.checked) {
this.$showFailToast('请同意协议'); // this.$showFailToast('');
return; // return;
} // }
this.submitOrder(); this.submitOrder();
}, },
onShowDetail(e) { onShowDetail(e) {

View File

@ -1,165 +0,0 @@
<template>
<BasePage>
<div class="tradelist">
<div class="tabs">
<van-tabs class="area" v-model:active="TradeArea" color="#f00" title-active-color="#222"
title-inactive-color="#999" line-width="0" line-height=".667vw" @change="changeMall">
<van-tab v-for="i in mallList" :title="i.label" :name="i.value"></van-tab>
</van-tabs>
<van-tabs class="states" v-model:active="activeTab" color="#ca2904" title-active-color="#ca2904"
title-inactive-color="#000" line-width="4vw" line-height=".667vw" @change="onTabChange">
<van-tab title="全部" name=""></van-tab>
<van-tab v-for="i in tradeStates" :title="i.label" :name="String(i.value)"></van-tab>
</van-tabs>
</div>
<van-search v-model="searchParams.ordernum" left-icon=" " shape="round" placeholder="输入订单号搜索" @search="onSearch"
@clear="onClear">
<template #right-icon>
<van-icon name="/img/sort-search.png" @click="onSearch"></van-icon>
</template>
</van-search>
<BaseList ref="baseList" url="/v1/client/FOrdersClient" :params="searchParams" :parseData="res => res.data.items"
style="padding: 3.33vw;" @refresh="onRefresh">
<template #default="{ item }">
<div :key="item.ordernum" class="list">
<div class="code">
订单编号:{{ item.ordernum }}
<img src="/img/orderCopy.png" @click="$copyText(item.ordernum); $showSuccessToast('复制订单编号成功')" />
</div>
<div class="_info" v-for="list in (item.orderdetails || [])" :key="list.id">
<img :src="$file(list.proimg)">
<div class="_c">
<div class="_name">
<span>{{ list.proname }}</span>
</div>
<div class="_spec">
<span>{{ list.proskuname?.split(';').join('/') }}</span>
<p>x{{ list.buynums }}</p>
</div>
<div class="_price">
<span>¥{{ list.originalprice?.toFixed(2) }}</span>
<div>
<span style="margin-left: auto;">实付</span>
<b><span></span>{{ list.saleprice?.toFixed(2) }}</b>
</div>
</div>
</div>
</div>
<p v-if="item.remark" style="margin-bottom: 3vw;">
订单备注{{ item.remark }}
</p>
<div class="state">
<b :class="`b${item.state}`">
{{ item.statename }}
</b>
<div class="btn">
<a class="a2" v-if="item.state == 0" @click="cancelTrade(item)">
取消订单
</a>
<a class="a0" v-if="item.state == 0" @click="$navigate(`/Pay?ordernum=${item.ordernum}`)">
立即支付
</a>
<a class="a1" @click="$navigate(`/TradeDetail?ordernum=${item.ordernum}`)">
查看详情
</a>
</div>
</div>
</div>
</template>
</BaseList>
</div>
</BasePage>
</template>
<script>
export default {
name: 'TradeList',
data() {
return {
activeTab: '',
TradeArea: Number(this.$route.query.TradeArea) || 3,
searchParams: {
ordernum: '',
state: '',
mallstate: Number(this.$route.query.TradeArea) || 3,
},
tradeStates: [
],
mallList: [
{ value: 3, label: '礼包订单' },
{ value: 2, label: '商城订单' },
{ value: 1, label: '买单订单' },
],
}
},
mounted() {
this.getTradeStates();
},
watch: {
TradeArea(val) {
this.searchParams.mallstate = val;
},
'$route.query.state': {
handler(newVal) {
if (newVal !== undefined && newVal !== '') {
this.activeTab = String(newVal);
// this.getTradeStates();
} else {
this.activeTab = '';
}
}
}
},
methods: {
back() {
this.$router.push('/My')
},
onTabChange(name) {
this.searchParams.state = name;
this.$refs.baseList?.refresh();
},
changeMall(name) {
this.searchParams.mallstate = Number(name) || 3;
this.searchParams.state = '';
this.$refs.baseList?.refresh();
},
onSearch() {
this.$refs.baseList?.refresh();
},
onClear() {
this.searchParams.ordernum = '';
this.$refs.baseList?.refresh();
},
getTradeStates() {
this.$get('/v1/client/FOrdersClient/orderstate').then(res => {
this.tradeStates = res.data;
this.$nextTick(() => {
const stateFromRoute = this.$route.query.state;
if (stateFromRoute !== undefined && stateFromRoute !== '') {
this.activeTab = String(stateFromRoute);
this.searchParams.state = stateFromRoute;
}
});
}).catch((err) => {
this.$showFailToast(err.message || '获取订单状态失败');
});
},
onRefresh() {
},
cancelTrade(item) {
this.$showConfirmDialog({
title: "是否确认取消订单",
}).then(() => {
this.$put(`/v1/client/FOrdersClient/${item.ordernum}/cancel`).then(() => {
this.$showSuccessToast('取消订单成功');
this.$refs.baseList?.refresh();
}).catch(err => {
this.$showFailToast(err.errmsg || '取消失败');
});
}).catch(() => { });
},
}
}
</script>

View File

@ -34,7 +34,7 @@
</van-cell> </van-cell>
<!-- 微信支付 --> <!-- 微信支付 -->
<van-cell title="微信支付" is-link @click="payMethod = ['wechat']"> <van-cell title="微信支付" v-if="!hide" is-link @click="payMethod = ['wechat']">
<template #icon> <template #icon>
<img class="pay-icon" src="/img/pay_weixin.png" /> <img class="pay-icon" src="/img/pay_weixin.png" />
</template> </template>
@ -43,7 +43,7 @@
</template> </template>
</van-cell> </van-cell>
<van-cell title="快捷支付HJ(更顺畅)" is-link @click="payMethod = ['wechat']"> <van-cell title="快捷支付HJ(更顺畅)" v-if="!hide" is-link @click="payMethod = ['wechat']">
<template #icon> <template #icon>
<img class="pay-icon" src="/img/pay_bankcard.png" /> <img class="pay-icon" src="/img/pay_bankcard.png" />
</template> </template>
@ -83,6 +83,7 @@ export default {
needpay: 0, needpay: 0,
state: 0, state: 0,
}, },
hide: true,
wallet: { wallet: {
totalsum: 0, totalsum: 0,
}, },
@ -113,7 +114,7 @@ export default {
const walletRes = await this.$get('/v1/client/DUsermoneysClient/statistics'); const walletRes = await this.$get('/v1/client/DUsermoneysClient/statistics');
this.wallet = walletRes.data; this.wallet = walletRes.data;
} catch (err) { } catch (err) {
this.$showFailToast(err.errmsg || '加载失败'); this.$showFailToast(err.message || '加载失败');
} }
}, },
async doPay() { async doPay() {
@ -130,7 +131,7 @@ export default {
async balancePay() { async balancePay() {
try { try {
// //
const res = await this.$get(`/v1/client/FOrdersClient/${this.ordernum}/payali`); const res = await this.$get(`/v1/client/FOrdersClient/${this.ordernum}/payyue`);
if (res.data) { if (res.data) {
location.href = res.data; location.href = res.data;
} }
@ -142,7 +143,7 @@ export default {
}, 1000); }, 1000);
} }
} catch (err) { } catch (err) {
this.$showFailToast(err.errmsg || '支付失败'); this.$showFailToast(err.message || '支付失败');
} }
}, },
// //
@ -157,7 +158,7 @@ export default {
} }
this.showPayResult = true; this.showPayResult = true;
} catch (err) { } catch (err) {
this.$showFailToast(err.errmsg || '支付失败'); this.$showFailToast(err.message || '支付失败');
} }
}, },
// //
@ -169,7 +170,7 @@ export default {
} }
this.showPayResult = true; this.showPayResult = true;
} catch (err) { } catch (err) {
this.$showFailToast(err.errmsg || '支付失败'); this.$showFailToast(err.message || '支付失败');
} }
}, },
onPayCompleted() { onPayCompleted() {

View File

@ -41,7 +41,7 @@
<div class="top"> <div class="top">
<span>商品金额</span> <span>商品金额</span>
<b class="r"><span></span>{{ ((product.saleprice || 0) * (product.buynums || 1))?.toFixed(2) <b class="r"><span></span>{{ ((product.saleprice || 0) * (product.buynums || 1))?.toFixed(2)
}}</b> }}</b>
</div> </div>
<van-radio-group v-model="checked" checked-color="#ca2904"> <van-radio-group v-model="checked" checked-color="#ca2904">
<van-radio name="1" label-position="left"> <van-radio name="1" label-position="left">
@ -197,7 +197,7 @@ export default {
this.$showSuccessToast('提交成功'); this.$showSuccessToast('提交成功');
this.$navigate('/Pay?ordernum=' + data.data); this.$navigate('/Pay?ordernum=' + data.data);
}).catch(err => { }).catch(err => {
this.$showFailToast(err.errmsg); this.$showFailToast(err.message);
}).finally(() => { }).finally(() => {
this.isloading = false; this.isloading = false;
}); });

View File

@ -118,7 +118,7 @@ export default {
const res = await this.$get(`/v1/client/FOrdersClient/${this.ordernum}`); const res = await this.$get(`/v1/client/FOrdersClient/${this.ordernum}`);
this.data = res.data; this.data = res.data;
} catch (err) { } catch (err) {
this.$showFailToast(err.errmsg || '加载失败'); this.$showFailToast(err.message || '加载失败');
} }
}, },
} }

View File

@ -1,165 +1,215 @@
<template> <template>
<BasePage :back="back"> <BasePage>
<div class="order"> <div class="tradelist">
<div class="top"> <div class="tabs">
<van-tabs class="area" v-model:active="TradeArea" color="#f00" title-active-color="#f00" <van-tabs class="area" v-model:active="TradeArea" color="#f00" title-active-color="#222"
title-inactive-color="#000" line-width="4vw" line-height=".667vw" @change="changeMall"> title-inactive-color="#999" line-width="0" line-height=".667vw" @change="changeMall">
<van-tab v-for="i in mallList" :title="i.label" :name="i.value"></van-tab> <van-tab v-for="i in mallList" :title="i.label" :name="i.value"></van-tab>
</van-tabs> </van-tabs>
<van-tabs v-model:active="activeTab" color="#f00" title-active-color="#f00" title-inactive-color="#000" <van-tabs class="states" v-model:active="activeTab" color="#ca2904" title-active-color="#ca2904"
line-width="4vw" line-height=".667vw" @change="onTabChange"> title-inactive-color="#000" line-width="4vw" line-height=".667vw" @change="onTabChange">
<van-tab title="全部" name=""></van-tab> <van-tab title="全部" name=""></van-tab>
<van-tab v-for="i in tradeStates" :title="i.label" :name="String(i.value)"></van-tab> <van-tab v-for="i in tradeStates" :title="i.label" :name="String(i.value)"></van-tab>
</van-tabs> </van-tabs>
<van-search v-model="searchParams.ordernum" left-icon=" " shape="round" placeholder="输入订单号搜索" </div>
@search="onSearch" @clear="onClear"> <van-search v-model="searchParams.ordernum" left-icon=" " shape="round" placeholder="输入订单号搜索" @search="onSearch"
<template #right-icon> @clear="onClear">
<van-icon name="/img/sort-search.png" @click="onSearch"></van-icon> <template #right-icon>
</template> <van-icon name="/img/sort-search.png" @click="onSearch"></van-icon>
</van-search> </template>
</van-search>
<BaseList v-if="TradeArea !== 2" ref="baseList" url="/v1/client/FOrdersClient" :params="searchParams"
:parseData="res => res.data.items" style="padding: 3.33vw;" @refresh="onRefresh">
<template #default="{ item }">
<div class="list">
<div class="order_box">
<span>
订单编号:{{ item.ordernum }}
</span>
<img src="/img/copy_b.png" @click="$copyText(item.ordernum); $showSuccessToast('复制成功')" alt="">
</div> </div>
<BaseList ref="baseList" url="/v1/client/FOrdersClient" :params="searchParams" <div class="goods_box">
:parseData="res => res.data.items" class="b_l_w" style="padding: 3.33vw;" @refresh="onRefresh"> <img :src="$file(item.proimg)" alt="">
<template #default="{ item }">
<div :key="item.ordernum" class="list"> <div class="goods_info">
<div class="code"> <div class="tit">{{ item.proname }}</div>
订单编号:{{ item.ordernum }} <div class="spec">
<img src="/img/orderCopy.png" <span>{{ item.proskuname }}</span>
@click="$copyText(item.ordernum); $showSuccessToast('复制订单编号成功')" /> <p>x{{ item.buynums }}</p>
</div> </div>
<div class="_info" v-for="list in (item.orderdetails || [])" :key="list.id"> <div class="concession">
<img :src="$file(list.proimg)"> <span>¥{{ item.realmoney?.toFixed(2) }}</span>
<div class="_c"> <p v-if="item.discountratio">{{ item.discountratio }}%让利</p>
<div class="_name"> </div>
<span>{{ list.proname }}</span> </div>
</div> </div>
<div class="_spec">
<span>{{ list.proskuname?.split(';').join('/') }}</span> <div class="price">
<p>x{{ list.buynums }}</p> 实付<span><b>9999.05</b></span>
</div> </div>
<div class="_price">
<b><span></span>{{ list.saleprice?.toFixed(2) }}</b> <div class="state_box">
</div> <b :class="'b' + item.state">
</div> {{ item.statename }}
</div> </b>
<p v-if="item.remark" style="margin-bottom: 3vw;">
订单备注{{ item.remark }} <div class="btn_box">
</p> <button v-if="item.state === 0">取消订单</button>
<div class="state"> <button v-if="item.state === 3">查看物流</button>
<b :class="`b${item.state}`"> <button @click="$navigate(`TradeDetail?ordernum=${item.ordernum}`)">查看详情</button>
{{ item.statename }} <button v-if="item.state === 0">立即支付</button>
</b> </div>
<div class="btn"> </div>
<a class="a2" v-if="item.state == 0" @click="cancelTrade(item)"> </div>
取消订单 </template>
</a> </BaseList>
<a class="a0" v-if="item.state == 0"
@click="$navigate(`/Pay?ordernum=${item.ordernum}`)"> <BaseList v-else ref="baseList" url="/v1/client/FOrdersshopClient" :params="searchParams"
立即支付 :parseData="res => res.data.items" style="padding: 3.33vw;" @refresh="onRefresh">
</a> <template #default="{ item }">
<a class="a1" @click="$navigate(`/TradeDetail?ordernum=${item.ordernum}`)"> <div class="list">
查看详情 <div class="merchant_info">
</a> <img class="icon" :src="$file(item.shopimg)" alt="">
</div> <div class="inf">
</div> <span>{{ item.shopname }}</span>
</div> <div>
</template> <p>{{ item.ordermoney?.toFixed(2) }}</p>
</BaseList> <span class="dr" v-if="item.discountratio">
</div> {{ item.discountratio }}%让利
</BasePage> </span>
</div>
</div>
</div>
<div class="price">
实付<span><b>{{ item.ordermoney?.toFixed(2) }}</b></span>
</div>
<div class="detail_box">
<div>
<span>订单编号:</span>
<span class="r">
{{ item.ordernum }}
<img src="/img/copy_b.png" @click="$copyText(item.ordernum); $showSuccessToast('复制成功')" alt="">
</span>
</div>
<div>
<span>下单时间:</span>
<span class="r">
{{ $formatGMT(item.addtime, 'yyyy-MM-dd HH:mm:ss') }}
</span>
</div>
</div>
<div class="state_box">
<b :class="'b' + item.state">
{{ item.statename }}
</b>
<div class="btn_box">
<button @click="$navigate(`CheckoutTrade?ordernum=${item.ordernum}&type=user`)">查看详情</button>
</div>
</div>
</div>
</template>
</BaseList>
</div>
</BasePage>
</template> </template>
<script> <script>
import BaseList from '../../components/BaseList.vue';
export default { export default {
name: 'TradeList', name: 'TradeList',
data() { data() {
return { return {
activeTab: '', activeTab: '',
TradeArea: Number(this.$route.query.TradeArea) || 3, TradeArea: Number(this.$route.query.TradeArea) || 3,
searchParams: { searchParams: {
ordernum: '', ordernum: '',
state: '', state: '',
mallstate: Number(this.$route.query.TradeArea) || 3, mallstate: Number(this.$route.query.TradeArea) || 3,
}, },
tradeStates: [ tradeStates: [
], ],
mallList: [ mallList: [
{ value: 3, label: '商城订单' }, { value: 3, label: '商城订单' },
{ value: 2, label: '助农订单' }, { value: 1, label: '礼包订单' },
{ value: 1, label: '商务订单' }, { value: 2, label: '买单订单' },
], ],
}
},
mounted() {
this.getTradeStates();
},
watch: {
TradeArea(val) {
this.searchParams.mallstate = val;
},
'$route.query.state': {
handler(newVal) {
if (newVal !== undefined && newVal !== '') {
this.activeTab = String(newVal);
// this.getTradeStates();
} else {
this.activeTab = '';
}
}
}
},
methods: {
back() {
this.$router.push('/My')
},
onTabChange(name) {
this.searchParams.state = name;
this.$refs.baseList?.refresh();
},
changeMall(name) {
this.searchParams.mallstate = Number(name) || 3;
this.searchParams.state = '';
this.$refs.baseList?.refresh();
},
onSearch() {
this.$refs.baseList?.refresh();
},
onClear() {
this.searchParams.ordernum = '';
this.$refs.baseList?.refresh();
},
getTradeStates() {
this.$get('/v1/client/FOrdersClient/orderstate').then(res => {
this.tradeStates = res.data;
this.$nextTick(() => {
const stateFromRoute = this.$route.query.state;
if (stateFromRoute !== undefined && stateFromRoute !== '') {
this.activeTab = String(stateFromRoute);
this.searchParams.state = stateFromRoute;
}
});
}).catch((err) => {
this.$showFailToast(err.message || '获取订单状态失败');
});
},
onRefresh() {
},
cancelTrade(item) {
this.$showConfirmDialog({
title: "是否确认取消订单",
}).then(() => {
this.$put(`/v1/client/FOrdersClient/${item.ordernum}/cancel`).then(() => {
this.$showSuccessToast('取消订单成功');
this.$refs.baseList?.refresh();
}).catch(err => {
this.$showFailToast(err.errmsg || '取消失败');
});
}).catch(() => { });
},
} }
},
mounted() {
this.getTradeStates();
},
watch: {
TradeArea(val) {
this.searchParams.mallstate = val;
},
'$route.query.state': {
handler(newVal) {
if (newVal !== undefined && newVal !== '') {
this.activeTab = String(newVal);
// this.getTradeStates();
} else {
this.activeTab = '';
}
}
}
},
methods: {
back() {
this.$router.push('/My')
},
onTabChange(name) {
this.searchParams.state = name;
this.$refs.baseList?.refresh();
},
changeMall(name) {
this.searchParams.mallstate = Number(name) || 3;
this.searchParams.state = '';
this.$refs.baseList?.refresh();
},
onSearch() {
this.$refs.baseList?.refresh();
},
onClear() {
this.searchParams.ordernum = '';
this.$refs.baseList?.refresh();
},
getTradeStates() {
this.$get('/v1/client/FOrdersClient/orderstate').then(res => {
this.tradeStates = res.data;
this.$nextTick(() => {
const stateFromRoute = this.$route.query.state;
if (stateFromRoute !== undefined && stateFromRoute !== '') {
this.activeTab = String(stateFromRoute);
this.searchParams.state = stateFromRoute;
}
});
}).catch((err) => {
this.$showFailToast(err.message || '获取订单状态失败');
});
},
onRefresh() {
},
cancelTrade(item) {
this.$showConfirmDialog({
title: "是否确认取消订单",
}).then(() => {
this.$put(`/v1/client/FOrdersClient/${item.ordernum}/cancel`).then(() => {
this.$showSuccessToast('取消订单成功');
this.$refs.baseList?.refresh();
}).catch(err => {
this.$showFailToast(err.message || '取消失败');
});
}).catch(() => { });
},
}
} }
</script> </script>

View File

@ -1,249 +0,0 @@
<template>
<BasePage>
<van-cell-group class="b_l_w" style="margin-bottom: 132px;">
<van-swipe-cell v-for="item in data" :key="item.id">
<van-cell>
<template #title>
<div class="bank-card">
<img class="bank-icon"
:src="item.bankid == '91' ? '/img/AliPay.png' : '/img/transfer-i2.png'" fit="cover"
height="30" width="30" />
<div style="display: flex; flex-direction: column; margin-left: 6px">
<span style=" font-size: 6.667vw; display: flex; align-items: center;">
<span style="font-size: 4.667vw;">{{ item.realname || item.RealName }}
{{ item.bankcellphone || item.CardCode }}</span>
</span>
</div>
</div>
</template>
</van-cell>
<template #right>
<van-button style="height: 100%;" square text="删除" type="danger" class="delete-button"
@click="deleted(item)" />
</template>
</van-swipe-cell>
</van-cell-group>
<!-- <div class="bank-card-desc">
<span style="color: red">注意</span>绑定添加银行卡必须保证银行卡号银行预留手机号要同一个人信息才能添加成功仅限<span
style="color: red">添加成功</span>状态的银行卡才可用于提现添加不成功的银行卡无法用于提现
</div> -->
<van-action-sheet v-model:show="showAddAliPayPopup" :title="'新增支付宝账户'" style="min-height: 80vw;">
<div class="bankcard-edit">
<van-form @submit="save" label-align="top">
<van-cell-group inset>
<van-field v-model="tempData.Realname" label="真实姓名" placeholder="请输入支付宝账号绑定真实姓名"
:rules="[{ required: true, message: '请填写真实姓名' }]" clearable required />
<van-field v-model="tempData.Bankcellphone" label="支付宝账号" placeholder="请输入支付宝账号"
:rules="[{ required: true, message: '请填写支付宝账号' }]" clearable required />
<div class="w"
style="position: fixed;left:0;bottom: 0;padding: 3.333vw;border-top:1px solid #f5f5f5">
<van-button block round style="width: 100%" type="primary" native-type="save"
:loading="saving">保存</van-button>
</div>
</van-cell-group>
</van-form>
</div>
</van-action-sheet>
<van-action-sheet v-model:show="showAddPopup" :title="'新增银行卡'">
<div class="bankcard-edit">
<van-form @submit="saveBanks" label-align="top">
<van-cell-group inset>
<van-field v-model="tempData.RealName" label="姓名" placeholder="请输入真实姓名"
:rules="[{ required: true, message: '请填写真实姓名' }]" clearable required />
<van-field v-model="tempData.IDCode" label="身份证" placeholder="请输入身份证号"
:rules="[{ required: true, message: '请输入身份证号' }]" clearable required
:formatter="formatter" />
<van-field v-model="tempData.IatDate" label="身份证起始日期" placeholder="请选择身份证起始日期"
:rules="[{ required: true, message: '请选择身份证起始日期' }]" clearable required is-link
@click="tempData.obj = 'IatDate'; showDate = true;" readonly />
<van-field class="maxDate" name="radio" label="身份证截止日期" required>
<template #input>
<van-radio-group v-model="checked" direction="horizontal">
<van-radio :name="0">短期</van-radio>
<van-radio :name="1">长期</van-radio>
</van-radio-group>
</template>
</van-field>
<van-field v-model="tempData.ExpDate" v-if="!checked" label=" " placeholder="请选择身份证截止日期"
:rules="[{ required: true, message: '请选择身份证起截止日期' }]" clearable is-link
@click="tempData.obj = 'ExpDate'; showDate = true;" readonly />
<van-field v-model="tempData.Phone" label="手机号" placeholder="请输入手机号"
:rules="[{ required: true, message: '请填写手机号' }]" type="phone" clearable required
:formatter="formatter" />
<van-field v-model="tempData.CardCode" label="银行卡号" placeholder="请输入银行卡号"
:rules="[{ required: true, message: '请填写银行卡号' }]" clearable required
:formatter="formatter" />
<van-field v-model="tempData.ReceiveRegionName" label="开户地区" placeholder="请选择开户地区"
:rules="[{ required: true, message: '请选择开户地区' }]" clearable required is-link
@click="showRegion = true;" readonly />
<van-cell>
<template #title>
<van-button style="width: 100%" round type="primary" native-type="saveBanks"
:loading="saving">保存</van-button>
</template>
</van-cell>
</van-cell-group>
</van-form>
</div>
</van-action-sheet>
<van-action-bar>
<van-action-bar-button type="primary" text="添加支付宝" @click="addAliPay" />
<!-- <van-action-bar-button type="success" text="添加银行卡" @click="addBanks" /> -->
<van-action-bar-button type="danger" text="去提现" @click="cashout" />
</van-action-bar>
<van-popup v-model:show="showDate" position="bottom">
<van-date-picker v-model="currentDate" title="选择年月日" :columns-type="['year', 'month', 'day']"
:min-date="minDate" :max-date="maxDate" @confirm="onconfirm" @cancel="showDate = false" />
</van-popup>
<van-popup v-model:show="showRegion" round position="bottom">
<van-cascader v-model="region" title="请选择地区" :options="options" :field-names="defaultProps"
@change="onChange" @finish="onFinish" @close="showRegion = false" />
</van-popup>
</BasePage>
</template>
<script>
export default {
name: 'CashoutAccount',
mounted() {
this.init();
},
data() {
return {
data: [
],
showAddAliPayPopup: false,
showAddPopup: false,
bankData: [],
tempData: {},
saving: false,
showDate: false,
currentDate: [`${new Date().getFullYear()}`, `${new Date().getMonth() + 1}`],
minDate: new Date('1900/01/01'),
maxDate: new Date('2099/12/31'),
showRegion: false,
options: [],
defaultProps: {
value: "val",
},
checked: 0,
}
},
methods: {
init() {
this.$get('/v1/client/DUserbankcardsClient').then(data => {
this.data = data.data;
}).catch(err => {
this.$showFailToast(err.errmsg);
});
},
formatter(value) {
return value.replace(/\s/g, '');
},
onconfirm(value) {
this.tempData[this.tempData.obj] = this.currentDate.join('-');
this.showDate = false;
},
onChange(e) {
if (e.selectedOptions[e.tabIndex].leaf) {
e.selectedOptions[e.tabIndex].children = null;
this.showRegion = false;
return;
}
},
onFinish(e) {
this.showRegion = false;
this.tempData.CardProvince = e.selectedOptions.map(x => x.val)[0];
this.tempData.CardCity = e.selectedOptions.map(x => x.val)[1];
this.tempData.ReceiveRegionName = e.selectedOptions.map(x => x.text).join('');
},
addAliPay() {
this.tempData = new Object();
this.showAddAliPayPopup = true;
},
addBanks() {
this.tempData = new Object();
this.showAddPopup = true;
},
save() {
this.saving = true;
this.$post('/v1/client/DUserbankcardsClient', { ...this.tempData, Bankid: 91 }).then(data => {
this.$showSuccessToast('添加成功');
this.tempData = {};
// this.$refs.BaseList.refresh();
this.showAddAliPayPopup = false;
this.init();
}).catch(err => {
this.$showFailToast(err.errmsg);
}).finally(() => {
this.saving = false;
});
},
saveBanks() {
if (!this.$validPhone(this.tempData.Phone)) {
this.$showFailToast('手机号格式错误');
return;
}
if (!this.$validIdCard(this.tempData.IDCode)) {
this.$showFailToast('身份证格式错误');
return;
}
this.saving = true;
this.tempData.IatDate = this.tempData.IatDate.replaceAll('-', '');
if (!this.checked)
this.tempData.ExpDate = this.tempData.ExpDate.replaceAll('-', '');
else
this.tempData.ExpDate = '';
this.$post('Member/AddHuifuBankCard', this.tempData).then(res => {
this.$showSuccessToast('添加成功');
this.tempData = {};
this.$refs.BaseList.refresh();
this.showAddPopup = false;
}).catch(err => {
this.$showFailToast(err.errmsg);
}).finally(() => {
this.saving = false;
});
},
deleted(e) {
this.$del(`/v1/client/DUserbankcardsClient/${e.id}`).then(data => {
this.$showSuccessToast('删除成功');
this.init();
}).catch(err => {
this.$showFailToast(err.errmsg);
});
},
cashout() {
location.href = '#/Cashout';
},
}
}
</script>
<style>
.bank-card {
border-radius: 1.333vw;
display: flex;
align-items: center;
padding: 3.333vw;
.bank-icon {
margin-right: 10px;
}
}
.bank-card-desc {
position: fixed;
bottom: 40px;
padding: 3.333vw 3.333vw;
font-size: 3.333vw;
background: #fff;
}
</style>

View File

@ -0,0 +1,72 @@
<template>
<BasePage>
<div class="checkout">
<div class="shopinfo">
<img class="icon" :src="$file()" alt="">
<div class="inf">
<b>完美日记旗舰店</b>
<div class="hl">
<img src="/img/buybill.png" alt="">
<span>20%</span>
</div>
</div>
</div>
<div class="paynums_box">
<b class="tit">
买单金额
</b>
<div class="input_box">
¥<input type="number" placeholder="请输入买单金额">
</div>
</div>
<div class="deduction_box">
<van-radio-group v-model="checked">
<van-cell-group inset center>
<van-cell center title="积分抵扣" icon="/img/point_icon.png" clickable @click="checked = '1'">
<template #right-icon>
<span class="canuse">25000.00可用</span>
<span class="cantuse">暂无可用</span>
<span v-if="checked === '1'" class="use">-500.00</span>
<van-radio name="1" />
</template>
</van-cell>
<van-cell title="会员卡抵扣" icon="/img/vip_icon.png" clickable @click="checked = '2'">
<template #right-icon>
<span class="canuse">25000.00可用</span>
<span class="cantuse">暂无可用</span>
<span v-if="checked === '2'" class="use">-500.00</span>
<van-radio name="2" />
</template>
</van-cell>
</van-cell-group>
</van-radio-group>
<div class="price">
<p>
实付
</p>
<span><b>500.00</b></span>
</div>
</div>
<button class="payfor">
去支付
</button>
</div>
</BasePage>
</template>
<script>
export default {
data() {
return {
checked: '1',
}
}
}
</script>

View File

@ -0,0 +1,72 @@
<template>
<BasePage>
<div class="checkout">
<div class="shopinfo">
<img class="icon" :src="$file()" alt="">
<div class="inf">
<b>完美日记旗舰店</b>
<div class="hl">
<img src="/img/buybill.png" alt="">
<span>20%</span>
</div>
</div>
</div>
<div class="paynums_box">
<b class="tit">
买单金额
</b>
<div class="input_box">
¥<input type="number" placeholder="请输入买单金额">
</div>
</div>
<div class="deduction_box">
<van-radio-group v-model="checked">
<van-cell-group inset center>
<van-cell center title="积分抵扣" icon="/img/point_icon.png" clickable @click="checked = '1'">
<template #right-icon>
<span class="canuse">25000.00可用</span>
<span class="cantuse">暂无可用</span>
<span v-if="checked === '1'" class="use">-500.00</span>
<van-radio name="1" />
</template>
</van-cell>
<van-cell title="会员卡抵扣" icon="/img/vip_icon.png" clickable @click="checked = '2'">
<template #right-icon>
<span class="canuse">25000.00可用</span>
<span class="cantuse">暂无可用</span>
<span v-if="checked === '2'" class="use">-500.00</span>
<van-radio name="2" />
</template>
</van-cell>
</van-cell-group>
</van-radio-group>
<div class="price">
<p>
实付
</p>
<span><b>500.00</b></span>
</div>
</div>
<button class="payfor">
去支付
</button>
</div>
</BasePage>
</template>
<script>
export default {
data() {
return {
checked: '1',
}
}
}
</script>

View File

@ -1,4 +1,5 @@
<template> <template>
<ManagerPopup v-model="managerPopupVisible" />
<div class="my"> <div class="my">
<div class="top"> <div class="top">
<img class="avatar" v-if="data.userimg" :src="$file(data.userimg)"> <img class="avatar" v-if="data.userimg" :src="$file(data.userimg)">
@ -11,19 +12,18 @@
</div> </div>
<div class="box"> <div class="box">
<div class="vBicon vip"> <div class="vBicon vip">
<!-- {{ data.userlevelname }} --> {{ data.userlevelname }}
V1
</div> </div>
<div class="vBicon svip"> <div class="vBicon svip" v-if="data.col3">
{{ data.col2name }} SVIP {{ data.col3name }}
</div> </div>
<div class="vBicon director"> <div class="vBicon director" v-if="data.col1">
{{ data.col2name }}董事 {{ data.col1name }}
</div> </div>
</div> </div>
</div> </div>
<!-- v-if="data.isstudio" --> <!-- v-if="data.isstudio" -->
<div class="shopcenter" @click="$showManagerPopup()"> <div class="shopcenter" v-if="data.col2 || data.isshop" @click="$showManagerPopup()">
<span> <span>
管理中心 管理中心
<van-icon name="arrow" /> <van-icon name="arrow" />
@ -37,7 +37,7 @@
<img src="/img/my_w1.png" alt=""> <img src="/img/my_w1.png" alt="">
<span>余额</span> <span>余额</span>
</div> </div>
<b>1377.00</b> <b>{{ data.zijin?.toFixed(2) }}</b>
</div> </div>
<div @click="$navigate('CV')"> <div @click="$navigate('CV')">
@ -45,7 +45,7 @@
<img src="/img/my_w2.png" alt=""> <img src="/img/my_w2.png" alt="">
<span>会员卡额度</span> <span>会员卡额度</span>
</div> </div>
<b>13777.00</b> <b>{{ data.xiaofeiquan?.toFixed(2) }}</b>
</div> </div>
<div @click="$navigate('Point')"> <div @click="$navigate('Point')">
@ -53,7 +53,7 @@
<img src="/img/my_w3.png" alt=""> <img src="/img/my_w3.png" alt="">
<span>积分</span> <span>积分</span>
</div> </div>
<b>1377.00</b> <b>{{ data.xiaofeijifen?.toFixed(2) }}</b>
</div> </div>
</div> </div>
@ -67,19 +67,19 @@
</span> </span>
</div> </div>
<div class="c"> <div class="c">
<van-badge :dot="data.UnPayQty > 0" :offset="[3, -3]"> <van-badge :dot="data.ordercountdaifukuan > 0" :offset="[3, -3]">
<div class="st_box" @click="$navigate(`TradeList?TradeArea=3&state=0`)"> <div class="st_box" @click="$navigate(`TradeList?TradeArea=3&state=0`)">
<img src="/img/my_o1.png"> <img src="/img/my_o1.png">
<p>待付款</p> <p>待付款</p>
</div> </div>
</van-badge> </van-badge>
<van-badge :dot="data.UnSendQty > 0" :offset="[3, -3]"> <van-badge :dot="data.ordercountdaifahuo > 0" :offset="[3, -3]">
<div class="st_box" @click="$navigate(`TradeList?TradeArea=3&state=1`)"> <div class="st_box" @click="$navigate(`TradeList?TradeArea=3&state=1`)">
<img src="/img/my_o2.png"> <img src="/img/my_o2.png">
<p>待发货</p> <p>待发货</p>
</div> </div>
</van-badge> </van-badge>
<van-badge :dot="data.SendingQty > 0" :offset="[3, -3]"> <van-badge :dot="data.ordercountdaishouhuo > 0" :offset="[3, -3]">
<div class="st_box" @click="$navigate(`TradeList?TradeArea=3&state=3`)"> <div class="st_box" @click="$navigate(`TradeList?TradeArea=3&state=3`)">
<img src="/img/my_o3.png"> <img src="/img/my_o3.png">
<p>待收货</p> <p>待收货</p>
@ -93,7 +93,7 @@
</div> </div>
<div class="fast_to"> <div class="fast_to">
<img src="/img/my_f1.jpg" @click="$navigate('Invite')" alt=""> <img src="/img/my_f1.jpg" @click="toInvite()" alt="">
<img src="/img/my_f2.jpg" @click="$navigate('Team')" alt=""> <img src="/img/my_f2.jpg" @click="$navigate('Team')" alt="">
<img src="/img/my_f3.jpg" @click="$navigate('Allow')" alt=""> <img src="/img/my_f3.jpg" @click="$navigate('Allow')" alt="">
<img src="/img/my_f4.jpg" @click="$navigate('Certificate')" alt=""> <img src="/img/my_f4.jpg" @click="$navigate('Certificate')" alt="">
@ -178,7 +178,13 @@
<van-action-sheet v-model:show="changePasswordVisibled" title="修改登录密码"> <van-action-sheet v-model:show="changePasswordVisibled" title="修改登录密码">
<div class="my-setting-password"> <div class="my-setting-password">
<van-cell-group inset> <van-cell-group inset>
<van-field v-model="tempPasswordData.oldpwd" type="password" label="原密码" placeholder="请输入原密码" required /> <van-field style="white-space: nowrap;" v-model="tempPasswordData.code" center clearable label-width="24vw"
:label="this.data.cellphone" placeholder="请输入短信验证码">
<template #button>
<van-button @click="getSmsCode" color="#ca2904" size="small" type="primary" :disabled="isSendCode">{{
isSendCode ? `${sendCodeTime}s` : '获取验证码' }}</van-button>
</template>
</van-field>
<van-field v-model="tempPasswordData.newpwd" type="password" label="新密码" placeholder="请输入新密码" required /> <van-field v-model="tempPasswordData.newpwd" type="password" label="新密码" placeholder="请输入新密码" required />
<van-field v-model="tempPasswordData.repwd" type="password" label="确认密码" placeholder="请再次输入新密码" required /> <van-field v-model="tempPasswordData.repwd" type="password" label="确认密码" placeholder="请再次输入新密码" required />
<van-cell size="large"> <van-cell size="large">
@ -205,20 +211,30 @@
</template> </template>
<script> <script>
import ManagerPopup from "@/components/ManagerPopup.vue"
export default { export default {
name: 'My', name: 'My',
components: { ManagerPopup },
computed: { computed: {
}, },
mounted() { mounted() {
this.init(); this.init();
window.addEventListener('showManagerPopup', this.onShowManagerPopup)
window.addEventListener('closeManagerPopup', this.onCloseManagerPopup)
},
beforeUnmount() {
window.removeEventListener('showManagerPopup', this.onShowManagerPopup)
window.removeEventListener('closeManagerPopup', this.onCloseManagerPopup)
}, },
data() { data() {
return { return {
managerPopupVisible: false,
data: { userimg: '', username: '' }, data: { userimg: '', username: '' },
settingVisibled: false, settingVisibled: false,
changePasswordVisibled: false, changePasswordVisibled: false,
tempPasswordData: { tempPasswordData: {
oldpwd: '', code: '',
newpwd: '', newpwd: '',
repwd: '', repwd: '',
}, },
@ -228,16 +244,54 @@ export default {
showFollow: false, showFollow: false,
hf_data: {}, hf_data: {},
hfLoading: true, hfLoading: true,
isSendCode: false,
sendCodeTime: 0,
} }
}, },
methods: { methods: {
init() { init() {
this.$get('/v1/client/DUsersClient').then(data => { const code = this.$route.query.code
// console.log(data); if (code) {
this.data = data.data; this.$post('/v1/client/AuthClient/loginwxweb', { code }).then(res => {
this.$ls.set('cellphone', data.data.cellphone); this.$showSuccessToast('登录成功')
this.$ls.set('userimg', data.data.userimg); }).catch(err => {
this.$ls.set('nickname', data.data.nickname) this.$showFailToast(err.message || '微信登录失败')
})
}
Promise.all(
[
this.$get('/v1/client/DUsersClient').then(data => {
// console.log(data);
this.data = data.data;
this.$ls.set('cellphone', data.data.cellphone);
this.$ls.set('userimg', data.data.userimg);
this.$ls.set('nickname', data.data.nickname);
this.$ls.set('isshop', data.data.isshop);
this.$ls.set('iscenter', data.data.col2);
this.$ls.set('user_id', data.data.id);
this.$ls.set('huiyuankaid', data.data.huiyuankaid)
}),
]
)
this.checkWxLogin()
},
onShowManagerPopup() {
this.managerPopupVisible = true
},
onCloseManagerPopup() {
this.managerPopupVisible = false
},
checkWxLogin() {
if (!this.$isWechat()) return
if (this.$route.query.code) return
this.$get('/v1/client/AuthClient/loginwxweburl', {
returnUrl: `${encodeURIComponent(window.location.href)}`
}).then(res => {
if (res.data) {
window.location.href = res.data
}
}).catch(res => {
alert(res)
}) })
}, },
logout() { logout() {
@ -251,6 +305,14 @@ export default {
}, 100); }, 100);
}).catch(() => { }); }).catch(() => { });
}, },
toInvite() {
if (!this.data.allowinvitation) {
this.$showFailToast('您暂无邀请权限');
return
}
this.$navigate('Invite')
},
upload(file) { upload(file) {
this.tempData.userimg = file.file; this.tempData.userimg = file.file;
}, },
@ -263,7 +325,7 @@ export default {
headers: { 'Authorization': `Bearer ${localStorage.getItem('token')}` }, headers: { 'Authorization': `Bearer ${localStorage.getItem('token')}` },
body: fd, body: fd,
}).then(res => res.json()).then(res => { }).then(res => res.json()).then(res => {
if (res.status !== 200) throw new Error(res.errmsg); if (res.status !== 200) throw new Error(res.message);
this.tempData.userimg = res.data; this.tempData.userimg = res.data;
}).then(() => { }).then(() => {
return this.$put('/v1/client/DUsersClient', { return this.$put('/v1/client/DUsersClient', {
@ -275,7 +337,7 @@ export default {
this.showInfo = false; this.showInfo = false;
window.location.reload(); window.location.reload();
}).catch(err => { }).catch(err => {
this.$showFailToast(err.errmsg || err.message || '保存失败'); this.$showFailToast(err.message || err.message || '保存失败');
}); });
} else { } else {
this.$put('/v1/client/DUsersClient', { this.$put('/v1/client/DUsersClient', {
@ -286,7 +348,7 @@ export default {
this.showInfo = false; this.showInfo = false;
window.location.reload(); window.location.reload();
}).catch(err => { }).catch(err => {
this.$showFailToast(err.errmsg || '保存失败'); this.$showFailToast(err.message || '保存失败');
}); });
} }
}, },
@ -297,11 +359,29 @@ export default {
} }
return true; return true;
}, },
getSmsCode() {
if (this.isSendCode) return;
this.isSendCode = true;
this.sendCodeTime = 60;
const id = setInterval(() => {
if (this.sendCodeTime > 0) this.sendCodeTime--;
else { clearInterval(id); this.isSendCode = false; }
}, 1000);
this.$post('/v1/client/AuthClient/sendcode', {
"purpose": "chgpwd",
"cellphone": this.data.cellphone
}).then(res => {
if (res.status === 200) {
this.$showSuccessToast('验证码发送成功')
}
}).catch(err => {
clearInterval(id);
this.isSendCode = false;
this.$showFailToast(err.message);
});
},
setPassword() { setPassword() {
if (!this.tempPasswordData.oldpwd) {
this.$showFailToast('请输入原密码');
return;
}
if (!this.tempPasswordData.newpwd) { if (!this.tempPasswordData.newpwd) {
this.$showFailToast('请输入新密码'); this.$showFailToast('请输入新密码');
return; return;
@ -311,19 +391,27 @@ export default {
return; return;
} }
this.saving = true; this.saving = true;
this.$post('/v1/client/DUsersClient/changepwd', { this.$put('/v1/client/DUsersClient/changepwd', {
oldpwd: this.tempPasswordData.oldpwd, "password": this.tempPasswordData.newpwd,
newpwd: this.tempPasswordData.newpwd, "code": this.tempPasswordData.code
}).then((res) => { }).then(res => {
if (res.status !== 200) { if (res.status === 200) {
this.$showFailToast(res.message || '修改失败'); this.$showDialog({
return; title: '密码重置成功!',
message: '点击确认登录中心重新登录',
theme: 'round-button',
confirmButtonText: '确定',
}).then(() => {
this.saving = false;
this.$ls.remove('token');
location.replace('#/Login');
});
} else {
this.$showFailToast(res.message);
this.saving = false;
} }
this.$showSuccessToast('密码修改成功');
this.changePasswordVisibled = false;
}).catch(err => { }).catch(err => {
this.$showFailToast(err.message || '修改失败'); this.$showFailToast(err.message);
}).finally(() => {
this.saving = false; this.saving = false;
}); });
}, },

View File

@ -85,9 +85,7 @@
</div> </div>
<BaseList ref="baseList" <BaseList ref="baseList" :url="listUrl" :parseData="parseData" class="list_box">
:url="active === 0 ? '/v1/client/DUsersClient/friend' : '/v1/client/DUsersClient/allfriend'"
:list="data" class="list_box">
<template #default="{ item }"> <template #default="{ item }">
<div class="list" :key="item.id"> <div class="list" :key="item.id">
<div class="user_box"> <div class="user_box">
@ -110,7 +108,7 @@
<div> <div>
<span>{{ $formatGMT(item.addtime, 'yyyy-MM-dd HH:mm:ss') }}</span> <span>{{ $formatGMT(item.addtime, 'yyyy-MM-dd HH:mm:ss') }}</span>
<span class="r" @click="show = true"> <span class="r" v-if="item.isshop" @click="openshop(item.id)">
商家信息 <van-icon name="arrow"></van-icon> 商家信息 <van-icon name="arrow"></van-icon>
</span> </span>
<!-- <span class="r"> <!-- <span class="r">
@ -127,11 +125,11 @@
<van-popup v-model:show="show" style="padding: 4vw 3.33vw;border-radius: 2.67vw;"> <van-popup v-model:show="show" style="padding: 4vw 3.33vw;border-radius: 2.67vw;">
<!-- 该账号商家信息 --> <!-- 该账号商家信息 -->
<div class="merchantinfo"> <div class="merchantinfo">
<img src="" alt=""> <img :src="$file(shopinfo.shopimg)" alt="">
<div class="inf"> <div class="inf">
<b>name</b> <b>{{ shopinfo.shopname }}</b>
<span>账号</span> <span>账号{{ shopinfo.shopphone }}</span>
</div> </div>
</div> </div>
</van-popup> </van-popup>
@ -159,6 +157,7 @@ export default {
], ],
total: { total: {
}, },
shopinfo: {},
title: this.$route.query.title || null, title: this.$route.query.title || null,
}; };
}, },
@ -170,6 +169,31 @@ export default {
}, },
updateList() { updateList() {
this.$refs.baseList.refresh() this.$refs.baseList.refresh()
},
parseData(res) {
if (this.active === 2) {
return res.data ? [res.data] : []
} else {
return res.data.items || []
}
},
openshop(e) {
this.$get(`/v1/client/DShopsClient/${e}`).then(res => {
// console.log(res);
this.shopinfo = res.data;
this.show = true;
})
}
},
computed: {
listUrl() {
if (this.active === 0) {
return '/v1/client/DUsersClient/friend'
} else if (this.active === 1) {
return '/v1/client/DUsersClient/shop'
} else {
return '/v1/client/DUsersClient/referrer'
}
} }
}, },
}; };

View File

@ -7,7 +7,7 @@
<van-icon name="question-o" @click.stop="showTerm = true"></van-icon> <van-icon name="question-o" @click.stop="showTerm = true"></van-icon>
</div> </div>
<b>4000.00</b> <b>{{ data.all?.toFixed(2) }}</b>
</div> </div>
<div class="content"> <div class="content">
@ -21,7 +21,7 @@
<span> <span>
自己礼包消费业绩 自己礼包消费业绩
</span> </span>
<span class="r"></span> <span class="r">{{ data.self?.toFixed(2) }}</span>
</div> </div>
<div class="item"> <div class="item">
@ -29,7 +29,7 @@
<span> <span>
网体礼包消费业绩 网体礼包消费业绩
</span> </span>
<span class="r"></span> <span class="r">{{ data.net?.toFixed(2) }}</span>
</div> </div>
</div> </div>
</div> </div>
@ -51,6 +51,16 @@ export default {
} }
} }
},
mounted() {
this.init()
},
methods: {
init() {
this.$get('/v1/client/DUsersClient/libaoyeji').then(res => {
this.data = res.data
})
}
} }
} }
</script> </script>

View File

@ -168,7 +168,7 @@
当前余额 <van-icon name="question-o" @click.stop="showTerm = true"></van-icon> 当前余额 <van-icon name="question-o" @click.stop="showTerm = true"></van-icon>
</b> </b>
<div class="co_box"> <div class="co_box" @click="$navigate('CashoutRecord')">
<img src="/img/co_icon.png" alt=""> <img src="/img/co_icon.png" alt="">
<span>提现记录</span> <span>提现记录</span>
<van-icon name="arrow"></van-icon> <van-icon name="arrow"></van-icon>
@ -237,8 +237,7 @@
item.balance?.toFixed(2) }}</div> item.balance?.toFixed(2) }}</div>
</td> </td>
<td style="text-align: right;"> <td style="text-align: right;">
<van-tag :type="item.nums > 0 ? 'primary' : 'danger'" <van-tag :class="item.nums > 0 ? 'in' : 'out'" style="margin-bottom: 2vw;">
style="margin-bottom: 2vw;">
{{ item.nums > 0 ? "增加:+" : "减少:" {{ item.nums > 0 ? "增加:+" : "减少:"
}}{{ (item.nums).toFixed(2) }} }}{{ (item.nums).toFixed(2) }}
</van-tag> </van-tag>

View File

@ -6,10 +6,10 @@
<img style="height: 10.4vw;" src="/img/logo.png" alt=""> <img style="height: 10.4vw;" src="/img/logo.png" alt="">
<div class="u_info"> <div class="u_info">
<b>会员卡<van-icon style="margin-left: 1.2vw;" name="question-o" @click.stop="showTerm = true"></van-icon></b> <b>会员卡<van-icon style="margin-left: 1.2vw;" name="question-o" @click.stop="showTerm = true"></van-icon></b>
<span>123456789</span> <span>{{ huiyuankaid }}</span>
</div> </div>
<div class="record r"> <div class="record r" @click="$navigate('CertificateRecord')">
赠卡记录 赠卡记录
<van-icon name="arrow"></van-icon> <van-icon name="arrow"></van-icon>
</div> </div>
@ -21,7 +21,7 @@
<b>{{ data.totalsum?.toFixed(2) }}</b> <b>{{ data.totalsum?.toFixed(2) }}</b>
</div> </div>
<button> <button @click="$navigate('Transfer')">
赠卡 赠卡
</button> </button>
</div> </div>
@ -56,7 +56,7 @@
<span :class="item.nums > 0 ? 'in' : 'out'" class="r"> <span :class="item.nums > 0 ? 'in' : 'out'" class="r">
<span v-if="item.nums > 0">增加+</span> <span v-if="item.nums > 0">增加+</span>
<span v-else>减少</span> <span v-else>减少</span>
{{ item.nums }} {{ item.nums?.toFixed(2) }}
</span> </span>
</div> </div>
<span> <span>
@ -96,6 +96,7 @@ export default {
showDate: false, showDate: false,
showTerm: false, showTerm: false,
data: {}, data: {},
huiyuankaid: '',
date: [`${new Date().getFullYear()}`, `${new Date().getMonth() + 1}`], date: [`${new Date().getFullYear()}`, `${new Date().getMonth() + 1}`],
currentDate: [`${new Date().getFullYear()}`, `${new Date().getMonth() + 1}`], currentDate: [`${new Date().getFullYear()}`, `${new Date().getMonth() + 1}`],
searchParams: { searchParams: {
@ -117,6 +118,7 @@ export default {
init() { init() {
this.$get('/v1/client/DUserxiaofeiquansClient/statistics', this.searchParams).then(res => { this.$get('/v1/client/DUserxiaofeiquansClient/statistics', this.searchParams).then(res => {
this.data = res.data; this.data = res.data;
this.huiyuankaid = this.$ls.get('huiyuankaid');
}) })
} }
} }

View File

@ -42,11 +42,21 @@
</template> </template>
<script> <script>
export default { export default {
mounted() {
this.init()
},
data() { data() {
return { return {
active: 0, active: 0,
check: false, check: false,
} }
},
methods: {
init() {
this.$get('/v1/client/DUserlipinquansClient').then(res => {
this.data = res;
})
}
} }
} }
</script> </script>

View File

@ -0,0 +1,88 @@
<template>
<BasePage>
<div class="verif">
<div class="search_box">
<img src="/img/search.png" alt="">
<input type="text" placeholder="输入用户账号/礼品券码搜索" v-if="type === 'verif'">
<input type="text" placeholder="输入用户账号/会员卡号搜索" v-else>
</div>
<div class="list">
<div class="item">
<div class="t">
<img class="icon" src="" alt="">
<div>
<span>用户123</span>
<p>账号123456789</p>
</div>
<span class="r tt" v-if="type === 'verif'">
已核销
</span>
<span class="r pre" v-else>
赠送额度: <b>500.00</b>
</span>
</div>
<div class="info_box">
<div>
<span class="left">
订单编号
</span>
<span class="r rg">
13125562015232322332326
<img src="/img/copy_b.png" alt="">
</span>
</div>
<div v-if="type === 'verif'">
<span class="left">
礼品券码:
</span>
<span class="r rg">
13125562015232322332326
<img src="/img/copy_b.png" alt="">
</span>
</div>
<div v-if="type !== 'verif'">
<span class="left">
会员卡号
</span>
<span class="r rg">
13125562015232322332326
<img src="/img/copy_b.png" alt="">
</span>
</div>
<div v-if="type !== 'verif'">
<span class="left">
赠送时间
</span>
<span class="r rg">
13125562015232322332326
</span>
</div>
<div v-if="type === 'verif'">
<span class="left">
核销时间:
</span>
<span class="r rg">
13125562015232322332326
</span>
</div>
</div>
</div>
</div>
</div>
</BasePage>
</template>
<script>
export default {
data() {
return {
type: this.$route.query.type,
}
}
}
</script>

View File

@ -68,7 +68,7 @@
item.balance?.toFixed(2) }}</div> item.balance?.toFixed(2) }}</div>
</td> </td>
<td style="text-align: right;"> <td style="text-align: right;">
<van-tag :type="item.nums > 0 ? 'primary' : 'danger'" style="margin-bottom: 2vw;"> <van-tag :class="item.nums > 0 ? 'in' : 'out'" style="margin-bottom: 2vw;">
{{ item.nums > 0 ? "增加:+" : "减少:" {{ item.nums > 0 ? "增加:+" : "减少:"
}}{{ (item.nums).toFixed(2) }} }}{{ (item.nums).toFixed(2) }}
</van-tag> </van-tag>

View File

@ -2,12 +2,15 @@
<BasePage> <BasePage>
<div class="transfer"> <div class="transfer">
<div class="top"> <div class="top">
<input v-model="userName" type="text" maxlength="11" @change="checkExists" placeholder="请输入转账账号"> <div class="tit">
被赠送人账号
</div>
<input v-model="userName" type="text" maxlength="11" @change="checkExists" placeholder="请输入被赠送人ID">
<hr> <hr>
<span class="errorinfo">{{ errorInfo }}</span> <span class="errorinfo">{{ errorInfo }}</span>
</div> </div>
<div class="type_box"> <!-- <div class="type_box">
<div class="title"> <div class="title">
<b>互转类型</b> <b>互转类型</b>
</div> </div>
@ -20,26 +23,32 @@
<span>剩余265444.00</span> <span>剩余265444.00</span>
</p> </p>
</van-radio> </van-radio>
<!-- <van-radio name="2" label-position="left"> <van-radio name="2" label-position="left">
<img src="/img/balance-i1.png" alt=""> <img src="/img/balance-i1.png" alt="">
<p> <p>
转余额 转余额
<span>剩余265444.00</span> <span>剩余265444.00</span>
</p> </p>
</van-radio> --> </van-radio>
</van-radio-group> </van-radio-group>
</div> </div> -->
<div class="quota_box"> <div class="quota_box">
<div class="title"> <div class="title">
<b>转账数额</b> <b>赠送额度</b>
<span class="r">
<van-icon name="info-o" />
赠送说明
</span>
</div> </div>
<input v-model="amount" type="number" placeholder="请输入转账数额"> <!-- <input v-model="amount" type="number" placeholder="请输入转账数额"> -->
<b class="nums">500.00</b>
<hr>
</div> </div>
<div class="com_btn"> <div class="com_btn">
<van-button type="primary" color="#22a56e" round @click="toTransfer">确认转账</van-button> <van-button type="primary" color="#ea3e23" round @click="toTransfer">确认赠送</van-button>
</div> </div>
</div> </div>
</BasePage> </BasePage>
@ -57,7 +66,7 @@ export default {
// this.wallet = data[0]; // this.wallet = data[0];
// }).catch(err => { // }).catch(err => {
// this.$showFailToast(":" + err.errmsg); // this.$showFailToast(":" + err.message);
// }); // });
}, },
// watch: { // watch: {
@ -91,6 +100,7 @@ export default {
// }, // },
data() { data() {
return { return {
amount: 500.00,
checked: 'balance', checked: 'balance',
checkedCH: "余额", checkedCH: "余额",
left: 0, left: 0,
@ -180,7 +190,7 @@ export default {
if (err.errcode == 10702) { if (err.errcode == 10702) {
this.$showFailToast(this.checkedCH + "转出失败:可转出的" + this.checkedCH + "不足"); this.$showFailToast(this.checkedCH + "转出失败:可转出的" + this.checkedCH + "不足");
} else } else
this.$showFailToast(this.checkedCH + "转出失败:" + err.errmsg); this.$showFailToast(this.checkedCH + "转出失败:" + err.message);
}); });
}) })
}, 500); }, 500);