checkpoint: 冻结资金开工前龙先生小程序本地备份(不推远程)
Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
11
app.json
11
app.json
@@ -218,6 +218,15 @@
|
|||||||
"components/fakuan-pay/fakuan-pay"
|
"components/fakuan-pay/fakuan-pay"
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"root": "pages/gongdan",
|
||||||
|
"pages": [
|
||||||
|
"create/create",
|
||||||
|
"list/list",
|
||||||
|
"detail/detail",
|
||||||
|
"chongzhi-list/chongzhi-list"
|
||||||
|
]
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"root": "pages/phone-auth",
|
"root": "pages/phone-auth",
|
||||||
"pages": ["phone-auth"]
|
"pages": ["phone-auth"]
|
||||||
@@ -257,7 +266,7 @@
|
|||||||
"navigationStyle": "default",
|
"navigationStyle": "default",
|
||||||
"backgroundTextStyle": "light",
|
"backgroundTextStyle": "light",
|
||||||
"navigationBarBackgroundColor": "#fff",
|
"navigationBarBackgroundColor": "#fff",
|
||||||
"navigationBarTitleText": "星阙网络"
|
"navigationBarTitleText": "龙先生电竞"
|
||||||
},
|
},
|
||||||
"tabBar": {
|
"tabBar": {
|
||||||
"custom": true,
|
"custom": true,
|
||||||
|
|||||||
58
components/tousu-float/tousu-float.js
Normal file
58
components/tousu-float/tousu-float.js
Normal file
@@ -0,0 +1,58 @@
|
|||||||
|
const STORAGE_KEY = 'tousuFloatHidden';
|
||||||
|
|
||||||
|
Component({
|
||||||
|
data: {
|
||||||
|
hidden: false,
|
||||||
|
},
|
||||||
|
|
||||||
|
lifetimes: {
|
||||||
|
attached() {
|
||||||
|
this._syncHidden();
|
||||||
|
},
|
||||||
|
},
|
||||||
|
|
||||||
|
pageLifetimes: {
|
||||||
|
show() {
|
||||||
|
this._syncHidden();
|
||||||
|
},
|
||||||
|
},
|
||||||
|
|
||||||
|
methods: {
|
||||||
|
_syncHidden() {
|
||||||
|
let hidden = false;
|
||||||
|
try {
|
||||||
|
hidden = wx.getStorageSync(STORAGE_KEY) === 1 || wx.getStorageSync(STORAGE_KEY) === '1';
|
||||||
|
} catch (e) {}
|
||||||
|
if (hidden !== this.data.hidden) {
|
||||||
|
this.setData({ hidden });
|
||||||
|
}
|
||||||
|
},
|
||||||
|
|
||||||
|
go() {
|
||||||
|
wx.navigateTo({
|
||||||
|
url: '/pages/gongdan/create/create',
|
||||||
|
fail: (err) => {
|
||||||
|
console.error('打开投诉页失败', err);
|
||||||
|
wx.showToast({ title: '打开失败,请重试', icon: 'none' });
|
||||||
|
},
|
||||||
|
});
|
||||||
|
},
|
||||||
|
|
||||||
|
onDismiss(e) {
|
||||||
|
if (e && e.stopPropagation) e.stopPropagation();
|
||||||
|
wx.showModal({
|
||||||
|
title: '隐藏投诉入口',
|
||||||
|
content: '隐藏后可在「我的 / 工单」中继续投诉。需要恢复时可清除小程序缓存。',
|
||||||
|
confirmText: '不再显示',
|
||||||
|
cancelText: '取消',
|
||||||
|
success: (res) => {
|
||||||
|
if (!res.confirm) return;
|
||||||
|
try {
|
||||||
|
wx.setStorageSync(STORAGE_KEY, 1);
|
||||||
|
} catch (err) {}
|
||||||
|
this.setData({ hidden: true });
|
||||||
|
},
|
||||||
|
});
|
||||||
|
},
|
||||||
|
},
|
||||||
|
});
|
||||||
1
components/tousu-float/tousu-float.json
Normal file
1
components/tousu-float/tousu-float.json
Normal file
@@ -0,0 +1 @@
|
|||||||
|
{"component":true}
|
||||||
6
components/tousu-float/tousu-float.wxml
Normal file
6
components/tousu-float/tousu-float.wxml
Normal file
@@ -0,0 +1,6 @@
|
|||||||
|
<view class="tousu-wrap" wx:if="{{!hidden}}">
|
||||||
|
<view class="float" catchtap="go">投诉</view>
|
||||||
|
<view class="dismiss-row" catchtap="onDismiss">
|
||||||
|
<text class="dismiss-label">不再显示</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
37
components/tousu-float/tousu-float.wxss
Normal file
37
components/tousu-float/tousu-float.wxss
Normal file
@@ -0,0 +1,37 @@
|
|||||||
|
.tousu-wrap {
|
||||||
|
position: fixed;
|
||||||
|
right: 24rpx;
|
||||||
|
bottom: 280rpx;
|
||||||
|
z-index: 999;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: flex-end;
|
||||||
|
gap: 6rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
.float {
|
||||||
|
min-width: 96rpx;
|
||||||
|
height: 72rpx;
|
||||||
|
padding: 0 22rpx;
|
||||||
|
border-radius: 36rpx;
|
||||||
|
background: rgba(55, 55, 55, 0.72);
|
||||||
|
color: #f5f5f5;
|
||||||
|
font-size: 26rpx;
|
||||||
|
font-weight: 500;
|
||||||
|
letter-spacing: 1rpx;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
box-shadow: 0 4rpx 12rpx rgba(0, 0, 0, 0.12);
|
||||||
|
}
|
||||||
|
|
||||||
|
.dismiss-row {
|
||||||
|
padding: 4rpx 8rpx;
|
||||||
|
}
|
||||||
|
|
||||||
|
.dismiss-label {
|
||||||
|
font-size: 20rpx;
|
||||||
|
color: rgba(120, 120, 120, 0.9);
|
||||||
|
text-decoration: underline;
|
||||||
|
text-underline-offset: 4rpx;
|
||||||
|
}
|
||||||
@@ -1,11 +1,11 @@
|
|||||||
/**
|
/**
|
||||||
* 小程序所属俱乐部配置 — 每个小程序工程编译前改这里即可。
|
* 小程序所属俱乐部配置 — 每个小程序工程编译前改这里即可。
|
||||||
* 星阙 = xq;星之界 = xzj;与 club 表 club_id 一致。
|
* 星阙 = xq;星之界 = xzj;龙先生 = lxs(与后台 club 表 club_id 一致,勿写成 lsx)。
|
||||||
* 不要依赖后端猜测:前端必须明确所属 club。
|
* 不要依赖后端猜测:前端必须明确所属 club。
|
||||||
*/
|
*/
|
||||||
export const CLUB_ID = 'xzj';
|
export const CLUB_ID = 'lxs';
|
||||||
|
|
||||||
/** 与 club 表 wx_appid 一致,登录时可传给后端反查 club */
|
/** 与 club 表 wx_appid 一致,登录时可传给后端反查 club */
|
||||||
export const WX_APP_ID = 'wxdefa454152e78a03';
|
export const WX_APP_ID = 'wx7ff90e9d024fcdb8';
|
||||||
|
|
||||||
export const CLUB_NAME = '星之界电竞';
|
export const CLUB_NAME = '龙先生电竞';
|
||||||
|
|||||||
@@ -884,6 +884,10 @@ Page({
|
|||||||
|
|
||||||
noop() {},
|
noop() {},
|
||||||
|
|
||||||
|
goToComplaintCreate() {
|
||||||
|
wx.navigateTo({ url: '/pages/gongdan/create/create' });
|
||||||
|
},
|
||||||
|
|
||||||
onReachBottom() {
|
onReachBottom() {
|
||||||
if (this.data.isLoading || this.data.isLoadingMore) return;
|
if (this.data.isLoading || this.data.isLoadingMore) return;
|
||||||
if (this.data.hasMore && !this.data.isLoading && this.data.xuanzhongLeixingId) {
|
if (this.data.hasMore && !this.data.isLoading && this.data.xuanzhongLeixingId) {
|
||||||
|
|||||||
@@ -39,6 +39,12 @@
|
|||||||
|
|
||||||
|
|
||||||
<!-- 公告置顶 -->
|
<!-- 公告置顶 -->
|
||||||
|
<view class="tousu-top-bar" catchtap="goToComplaintCreate">
|
||||||
|
<text class="tousu-top-bar-txt">投诉 / 反馈</text>
|
||||||
|
<text class="tousu-top-bar-sub">点这里提交工单</text>
|
||||||
|
<text class="tousu-top-bar-arrow">›</text>
|
||||||
|
</view>
|
||||||
|
|
||||||
<view class="xym-gonggao-bar" wx:if="{{gonggao}}">
|
<view class="xym-gonggao-bar" wx:if="{{gonggao}}">
|
||||||
<image class="xym-gonggao-ico" src="https://bintao.xmxym88.com/xcx/bintao/38.png" mode="aspectFit"/>
|
<image class="xym-gonggao-ico" src="https://bintao.xmxym88.com/xcx/bintao/38.png" mode="aspectFit"/>
|
||||||
<text class="xym-gonggao-txt">{{gonggao}}</text>
|
<text class="xym-gonggao-txt">{{gonggao}}</text>
|
||||||
|
|||||||
@@ -14,6 +14,34 @@ page {
|
|||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
position: relative;
|
position: relative;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.tousu-top-bar {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 12rpx;
|
||||||
|
margin: 16rpx 24rpx 8rpx;
|
||||||
|
padding: 18rpx 24rpx;
|
||||||
|
border-radius: 14rpx;
|
||||||
|
background: linear-gradient(90deg, #e85a3a 0%, #f07858 100%);
|
||||||
|
box-shadow: 0 6rpx 18rpx rgba(232, 90, 58, 0.28);
|
||||||
|
z-index: 5;
|
||||||
|
position: relative;
|
||||||
|
}
|
||||||
|
.tousu-top-bar-txt {
|
||||||
|
color: #fff;
|
||||||
|
font-size: 28rpx;
|
||||||
|
font-weight: 600;
|
||||||
|
}
|
||||||
|
.tousu-top-bar-sub {
|
||||||
|
flex: 1;
|
||||||
|
color: rgba(255,255,255,0.88);
|
||||||
|
font-size: 22rpx;
|
||||||
|
}
|
||||||
|
.tousu-top-bar-arrow {
|
||||||
|
color: #fff;
|
||||||
|
font-size: 36rpx;
|
||||||
|
line-height: 1;
|
||||||
|
}
|
||||||
|
|
||||||
/* 背景动态纹理,增加层次感 */
|
/* 背景动态纹理,增加层次感 */
|
||||||
.qiangdan-page::before {
|
.qiangdan-page::before {
|
||||||
|
|||||||
@@ -31,6 +31,9 @@ Page({
|
|||||||
yajinActive: false,
|
yajinActive: false,
|
||||||
depositRules: DEFAULT_RULES,
|
depositRules: DEFAULT_RULES,
|
||||||
depositBenefits: DEFAULT_BENEFITS,
|
depositBenefits: DEFAULT_BENEFITS,
|
||||||
|
rulesTitle: '履约金规则',
|
||||||
|
benefitsTitle: '平台履约金权益',
|
||||||
|
pageCopy: null,
|
||||||
agreed: false,
|
agreed: false,
|
||||||
payAmountLabel: '',
|
payAmountLabel: '',
|
||||||
yajinAmount: '100',
|
yajinAmount: '100',
|
||||||
@@ -52,6 +55,7 @@ Page({
|
|||||||
this._jumpParams = options || {};
|
this._jumpParams = options || {};
|
||||||
this.initImages();
|
this.initImages();
|
||||||
this.loadUserInfo();
|
this.loadUserInfo();
|
||||||
|
this.fetchPageCopy();
|
||||||
},
|
},
|
||||||
|
|
||||||
onHide() {
|
onHide() {
|
||||||
@@ -64,6 +68,9 @@ Page({
|
|||||||
this.registerNotification();
|
this.registerNotification();
|
||||||
this.loadYajin();
|
this.loadYajin();
|
||||||
this.refreshConfiguredIcons();
|
this.refreshConfiguredIcons();
|
||||||
|
if (!this.data.pageCopy) {
|
||||||
|
this.fetchPageCopy();
|
||||||
|
}
|
||||||
PopupService.checkAndShow(this, 'dashouchongzhi');
|
PopupService.checkAndShow(this, 'dashouchongzhi');
|
||||||
const preset = this._jumpParams?.presetAmount || this._jumpParams?.requiredYajin;
|
const preset = this._jumpParams?.presetAmount || this._jumpParams?.requiredYajin;
|
||||||
if (preset && parseFloat(preset) > 0) {
|
if (preset && parseFloat(preset) > 0) {
|
||||||
@@ -81,6 +88,73 @@ Page({
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
|
resolveOssUrl(path) {
|
||||||
|
if (!path) return '';
|
||||||
|
if (path.startsWith('http')) return path;
|
||||||
|
return (app.globalData.ossImageUrl || '') + path;
|
||||||
|
},
|
||||||
|
|
||||||
|
async fetchPageCopy() {
|
||||||
|
try {
|
||||||
|
const res = await request({
|
||||||
|
url: '/jituan/recharge-page-copy',
|
||||||
|
method: 'POST',
|
||||||
|
data: { page_key: 'yajin' },
|
||||||
|
});
|
||||||
|
if (res.data && res.data.code === 0 && res.data.data) {
|
||||||
|
this.setData({ pageCopy: res.data.data.regions || {} });
|
||||||
|
} else {
|
||||||
|
this.setData({ pageCopy: {} });
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
console.warn('fetchPageCopy failed', e);
|
||||||
|
this.setData({ pageCopy: {} });
|
||||||
|
}
|
||||||
|
this.applyPageCopy();
|
||||||
|
},
|
||||||
|
|
||||||
|
applyPageCopy() {
|
||||||
|
const copy = this.data.pageCopy || {};
|
||||||
|
const patch = {};
|
||||||
|
|
||||||
|
const rulesRegion = copy.rules;
|
||||||
|
if (rulesRegion && Array.isArray(rulesRegion.items) && rulesRegion.items.length > 0) {
|
||||||
|
patch.depositRules = rulesRegion.items
|
||||||
|
.map((it) => (typeof it === 'string' ? it : (it && it.text) || ''))
|
||||||
|
.filter(Boolean);
|
||||||
|
if (rulesRegion.title) patch.rulesTitle = rulesRegion.title;
|
||||||
|
} else {
|
||||||
|
patch.depositRules = DEFAULT_RULES;
|
||||||
|
patch.rulesTitle = '履约金规则';
|
||||||
|
}
|
||||||
|
|
||||||
|
const benefitsRegion = copy.benefits;
|
||||||
|
const fb = (key) => `${ICON_FOLDER}/${key}.png`;
|
||||||
|
if (benefitsRegion && Array.isArray(benefitsRegion.items) && benefitsRegion.items.length > 0) {
|
||||||
|
patch.depositBenefits = benefitsRegion.items.map((item, i) => {
|
||||||
|
const fallback = DEFAULT_BENEFITS[i];
|
||||||
|
const iconUrl = item.icon_url
|
||||||
|
? this.resolveOssUrl(item.icon_url)
|
||||||
|
: (fallback
|
||||||
|
? resolveMiniappIcon(app, fallback.key, fb(fallback.key))
|
||||||
|
: '');
|
||||||
|
return {
|
||||||
|
label: item.label || item.title || '',
|
||||||
|
iconUrl,
|
||||||
|
};
|
||||||
|
});
|
||||||
|
if (benefitsRegion.title) patch.benefitsTitle = benefitsRegion.title;
|
||||||
|
} else {
|
||||||
|
patch.depositBenefits = DEFAULT_BENEFITS.map((item) => ({
|
||||||
|
label: item.label,
|
||||||
|
iconUrl: resolveMiniappIcon(app, item.key, fb(item.key)),
|
||||||
|
}));
|
||||||
|
patch.benefitsTitle = '平台履约金权益';
|
||||||
|
}
|
||||||
|
|
||||||
|
this.setData(patch);
|
||||||
|
},
|
||||||
|
|
||||||
initImages() {
|
initImages() {
|
||||||
const fb = (key) => `${ICON_FOLDER}/${key}.png`;
|
const fb = (key) => `${ICON_FOLDER}/${key}.png`;
|
||||||
const depositBenefits = DEFAULT_BENEFITS.map((item) => ({
|
const depositBenefits = DEFAULT_BENEFITS.map((item) => ({
|
||||||
@@ -94,6 +168,9 @@ Page({
|
|||||||
},
|
},
|
||||||
depositBenefits,
|
depositBenefits,
|
||||||
});
|
});
|
||||||
|
if (this.data.pageCopy) {
|
||||||
|
this.applyPageCopy();
|
||||||
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
async refreshConfiguredIcons() {
|
async refreshConfiguredIcons() {
|
||||||
|
|||||||
@@ -31,7 +31,7 @@
|
|||||||
</view>
|
</view>
|
||||||
|
|
||||||
<view class="section-card">
|
<view class="section-card">
|
||||||
<text class="section-title">履约金规则</text>
|
<text class="section-title">{{rulesTitle || '履约金规则'}}</text>
|
||||||
<view class="rule-list">
|
<view class="rule-list">
|
||||||
<view wx:for="{{depositRules}}" wx:key="index" class="rule-item">
|
<view wx:for="{{depositRules}}" wx:key="index" class="rule-item">
|
||||||
<text class="rule-num">{{index + 1}}.</text>
|
<text class="rule-num">{{index + 1}}.</text>
|
||||||
@@ -41,7 +41,7 @@
|
|||||||
</view>
|
</view>
|
||||||
|
|
||||||
<view class="section-card">
|
<view class="section-card">
|
||||||
<text class="section-title">平台履约金权益</text>
|
<text class="section-title">{{benefitsTitle || '平台履约金权益'}}</text>
|
||||||
<view class="benefit-grid">
|
<view class="benefit-grid">
|
||||||
<view wx:for="{{depositBenefits}}" wx:key="label" class="benefit-item">
|
<view wx:for="{{depositBenefits}}" wx:key="label" class="benefit-item">
|
||||||
<view wx:if="{{item.iconUrl}}" class="icon-clip icon-clip-deposit-benefit">
|
<view wx:if="{{item.iconUrl}}" class="icon-clip icon-clip-deposit-benefit">
|
||||||
|
|||||||
@@ -34,6 +34,10 @@ Page({
|
|||||||
loadingText: '支付中...',
|
loadingText: '支付中...',
|
||||||
currentDingdanid: '',
|
currentDingdanid: '',
|
||||||
detailRules: [],
|
detailRules: [],
|
||||||
|
rulesTitle: '',
|
||||||
|
benefitsTitle: '',
|
||||||
|
advantagesTitle: '平台优势',
|
||||||
|
pageCopy: null,
|
||||||
jumpParams: {},
|
jumpParams: {},
|
||||||
showPayMethodModal: false,
|
showPayMethodModal: false,
|
||||||
currentBuyType: null,
|
currentBuyType: null,
|
||||||
@@ -100,9 +104,28 @@ onHide() {
|
|||||||
// ========== 初始化页面 ==========
|
// ========== 初始化页面 ==========
|
||||||
async initPage() {
|
async initPage() {
|
||||||
this.loadFromGlobalData();
|
this.loadFromGlobalData();
|
||||||
|
await this.fetchPageCopy();
|
||||||
await this.fetchHuiyuanList();
|
await this.fetchHuiyuanList();
|
||||||
},
|
},
|
||||||
|
|
||||||
|
async fetchPageCopy() {
|
||||||
|
try {
|
||||||
|
const res = await request({
|
||||||
|
url: '/jituan/recharge-page-copy',
|
||||||
|
method: 'POST',
|
||||||
|
data: { page_key: 'huiyuan' },
|
||||||
|
});
|
||||||
|
if (res.data && res.data.code === 0 && res.data.data) {
|
||||||
|
this.setData({ pageCopy: res.data.data.regions || {} });
|
||||||
|
} else {
|
||||||
|
this.setData({ pageCopy: {} });
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
console.warn('fetchPageCopy failed', e);
|
||||||
|
this.setData({ pageCopy: {} });
|
||||||
|
}
|
||||||
|
},
|
||||||
|
|
||||||
initImages() {
|
initImages() {
|
||||||
this.setData({
|
this.setData({
|
||||||
imgUrls: {
|
imgUrls: {
|
||||||
@@ -133,6 +156,25 @@ onHide() {
|
|||||||
|
|
||||||
buildPlatformAdvantages() {
|
buildPlatformAdvantages() {
|
||||||
const fb = (name) => `${ICON_FOLDER}/${name}.png`;
|
const fb = (name) => `${ICON_FOLDER}/${name}.png`;
|
||||||
|
const region = (this.data.pageCopy || {}).advantages;
|
||||||
|
if (region && Array.isArray(region.items) && region.items.length > 0) {
|
||||||
|
return region.items.map((item, i) => {
|
||||||
|
const fallbackKey = [
|
||||||
|
ICON_KEYS.FIGHTER_RECHARGE_ADVANTAGE_1,
|
||||||
|
ICON_KEYS.FIGHTER_RECHARGE_ADVANTAGE_2,
|
||||||
|
ICON_KEYS.FIGHTER_RECHARGE_ADVANTAGE_3,
|
||||||
|
ICON_KEYS.FIGHTER_RECHARGE_ADVANTAGE_4,
|
||||||
|
][i];
|
||||||
|
const iconUrl = item.icon_url
|
||||||
|
? this.resolveOssUrl(item.icon_url)
|
||||||
|
: (fallbackKey ? this._icon(fallbackKey, fb(fallbackKey)) : '');
|
||||||
|
return {
|
||||||
|
title: item.title || '',
|
||||||
|
desc: item.desc || '',
|
||||||
|
iconUrl,
|
||||||
|
};
|
||||||
|
});
|
||||||
|
}
|
||||||
const keys = [
|
const keys = [
|
||||||
ICON_KEYS.FIGHTER_RECHARGE_ADVANTAGE_1,
|
ICON_KEYS.FIGHTER_RECHARGE_ADVANTAGE_1,
|
||||||
ICON_KEYS.FIGHTER_RECHARGE_ADVANTAGE_2,
|
ICON_KEYS.FIGHTER_RECHARGE_ADVANTAGE_2,
|
||||||
@@ -166,10 +208,31 @@ onHide() {
|
|||||||
},
|
},
|
||||||
|
|
||||||
buildMemberBenefits(huiyuan = {}) {
|
buildMemberBenefits(huiyuan = {}) {
|
||||||
|
const region = (this.data.pageCopy || {}).benefits;
|
||||||
|
const fb = (name) => `${ICON_FOLDER}/${name}.png`;
|
||||||
|
if (region && Array.isArray(region.items) && region.items.length > 0) {
|
||||||
|
const fallbackKeys = [
|
||||||
|
ICON_KEYS.FIGHTER_RECHARGE_BENEFIT_1,
|
||||||
|
ICON_KEYS.FIGHTER_RECHARGE_BENEFIT_2,
|
||||||
|
ICON_KEYS.FIGHTER_RECHARGE_BENEFIT_3,
|
||||||
|
];
|
||||||
|
return region.items.map((item, i) => {
|
||||||
|
const key = fallbackKeys[i];
|
||||||
|
const iconUrl = item.icon_url
|
||||||
|
? this.resolveOssUrl(item.icon_url)
|
||||||
|
: (key ? this._icon(key, fb(key)) : '');
|
||||||
|
return {
|
||||||
|
title: item.title || '',
|
||||||
|
desc: item.desc || '',
|
||||||
|
iconUrl,
|
||||||
|
accentColor: item.accent_color || '',
|
||||||
|
accentStyle: item.accent_color ? `color:${item.accent_color}` : '',
|
||||||
|
};
|
||||||
|
});
|
||||||
|
}
|
||||||
const name = huiyuan.mingzi || '会员';
|
const name = huiyuan.mingzi || '会员';
|
||||||
const formalPrice = huiyuan.jiage || '0';
|
const formalPrice = huiyuan.jiage || '0';
|
||||||
const trialPrice = huiyuan.trial_price || '0';
|
const trialPrice = huiyuan.trial_price || '0';
|
||||||
const fb = (name) => `${ICON_FOLDER}/${name}.png`;
|
|
||||||
const meta = [
|
const meta = [
|
||||||
{
|
{
|
||||||
key: ICON_KEYS.FIGHTER_RECHARGE_BENEFIT_1,
|
key: ICON_KEYS.FIGHTER_RECHARGE_BENEFIT_1,
|
||||||
@@ -197,11 +260,23 @@ onHide() {
|
|||||||
},
|
},
|
||||||
|
|
||||||
applyCurrentHuiyuan(huiyuan, index) {
|
applyCurrentHuiyuan(huiyuan, index) {
|
||||||
|
const copy = this.data.pageCopy || {};
|
||||||
|
const name = huiyuan.mingzi || '会员';
|
||||||
|
const rulesTitle = (copy.rules && copy.rules.title)
|
||||||
|
|| `${name}规则`;
|
||||||
|
const benefitsTitle = (copy.benefits && copy.benefits.title)
|
||||||
|
|| `${name}专属权益`;
|
||||||
|
const advantagesTitle = (copy.advantages && copy.advantages.title)
|
||||||
|
|| '平台优势';
|
||||||
this.setData({
|
this.setData({
|
||||||
currentHuiyuanIndex: index,
|
currentHuiyuanIndex: index,
|
||||||
currentHuiyuan: huiyuan,
|
currentHuiyuan: huiyuan,
|
||||||
detailRules: this.buildDetailRules(huiyuan),
|
detailRules: this.buildDetailRules(huiyuan),
|
||||||
memberBenefits: this.buildMemberBenefits(huiyuan),
|
memberBenefits: this.buildMemberBenefits(huiyuan),
|
||||||
|
platformAdvantages: this.buildPlatformAdvantages(),
|
||||||
|
rulesTitle,
|
||||||
|
benefitsTitle,
|
||||||
|
advantagesTitle,
|
||||||
memberBadge: huiyuan.mingzi || '会员',
|
memberBadge: huiyuan.mingzi || '会员',
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
@@ -315,6 +390,13 @@ onHide() {
|
|||||||
},
|
},
|
||||||
|
|
||||||
buildDetailRules(huiyuan = {}) {
|
buildDetailRules(huiyuan = {}) {
|
||||||
|
const region = (this.data.pageCopy || {}).rules;
|
||||||
|
if (region && Array.isArray(region.items) && region.items.length > 0) {
|
||||||
|
return region.items
|
||||||
|
.map((it) => (typeof it === 'string' ? it : (it && it.text) || ''))
|
||||||
|
.filter(Boolean)
|
||||||
|
.slice(0, 4);
|
||||||
|
}
|
||||||
const formalDays = huiyuan.formal_days || 30;
|
const formalDays = huiyuan.formal_days || 30;
|
||||||
const rules = [
|
const rules = [
|
||||||
`有效期${formalDays}天`,
|
`有效期${formalDays}天`,
|
||||||
|
|||||||
@@ -53,7 +53,7 @@
|
|||||||
|
|
||||||
<view class="section-head">
|
<view class="section-head">
|
||||||
<view class="section-bar"></view>
|
<view class="section-bar"></view>
|
||||||
<text class="section-title">{{currentHuiyuan.mingzi || '会员'}}规则</text>
|
<text class="section-title">{{rulesTitle || ((currentHuiyuan.mingzi || '会员') + '规则')}}</text>
|
||||||
</view>
|
</view>
|
||||||
<scroll-view class="rules-scroll" scroll-x enable-flex>
|
<scroll-view class="rules-scroll" scroll-x enable-flex>
|
||||||
<view class="rules-row">
|
<view class="rules-row">
|
||||||
@@ -66,7 +66,7 @@
|
|||||||
|
|
||||||
<view class="section-head">
|
<view class="section-head">
|
||||||
<view class="section-bar"></view>
|
<view class="section-bar"></view>
|
||||||
<text class="section-title">{{currentHuiyuan.mingzi || '会员'}}专属权益</text>
|
<text class="section-title">{{benefitsTitle || ((currentHuiyuan.mingzi || '会员') + '专属权益')}}</text>
|
||||||
</view>
|
</view>
|
||||||
<view class="benefits-row">
|
<view class="benefits-row">
|
||||||
<view wx:for="{{memberBenefits}}" wx:key="title" class="benefit-card">
|
<view wx:for="{{memberBenefits}}" wx:key="title" class="benefit-card">
|
||||||
@@ -74,13 +74,13 @@
|
|||||||
<image class="icon-clip-img" src="{{item.iconUrl}}" mode="aspectFill" />
|
<image class="icon-clip-img" src="{{item.iconUrl}}" mode="aspectFill" />
|
||||||
</view>
|
</view>
|
||||||
<text class="benefit-title">{{item.title}}</text>
|
<text class="benefit-title">{{item.title}}</text>
|
||||||
<text class="benefit-desc">{{item.desc}}</text>
|
<text class="benefit-desc" style="{{item.accentStyle}}">{{item.desc}}</text>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
<view class="section-head">
|
<view class="section-head">
|
||||||
<view class="section-bar"></view>
|
<view class="section-bar"></view>
|
||||||
<text class="section-title">平台优势</text>
|
<text class="section-title">{{advantagesTitle || '平台优势'}}</text>
|
||||||
</view>
|
</view>
|
||||||
<view class="advantage-grid">
|
<view class="advantage-grid">
|
||||||
<view wx:for="{{platformAdvantages}}" wx:key="title" class="advantage-item">
|
<view wx:for="{{platformAdvantages}}" wx:key="title" class="advantage-item">
|
||||||
|
|||||||
@@ -126,6 +126,7 @@ Page(createPage({
|
|||||||
iconKaoheZhongxin: icon(ICON_KEYS.FIGHTER_MINE_KAOHE_ZHONGXIN, 'beijing/kaohe/zhongxin.png'),
|
iconKaoheZhongxin: icon(ICON_KEYS.FIGHTER_MINE_KAOHE_ZHONGXIN, 'beijing/kaohe/zhongxin.png'),
|
||||||
iconShangjia: icon(ICON_KEYS.FIGHTER_MINE_SHANGJIA, 'beijing/tubiao/grzx_shangjia.jpg'),
|
iconShangjia: icon(ICON_KEYS.FIGHTER_MINE_SHANGJIA, 'beijing/tubiao/grzx_shangjia.jpg'),
|
||||||
iconDashouAuth: icon(ICON_KEYS.FIGHTER_MINE_DASHOU_AUTH, 'beijing/tubiao/grzx_dashou.jpg'),
|
iconDashouAuth: icon(ICON_KEYS.FIGHTER_MINE_DASHOU_AUTH, 'beijing/tubiao/grzx_dashou.jpg'),
|
||||||
|
iconComplaint: icon(ICON_KEYS.FIGHTER_COMPLAINT_RECORD, 'beijing/guanshiduan/icon-contact.png'),
|
||||||
iconClear: icon(ICON_KEYS.FIGHTER_MINE_CLEAR, 'beijing/tubiao/grzx_qingchu.jpg'),
|
iconClear: icon(ICON_KEYS.FIGHTER_MINE_CLEAR, 'beijing/tubiao/grzx_qingchu.jpg'),
|
||||||
iconSwitch: icon(ICON_KEYS.FIGHTER_MINE_SWITCH, `${ICON_FOLDER}/fighter_mine_switch.png`),
|
iconSwitch: icon(ICON_KEYS.FIGHTER_MINE_SWITCH, `${ICON_FOLDER}/fighter_mine_switch.png`),
|
||||||
iconRecord: icon(ICON_KEYS.FIGHTER_MINE_RECORD, 'beijing/guanshiduan/icon-record.png'),
|
iconRecord: icon(ICON_KEYS.FIGHTER_MINE_RECORD, 'beijing/guanshiduan/icon-record.png'),
|
||||||
@@ -329,7 +330,12 @@ Page(createPage({
|
|||||||
push('contactZuzhang', '联系组长', img.iconContact);
|
push('contactZuzhang', '联系组长', img.iconContact);
|
||||||
}
|
}
|
||||||
push('goToKefu', '在线客服', img.iconKefu);
|
push('goToKefu', '在线客服', img.iconKefu);
|
||||||
push('onTapShangjiaAuth', d.shangjiaCertified ? '进入商家端' : '商家认证', img.iconShangjia);
|
push('goToComplaintCreate', '投诉反馈', img.iconComplaint || img.iconContact);
|
||||||
|
push('goToComplaintList', '投诉记录', img.iconComplaint || img.iconRecord);
|
||||||
|
// 龙先生:不提供前端商家认证,仅已开通时进入商家端
|
||||||
|
if (d.shangjiaCertified) {
|
||||||
|
push('onTapShangjiaAuth', '进入商家端', img.iconShangjia);
|
||||||
|
}
|
||||||
push('onTapStaffAuth', isStaffMode() ? '商家客服工作台' : '商家客服入驻', img.iconKefu || img.iconShangjia);
|
push('onTapStaffAuth', isStaffMode() ? '商家客服工作台' : '商家客服入驻', img.iconKefu || img.iconShangjia);
|
||||||
if (d.showPindaoEntry) {
|
if (d.showPindaoEntry) {
|
||||||
push('openPindaoModal', '频道', img.iconPindao);
|
push('openPindaoModal', '频道', img.iconPindao);
|
||||||
@@ -1166,7 +1172,7 @@ Page(createPage({
|
|||||||
|
|
||||||
enterShangjiaCenter() {
|
enterShangjiaCenter() {
|
||||||
if (!this.data.shangjiaCertified) {
|
if (!this.data.shangjiaCertified) {
|
||||||
wx.navigateTo({ url: '/pages/verify/verify?type=shangjia' });
|
wx.showToast({ title: '请联系客服开通商家', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
enterLockedRole('shangjia', getApp());
|
enterLockedRole('shangjia', getApp());
|
||||||
@@ -1177,10 +1183,13 @@ Page(createPage({
|
|||||||
this.enterShangjiaCenter();
|
this.enterShangjiaCenter();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
wx.navigateTo({ url: '/pages/verify/verify?type=shangjia' });
|
wx.showToast({ title: '请联系客服开通商家', icon: 'none' });
|
||||||
},
|
},
|
||||||
goToReceiveOrder() { wx.switchTab({ url: '/pages/accept-order/accept-order' }) },
|
goToReceiveOrder() { wx.switchTab({ url: '/pages/accept-order/accept-order' }) },
|
||||||
|
|
||||||
|
goToComplaintList() { wx.navigateTo({ url: '/pages/gongdan/list/list' }) },
|
||||||
|
goToComplaintCreate() { wx.navigateTo({ url: '/pages/gongdan/create/create' }) },
|
||||||
|
|
||||||
async loadMyZhidingOrders() {
|
async loadMyZhidingOrders() {
|
||||||
if (!isCenterPageActive(this, 'isDashou', 'dashoustatus')) return;
|
if (!isCenterPageActive(this, 'isDashou', 'dashoustatus')) return;
|
||||||
try {
|
try {
|
||||||
|
|||||||
@@ -3,7 +3,8 @@
|
|||||||
"global-notification": "/components/global-notification/global-notification",
|
"global-notification": "/components/global-notification/global-notification",
|
||||||
"chenghao-tag": "/components/chenghao-tag/chenghao-tag",
|
"chenghao-tag": "/components/chenghao-tag/chenghao-tag",
|
||||||
"tab-bar": "/tab-bar/index",
|
"tab-bar": "/tab-bar/index",
|
||||||
"pindao-modal": "/components/pindao-modal/pindao-modal"
|
"pindao-modal": "/components/pindao-modal/pindao-modal",
|
||||||
|
"tousu-float": "/components/tousu-float/tousu-float"
|
||||||
},
|
},
|
||||||
"navigationStyle": "custom",
|
"navigationStyle": "custom",
|
||||||
"backgroundColor": "#fff8e1",
|
"backgroundColor": "#fff8e1",
|
||||||
|
|||||||
@@ -18,6 +18,7 @@
|
|||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
<tab-bar/>
|
<tab-bar/>
|
||||||
|
<tousu-float />
|
||||||
</view>
|
</view>
|
||||||
</block>
|
</block>
|
||||||
|
|
||||||
@@ -27,6 +28,7 @@
|
|||||||
<view class="page-header">
|
<view class="page-header">
|
||||||
<view class="status-bar" style="height:{{statusBar}}px"></view>
|
<view class="status-bar" style="height:{{statusBar}}px"></view>
|
||||||
<view class="nav-bar" style="height:{{navBar - statusBar}}px">
|
<view class="nav-bar" style="height:{{navBar - statusBar}}px">
|
||||||
|
<view class="nav-tousu" catchtap="goToComplaintCreate">投诉</view>
|
||||||
<text class="nav-title">我的</text>
|
<text class="nav-title">我的</text>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
@@ -194,12 +196,13 @@
|
|||||||
<view class="content-bottom"></view>
|
<view class="content-bottom"></view>
|
||||||
</scroll-view>
|
</scroll-view>
|
||||||
|
|
||||||
<view class="follow-kuaishou {{followClass}}" bindtap="toggleFollowKuaishou">
|
<view class="follow-kuaishou {{followClass}}" bindtap="toggleFollowKuaishou" wx:if="{{false}}">
|
||||||
<image class="ks-icon" src="{{ksIcon}}" mode="aspectFit"/>
|
<image class="ks-icon" src="{{ksIcon}}" mode="aspectFit"/>
|
||||||
<text wx:if="{{followExpanded}}" class="ks-text" catchtap="goToGuanzhuKs">关注快手</text>
|
<text wx:if="{{followExpanded}}" class="ks-text" catchtap="goToGuanzhuKs">关注快手</text>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
<tab-bar/>
|
<tab-bar/>
|
||||||
|
<tousu-float />
|
||||||
</view>
|
</view>
|
||||||
</block>
|
</block>
|
||||||
|
|
||||||
|
|||||||
@@ -28,6 +28,24 @@ page {
|
|||||||
background: linear-gradient(180deg, #f7dc51 0%, #ffd061 100%);
|
background: linear-gradient(180deg, #f7dc51 0%, #ffd061 100%);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.nav-tousu {
|
||||||
|
position: absolute;
|
||||||
|
left: 24rpx;
|
||||||
|
top: 50%;
|
||||||
|
transform: translateY(-50%);
|
||||||
|
min-width: 88rpx;
|
||||||
|
height: 48rpx;
|
||||||
|
line-height: 48rpx;
|
||||||
|
text-align: center;
|
||||||
|
padding: 0 16rpx;
|
||||||
|
border-radius: 24rpx;
|
||||||
|
background: rgba(55, 55, 55, 0.55);
|
||||||
|
color: #f5f5f5;
|
||||||
|
font-size: 22rpx;
|
||||||
|
font-weight: 500;
|
||||||
|
z-index: 5;
|
||||||
|
}
|
||||||
|
|
||||||
.status-bar,
|
.status-bar,
|
||||||
.nav-bar,
|
.nav-bar,
|
||||||
.content,
|
.content,
|
||||||
|
|||||||
27
pages/gongdan/chongzhi-list/chongzhi-list.js
Normal file
27
pages/gongdan/chongzhi-list/chongzhi-list.js
Normal file
@@ -0,0 +1,27 @@
|
|||||||
|
import request from '../../../utils/request.js'
|
||||||
|
|
||||||
|
Page({
|
||||||
|
data: { list: [], loading: false, page: 1 },
|
||||||
|
onShow() { this.load(true) },
|
||||||
|
copy(e) { wx.setClipboardData({ data: String(e.currentTarget.dataset.t || '') }) },
|
||||||
|
complain(e) {
|
||||||
|
const id = e.currentTarget.dataset.id
|
||||||
|
wx.navigateTo({ url: `/pages/gongdan/create/create?leixing=2&chongzhi_id=${encodeURIComponent(id)}` })
|
||||||
|
},
|
||||||
|
async load(reset) {
|
||||||
|
if (this.data.loading) return
|
||||||
|
this.setData({ loading: true })
|
||||||
|
try {
|
||||||
|
const page = reset ? 1 : this.data.page
|
||||||
|
const res = await request({ url: '/gongdan/chongzhi-list/', method: 'POST', data: { page, page_size: 20 } })
|
||||||
|
const body = res.data || {}
|
||||||
|
if (body.code === 200 || body.code === 0) {
|
||||||
|
const rows = (body.data && body.data.list) || []
|
||||||
|
this.setData({ list: reset ? rows : this.data.list.concat(rows), page: page + 1 })
|
||||||
|
}
|
||||||
|
} finally {
|
||||||
|
this.setData({ loading: false })
|
||||||
|
}
|
||||||
|
},
|
||||||
|
onReachBottom() { this.load(false) },
|
||||||
|
})
|
||||||
1
pages/gongdan/chongzhi-list/chongzhi-list.json
Normal file
1
pages/gongdan/chongzhi-list/chongzhi-list.json
Normal file
@@ -0,0 +1 @@
|
|||||||
|
{"navigationBarTitleText":"充值记录","usingComponents":{}}
|
||||||
13
pages/gongdan/chongzhi-list/chongzhi-list.wxml
Normal file
13
pages/gongdan/chongzhi-list/chongzhi-list.wxml
Normal file
@@ -0,0 +1,13 @@
|
|||||||
|
<view class="page">
|
||||||
|
<view wx:if="{{!list.length && !loading}}" class="empty">暂无充值记录</view>
|
||||||
|
<view class="card" wx:for="{{list}}" wx:key="dingdan_id">
|
||||||
|
<view class="row">
|
||||||
|
<text class="t">{{item.leixing_label}}</text>
|
||||||
|
<text class="s">{{item.zhuangtai_label}}</text>
|
||||||
|
</view>
|
||||||
|
<view class="amt">¥{{item.jine}}</view>
|
||||||
|
<view class="id" bindtap="copy" data-t="{{item.dingdan_id}}">充值ID:{{item.dingdan_id}}(点复制)</view>
|
||||||
|
<view class="time">{{item.CreateTime}}</view>
|
||||||
|
<view class="act" bindtap="complain" data-id="{{item.dingdan_id}}">投诉此笔充值</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
9
pages/gongdan/chongzhi-list/chongzhi-list.wxss
Normal file
9
pages/gongdan/chongzhi-list/chongzhi-list.wxss
Normal file
@@ -0,0 +1,9 @@
|
|||||||
|
.page{padding:24rpx;background:#f5f6f8;min-height:100vh}
|
||||||
|
.empty{text-align:center;color:#999;padding:80rpx}
|
||||||
|
.card{background:#fff;border-radius:16rpx;padding:24rpx;margin-bottom:16rpx}
|
||||||
|
.row{display:flex;justify-content:space-between}
|
||||||
|
.t{font-size:30rpx;font-weight:600}
|
||||||
|
.s{font-size:22rpx;color:#856404}
|
||||||
|
.amt{font-size:36rpx;margin-top:8rpx;color:#111}
|
||||||
|
.id,.time{font-size:22rpx;color:#888;margin-top:8rpx}
|
||||||
|
.act{margin-top:16rpx;color:#2b6de5;font-size:26rpx}
|
||||||
154
pages/gongdan/create/create.js
Normal file
154
pages/gongdan/create/create.js
Normal file
@@ -0,0 +1,154 @@
|
|||||||
|
import request from '../../../utils/request.js'
|
||||||
|
import { openCustomerServiceChat } from '../../../utils/kefu-nav.js'
|
||||||
|
|
||||||
|
const TYPES = [
|
||||||
|
{ value: 1, label: '订单投诉' },
|
||||||
|
{ value: 2, label: '充值投诉' },
|
||||||
|
{ value: 3, label: '罚款投诉' },
|
||||||
|
{ value: 4, label: '管事投诉' },
|
||||||
|
{ value: 5, label: '被骗投诉' },
|
||||||
|
]
|
||||||
|
|
||||||
|
Page({
|
||||||
|
data: {
|
||||||
|
types: TYPES,
|
||||||
|
leixing: 1,
|
||||||
|
order_id: '',
|
||||||
|
chongzhi_id: '',
|
||||||
|
fadan_id: '',
|
||||||
|
guanshi_id: '',
|
||||||
|
shuoming: '',
|
||||||
|
images: [],
|
||||||
|
maxImages: 9,
|
||||||
|
submitting: false,
|
||||||
|
},
|
||||||
|
|
||||||
|
onLoad(q) {
|
||||||
|
const patch = {}
|
||||||
|
if (q.leixing) patch.leixing = Number(q.leixing) || 1
|
||||||
|
if (q.order_id) patch.order_id = decodeURIComponent(q.order_id)
|
||||||
|
if (q.chongzhi_id) patch.chongzhi_id = decodeURIComponent(q.chongzhi_id)
|
||||||
|
if (q.fadan_id) patch.fadan_id = decodeURIComponent(q.fadan_id)
|
||||||
|
if (Object.keys(patch).length) this.setData(patch)
|
||||||
|
},
|
||||||
|
|
||||||
|
onPickType(e) { this.setData({ leixing: Number(e.currentTarget.dataset.v) }) },
|
||||||
|
onOrderId(e) { this.setData({ order_id: e.detail.value }) },
|
||||||
|
onChongzhiId(e) { this.setData({ chongzhi_id: e.detail.value }) },
|
||||||
|
onFadanId(e) { this.setData({ fadan_id: e.detail.value }) },
|
||||||
|
onGuanshiId(e) { this.setData({ guanshi_id: e.detail.value }) },
|
||||||
|
onShuoming(e) { this.setData({ shuoming: e.detail.value }) },
|
||||||
|
|
||||||
|
openMiniKefu() { openCustomerServiceChat() },
|
||||||
|
openWxKefu() {
|
||||||
|
const app = getApp()
|
||||||
|
const cfg = app.globalData.kefuConfig || {}
|
||||||
|
if (!cfg.link || !cfg.enterpriseId) {
|
||||||
|
wx.showToast({ title: '微信客服未配置', icon: 'none' })
|
||||||
|
return
|
||||||
|
}
|
||||||
|
wx.openCustomerServiceChat({
|
||||||
|
extInfo: { url: cfg.link },
|
||||||
|
corpId: cfg.enterpriseId,
|
||||||
|
fail: () => wx.showToast({ title: '打开微信客服失败', icon: 'none' }),
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
goChongzhiList() { wx.navigateTo({ url: '/pages/gongdan/chongzhi-list/chongzhi-list' }) },
|
||||||
|
goPenalty() { wx.navigateTo({ url: '/pages/penalty/penalty/penalty' }) },
|
||||||
|
goMyList() { wx.navigateTo({ url: '/pages/gongdan/list/list' }) },
|
||||||
|
|
||||||
|
chooseImg() {
|
||||||
|
const left = this.data.maxImages - this.data.images.length
|
||||||
|
wx.chooseMedia({
|
||||||
|
count: left,
|
||||||
|
mediaType: ['image'],
|
||||||
|
success: async (res) => {
|
||||||
|
wx.showLoading({ title: '上传中' })
|
||||||
|
try {
|
||||||
|
const urls = [...this.data.images]
|
||||||
|
for (const f of res.tempFiles || []) {
|
||||||
|
const url = await this.uploadOne(f.tempFilePath)
|
||||||
|
if (url) urls.push(url)
|
||||||
|
}
|
||||||
|
this.setData({ images: urls.slice(0, this.data.maxImages) })
|
||||||
|
} catch (e) {
|
||||||
|
wx.showToast({ title: '上传失败', icon: 'none' })
|
||||||
|
} finally {
|
||||||
|
wx.hideLoading()
|
||||||
|
}
|
||||||
|
},
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
uploadOne(filePath) {
|
||||||
|
const app = getApp()
|
||||||
|
const base = (app.globalData.apiBaseUrl || '').replace(/\/$/, '')
|
||||||
|
const token = wx.getStorageSync('token') || ''
|
||||||
|
return new Promise((resolve, reject) => {
|
||||||
|
wx.uploadFile({
|
||||||
|
url: `${base}/gongdan/upload-image/`,
|
||||||
|
filePath,
|
||||||
|
name: 'file',
|
||||||
|
header: { Authorization: token ? `Bearer ${token}` : '' },
|
||||||
|
success: (res) => {
|
||||||
|
try {
|
||||||
|
const body = JSON.parse(res.data || '{}')
|
||||||
|
if ((body.code === 200 || body.code === 0) && body.data && body.data.url) {
|
||||||
|
resolve(body.data.url)
|
||||||
|
} else reject(new Error(body.message || '上传失败'))
|
||||||
|
} catch (e) { reject(e) }
|
||||||
|
},
|
||||||
|
fail: reject,
|
||||||
|
})
|
||||||
|
})
|
||||||
|
},
|
||||||
|
|
||||||
|
delImg(e) {
|
||||||
|
const i = e.currentTarget.dataset.i
|
||||||
|
const images = this.data.images.slice()
|
||||||
|
images.splice(i, 1)
|
||||||
|
this.setData({ images })
|
||||||
|
},
|
||||||
|
|
||||||
|
preview(e) {
|
||||||
|
wx.previewImage({ current: e.currentTarget.dataset.url, urls: this.data.images })
|
||||||
|
},
|
||||||
|
|
||||||
|
async submit() {
|
||||||
|
if (this.data.submitting) return
|
||||||
|
if (!(this.data.shuoming || '').trim()) {
|
||||||
|
wx.showToast({ title: '请填写投诉说明', icon: 'none' })
|
||||||
|
return
|
||||||
|
}
|
||||||
|
this.setData({ submitting: true })
|
||||||
|
try {
|
||||||
|
const res = await request({
|
||||||
|
url: '/gongdan/create/',
|
||||||
|
method: 'POST',
|
||||||
|
data: {
|
||||||
|
leixing: this.data.leixing,
|
||||||
|
shuoming: this.data.shuoming,
|
||||||
|
order_id: this.data.order_id,
|
||||||
|
chongzhi_id: this.data.chongzhi_id,
|
||||||
|
fadan_id: this.data.fadan_id,
|
||||||
|
guanshi_id: this.data.guanshi_id,
|
||||||
|
images: this.data.images,
|
||||||
|
},
|
||||||
|
})
|
||||||
|
const body = res.data || {}
|
||||||
|
if (body.code === 200 || body.code === 0) {
|
||||||
|
wx.showToast({ title: '提交成功', icon: 'success' })
|
||||||
|
setTimeout(() => {
|
||||||
|
wx.redirectTo({ url: '/pages/gongdan/list/list' })
|
||||||
|
}, 500)
|
||||||
|
} else {
|
||||||
|
wx.showToast({ title: body.message || body.msg || '提交失败', icon: 'none' })
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
wx.showToast({ title: '网络错误', icon: 'none' })
|
||||||
|
} finally {
|
||||||
|
this.setData({ submitting: false })
|
||||||
|
}
|
||||||
|
},
|
||||||
|
})
|
||||||
1
pages/gongdan/create/create.json
Normal file
1
pages/gongdan/create/create.json
Normal file
@@ -0,0 +1 @@
|
|||||||
|
{"navigationBarTitleText":"我要投诉","usingComponents":{}}
|
||||||
57
pages/gongdan/create/create.wxml
Normal file
57
pages/gongdan/create/create.wxml
Normal file
@@ -0,0 +1,57 @@
|
|||||||
|
<view class="page">
|
||||||
|
<view class="cs-bar">
|
||||||
|
<view class="cs-btn" bindtap="openMiniKefu">小程序客服</view>
|
||||||
|
<view class="cs-btn cs-wx" bindtap="openWxKefu">微信客服</view>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<view class="section">
|
||||||
|
<view class="label">投诉类型</view>
|
||||||
|
<view class="type-row">
|
||||||
|
<view
|
||||||
|
wx:for="{{types}}"
|
||||||
|
wx:key="value"
|
||||||
|
class="type-chip {{leixing==item.value?'on':''}}"
|
||||||
|
data-v="{{item.value}}"
|
||||||
|
bindtap="onPickType"
|
||||||
|
>{{item.label}}</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<view class="section" wx:if="{{leixing==1}}">
|
||||||
|
<view class="label">订单ID <text class="req">*</text></view>
|
||||||
|
<input class="input" placeholder="请输入或粘贴订单ID" value="{{order_id}}" bindinput="onOrderId"/>
|
||||||
|
</view>
|
||||||
|
<view class="section" wx:if="{{leixing==2}}">
|
||||||
|
<view class="label">充值记录ID <text class="req">*</text></view>
|
||||||
|
<input class="input" placeholder="请输入充值记录ID" value="{{chongzhi_id}}" bindinput="onChongzhiId"/>
|
||||||
|
<view class="link" bindtap="goChongzhiList">去充值记录复制 →</view>
|
||||||
|
</view>
|
||||||
|
<view class="section" wx:if="{{leixing==3}}">
|
||||||
|
<view class="label">罚单ID <text class="req">*</text></view>
|
||||||
|
<input class="input" placeholder="请输入罚单ID" value="{{fadan_id}}" bindinput="onFadanId"/>
|
||||||
|
<view class="link" bindtap="goPenalty">去罚款页查看 →</view>
|
||||||
|
</view>
|
||||||
|
<view class="section" wx:if="{{leixing==4}}">
|
||||||
|
<view class="label">管事ID(选填)</view>
|
||||||
|
<input class="input" placeholder="被投诉管事UID,可不填" value="{{guanshi_id}}" bindinput="onGuanshiId"/>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<view class="section">
|
||||||
|
<view class="label">投诉说明 <text class="req">*</text></view>
|
||||||
|
<textarea class="textarea" maxlength="500" placeholder="请详细描述问题" value="{{shuoming}}" bindinput="onShuoming"/>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<view class="section">
|
||||||
|
<view class="label">证据图片(最多{{maxImages}}张)</view>
|
||||||
|
<view class="img-row">
|
||||||
|
<view class="img-item" wx:for="{{images}}" wx:key="*this">
|
||||||
|
<image src="{{item}}" mode="aspectFill" bindtap="preview" data-url="{{item}}"/>
|
||||||
|
<view class="del" data-i="{{index}}" catchtap="delImg">×</view>
|
||||||
|
</view>
|
||||||
|
<view class="img-add" wx:if="{{images.length < maxImages}}" bindtap="chooseImg">+</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<button class="submit" loading="{{submitting}}" bindtap="submit">提交投诉</button>
|
||||||
|
<view class="foot-link" bindtap="goMyList">查看我的投诉记录</view>
|
||||||
|
</view>
|
||||||
20
pages/gongdan/create/create.wxss
Normal file
20
pages/gongdan/create/create.wxss
Normal file
@@ -0,0 +1,20 @@
|
|||||||
|
.page{padding:24rpx 28rpx 80rpx;background:#f5f6f8;min-height:100vh;box-sizing:border-box}
|
||||||
|
.cs-bar{display:flex;gap:16rpx;margin-bottom:24rpx}
|
||||||
|
.cs-btn{flex:1;text-align:center;padding:20rpx 0;border-radius:12rpx;background:#fff;font-size:28rpx;color:#1a1a1a;border:1rpx solid #e5e5e5}
|
||||||
|
.cs-wx{background:#07c160;color:#fff;border-color:#07c160}
|
||||||
|
.section{background:#fff;border-radius:16rpx;padding:24rpx;margin-bottom:20rpx}
|
||||||
|
.label{font-size:28rpx;color:#333;margin-bottom:16rpx;font-weight:500}
|
||||||
|
.req{color:#e54}
|
||||||
|
.type-row{display:flex;flex-wrap:wrap;gap:12rpx}
|
||||||
|
.type-chip{padding:12rpx 22rpx;border-radius:999rpx;background:#f0f1f3;font-size:24rpx;color:#666}
|
||||||
|
.type-chip.on{background:#1a1a1a;color:#fff}
|
||||||
|
.input{height:72rpx;background:#f7f8fa;border-radius:10rpx;padding:0 20rpx;font-size:28rpx}
|
||||||
|
.textarea{width:100%;min-height:180rpx;background:#f7f8fa;border-radius:10rpx;padding:16rpx 20rpx;font-size:28rpx;box-sizing:border-box}
|
||||||
|
.link{margin-top:12rpx;font-size:24rpx;color:#2b6de5}
|
||||||
|
.img-row{display:flex;flex-wrap:wrap;gap:16rpx}
|
||||||
|
.img-item,.img-add{width:160rpx;height:160rpx;border-radius:12rpx;position:relative;overflow:hidden;background:#f0f1f3}
|
||||||
|
.img-item image{width:100%;height:100%}
|
||||||
|
.del{position:absolute;right:0;top:0;width:40rpx;height:40rpx;background:rgba(0,0,0,.55);color:#fff;text-align:center;line-height:40rpx;font-size:28rpx}
|
||||||
|
.img-add{display:flex;align-items:center;justify-content:center;font-size:64rpx;color:#bbb}
|
||||||
|
.submit{margin-top:32rpx;background:#1a1a1a;color:#fff;border-radius:12rpx;font-size:30rpx}
|
||||||
|
.foot-link{text-align:center;margin-top:28rpx;color:#666;font-size:26rpx}
|
||||||
63
pages/gongdan/detail/detail.js
Normal file
63
pages/gongdan/detail/detail.js
Normal file
@@ -0,0 +1,63 @@
|
|||||||
|
import request from '../../../utils/request.js'
|
||||||
|
|
||||||
|
Page({
|
||||||
|
data: {
|
||||||
|
detail: null,
|
||||||
|
imageList: [],
|
||||||
|
shengjiList: [],
|
||||||
|
escShow: false,
|
||||||
|
escText: '',
|
||||||
|
escLoading: false,
|
||||||
|
id: '',
|
||||||
|
},
|
||||||
|
onLoad(q) {
|
||||||
|
this.setData({ id: q.id || '' })
|
||||||
|
this.load()
|
||||||
|
},
|
||||||
|
async load() {
|
||||||
|
const res = await request({ url: '/gongdan/detail/', method: 'POST', data: { gongdan_id: this.data.id } })
|
||||||
|
const body = res.data || {}
|
||||||
|
if (body.code === 200 || body.code === 0) {
|
||||||
|
const d = body.data || {}
|
||||||
|
this.setData({
|
||||||
|
detail: d,
|
||||||
|
imageList: Array.isArray(d.images) ? d.images : [],
|
||||||
|
shengjiList: Array.isArray(d.shengji_list) ? d.shengji_list : [],
|
||||||
|
})
|
||||||
|
}
|
||||||
|
},
|
||||||
|
copy(e) {
|
||||||
|
wx.setClipboardData({ data: String(e.currentTarget.dataset.t || '') })
|
||||||
|
},
|
||||||
|
preview(e) {
|
||||||
|
const urls = (this.data.imageList || []).map(i => i.url).filter(Boolean)
|
||||||
|
wx.previewImage({ current: e.currentTarget.dataset.url, urls })
|
||||||
|
},
|
||||||
|
async markBad() {
|
||||||
|
const res = await request({ url: '/gongdan/dissatisfied/', method: 'POST', data: { gongdan_id: this.data.id } })
|
||||||
|
if ((res.data || {}).code === 200) {
|
||||||
|
wx.showToast({ title: '已标记', icon: 'success' })
|
||||||
|
this.load()
|
||||||
|
} else wx.showToast({ title: (res.data || {}).message || '失败', icon: 'none' })
|
||||||
|
},
|
||||||
|
showEsc() { this.setData({ escShow: true }) },
|
||||||
|
onEsc(e) { this.setData({ escText: e.detail.value }) },
|
||||||
|
async doEsc() {
|
||||||
|
if (!this.data.escText.trim()) return wx.showToast({ title: '请填写补充说明', icon: 'none' })
|
||||||
|
this.setData({ escLoading: true })
|
||||||
|
try {
|
||||||
|
const res = await request({
|
||||||
|
url: '/gongdan/escalate/',
|
||||||
|
method: 'POST',
|
||||||
|
data: { gongdan_id: this.data.id, shuoming: this.data.escText },
|
||||||
|
})
|
||||||
|
if ((res.data || {}).code === 200) {
|
||||||
|
wx.showToast({ title: '已提交', icon: 'success' })
|
||||||
|
this.setData({ escShow: false, escText: '' })
|
||||||
|
this.load()
|
||||||
|
} else wx.showToast({ title: (res.data || {}).message || '失败', icon: 'none' })
|
||||||
|
} finally {
|
||||||
|
this.setData({ escLoading: false })
|
||||||
|
}
|
||||||
|
},
|
||||||
|
})
|
||||||
1
pages/gongdan/detail/detail.json
Normal file
1
pages/gongdan/detail/detail.json
Normal file
@@ -0,0 +1 @@
|
|||||||
|
{"navigationBarTitleText":"工单详情","usingComponents":{}}
|
||||||
34
pages/gongdan/detail/detail.wxml
Normal file
34
pages/gongdan/detail/detail.wxml
Normal file
@@ -0,0 +1,34 @@
|
|||||||
|
<view class="page" wx:if="{{detail}}">
|
||||||
|
<view class="card">
|
||||||
|
<view class="row"><text>{{detail.leixing_label}}</text><text class="status">{{detail.zhuangtai_label}}</text></view>
|
||||||
|
<view class="line" bindtap="copy" data-t="{{detail.gongdan_id}}">工单号:{{detail.gongdan_id}} 复制</view>
|
||||||
|
<view class="line" wx:if="{{detail.order_id}}" bindtap="copy" data-t="{{detail.order_id}}">订单ID:{{detail.order_id}}</view>
|
||||||
|
<view class="line" wx:if="{{detail.chongzhi_id}}" bindtap="copy" data-t="{{detail.chongzhi_id}}">充值ID:{{detail.chongzhi_id}}</view>
|
||||||
|
<view class="line" wx:if="{{detail.fadan_id}}" bindtap="copy" data-t="{{detail.fadan_id}}">罚单ID:{{detail.fadan_id}}</view>
|
||||||
|
<view class="block">{{detail.shuoming}}</view>
|
||||||
|
<view class="imgs" wx:if="{{imageList.length}}">
|
||||||
|
<image wx:for="{{imageList}}" wx:key="url" src="{{item.url}}" mode="aspectFill" bindtap="preview" data-url="{{item.url}}"/>
|
||||||
|
</view>
|
||||||
|
<view class="line" wx:if="{{detail.chuli_jieguo}}">处理结果:{{detail.chuli_jieguo}}</view>
|
||||||
|
<view class="line" wx:if="{{detail.chuliren_name}}">处理人:{{detail.chuliren_name}}</view>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<view class="card" wx:if="{{shengjiList.length}}">
|
||||||
|
<view class="h">补充说明记录</view>
|
||||||
|
<view wx:for="{{shengjiList}}" wx:key="cishu" class="sj">
|
||||||
|
<text>第{{item.cishu}}次:{{item.shuoming}}</text>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<view class="actions" wx:if="{{detail.zhuangtai == 2}}">
|
||||||
|
<button bindtap="markBad">不满意</button>
|
||||||
|
</view>
|
||||||
|
<view class="actions" wx:if="{{detail.zhuangtai == 2 || detail.zhuangtai == 3}}">
|
||||||
|
<button class="primary" bindtap="showEsc">继续投诉</button>
|
||||||
|
</view>
|
||||||
|
|
||||||
|
<view class="esc" wx:if="{{escShow}}">
|
||||||
|
<textarea placeholder="补充说明" value="{{escText}}" bindinput="onEsc"/>
|
||||||
|
<button class="primary" loading="{{escLoading}}" bindtap="doEsc">提交补充</button>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
14
pages/gongdan/detail/detail.wxss
Normal file
14
pages/gongdan/detail/detail.wxss
Normal file
@@ -0,0 +1,14 @@
|
|||||||
|
.page{padding:24rpx;background:#f5f6f8;min-height:100vh}
|
||||||
|
.card{background:#fff;border-radius:16rpx;padding:24rpx;margin-bottom:20rpx}
|
||||||
|
.row{display:flex;justify-content:space-between;font-size:30rpx;font-weight:600}
|
||||||
|
.status{font-size:24rpx;font-weight:400;color:#856404}
|
||||||
|
.line{font-size:24rpx;color:#666;margin-top:12rpx}
|
||||||
|
.block{margin-top:16rpx;font-size:28rpx;color:#333;line-height:1.5}
|
||||||
|
.imgs{display:flex;flex-wrap:wrap;gap:12rpx;margin-top:16rpx}
|
||||||
|
.imgs image{width:160rpx;height:160rpx;border-radius:10rpx}
|
||||||
|
.h{font-size:28rpx;font-weight:600;margin-bottom:12rpx}
|
||||||
|
.sj{font-size:26rpx;color:#555;margin-bottom:8rpx}
|
||||||
|
.actions{margin-top:12rpx}
|
||||||
|
.primary{background:#1a1a1a;color:#fff}
|
||||||
|
.esc{background:#fff;padding:24rpx;border-radius:16rpx;margin-top:20rpx}
|
||||||
|
.esc textarea{width:100%;min-height:160rpx;background:#f7f8fa;padding:16rpx;box-sizing:border-box;margin-bottom:16rpx}
|
||||||
26
pages/gongdan/list/list.js
Normal file
26
pages/gongdan/list/list.js
Normal file
@@ -0,0 +1,26 @@
|
|||||||
|
import request from '../../../utils/request.js'
|
||||||
|
|
||||||
|
Page({
|
||||||
|
data: { list: [], loading: false, page: 1 },
|
||||||
|
onShow() { this.load(true) },
|
||||||
|
goCreate() { wx.navigateTo({ url: '/pages/gongdan/create/create' }) },
|
||||||
|
goDetail(e) {
|
||||||
|
wx.navigateTo({ url: `/pages/gongdan/detail/detail?id=${e.currentTarget.dataset.id}` })
|
||||||
|
},
|
||||||
|
async load(reset) {
|
||||||
|
if (this.data.loading) return
|
||||||
|
this.setData({ loading: true })
|
||||||
|
try {
|
||||||
|
const page = reset ? 1 : this.data.page
|
||||||
|
const res = await request({ url: '/gongdan/my-list/', method: 'POST', data: { page, page_size: 20 } })
|
||||||
|
const body = res.data || {}
|
||||||
|
if (body.code === 200 || body.code === 0) {
|
||||||
|
const rows = (body.data && body.data.list) || []
|
||||||
|
this.setData({ list: reset ? rows : this.data.list.concat(rows), page: page + 1 })
|
||||||
|
}
|
||||||
|
} finally {
|
||||||
|
this.setData({ loading: false })
|
||||||
|
}
|
||||||
|
},
|
||||||
|
onReachBottom() { this.load(false) },
|
||||||
|
})
|
||||||
1
pages/gongdan/list/list.json
Normal file
1
pages/gongdan/list/list.json
Normal file
@@ -0,0 +1 @@
|
|||||||
|
{"navigationBarTitleText":"投诉记录","usingComponents":{}}
|
||||||
13
pages/gongdan/list/list.wxml
Normal file
13
pages/gongdan/list/list.wxml
Normal file
@@ -0,0 +1,13 @@
|
|||||||
|
<view class="page">
|
||||||
|
<view class="top-btn" bindtap="goCreate">+ 我要投诉</view>
|
||||||
|
<view wx:if="{{!list.length && !loading}}" class="empty">暂无投诉记录</view>
|
||||||
|
<view class="card" wx:for="{{list}}" wx:key="gongdan_id" bindtap="goDetail" data-id="{{item.gongdan_id}}">
|
||||||
|
<view class="row">
|
||||||
|
<text class="title">{{item.leixing_label}}</text>
|
||||||
|
<text class="status s{{item.zhuangtai}}">{{item.zhuangtai_label}}</text>
|
||||||
|
</view>
|
||||||
|
<view class="id">工单号 {{item.gongdan_id}}</view>
|
||||||
|
<view class="desc">{{item.shuoming}}</view>
|
||||||
|
<view class="time">{{item.CreateTime}}</view>
|
||||||
|
</view>
|
||||||
|
</view>
|
||||||
13
pages/gongdan/list/list.wxss
Normal file
13
pages/gongdan/list/list.wxss
Normal file
@@ -0,0 +1,13 @@
|
|||||||
|
.page{padding:24rpx;background:#f5f6f8;min-height:100vh;box-sizing:border-box}
|
||||||
|
.top-btn{background:#1a1a1a;color:#fff;text-align:center;padding:22rpx;border-radius:12rpx;margin-bottom:20rpx;font-size:28rpx}
|
||||||
|
.empty{text-align:center;color:#999;padding:80rpx 0}
|
||||||
|
.card{background:#fff;border-radius:16rpx;padding:24rpx;margin-bottom:16rpx}
|
||||||
|
.row{display:flex;justify-content:space-between;align-items:center}
|
||||||
|
.title{font-size:30rpx;font-weight:600;color:#222}
|
||||||
|
.status{font-size:22rpx;padding:4rpx 12rpx;border-radius:8rpx;background:#eee}
|
||||||
|
.s1{background:#fff3cd;color:#856404}
|
||||||
|
.s2{background:#d4edda;color:#155724}
|
||||||
|
.s3{background:#f8d7da;color:#721c24}
|
||||||
|
.s4{background:#e2e3e5;color:#383d41}
|
||||||
|
.id,.time{font-size:22rpx;color:#999;margin-top:8rpx}
|
||||||
|
.desc{font-size:26rpx;color:#555;margin-top:12rpx;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
|
||||||
@@ -1,5 +1,5 @@
|
|||||||
{
|
{
|
||||||
"navigationBarTitleText": "星之界",
|
"navigationBarTitleText": "龙先生电竞",
|
||||||
"usingComponents": {
|
"usingComponents": {
|
||||||
"global-notification": "/components/global-notification/global-notification"
|
"global-notification": "/components/global-notification/global-notification"
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -42,6 +42,7 @@ Page({
|
|||||||
showChexiaoModal: false, chexiaoLiyou: '', isChexiaoLoading: false,
|
showChexiaoModal: false, chexiaoLiyou: '', isChexiaoLoading: false,
|
||||||
showTuikuanModal: false, tuikuanLiyou: '', isTuikuanLoading: false,
|
showTuikuanModal: false, tuikuanLiyou: '', isTuikuanLoading: false,
|
||||||
showFakuanModal: false, fakuanLiyou: '', fakuanJine: '', yingxiangQiangdan: true, isFakuanLoading: false,
|
showFakuanModal: false, fakuanLiyou: '', fakuanJine: '', yingxiangQiangdan: true, isFakuanLoading: false,
|
||||||
|
fakuanEvidenceLocal: [],
|
||||||
showGhDashouModal: false, isGhDashouLoading: false,
|
showGhDashouModal: false, isGhDashouLoading: false,
|
||||||
showJiesuanConfirm: false, isJiesuanLoading: false,
|
showJiesuanConfirm: false, isJiesuanLoading: false,
|
||||||
jiesuanPingfen: 0, jiesuanLiuyan: '',
|
jiesuanPingfen: 0, jiesuanLiuyan: '',
|
||||||
@@ -462,9 +463,84 @@ Page({
|
|||||||
if (dingdanId) {
|
if (dingdanId) {
|
||||||
this.jiazaiXiangxiShuju(dingdanId)
|
this.jiazaiXiangxiShuju(dingdanId)
|
||||||
}
|
}
|
||||||
this.setData({ showFakuanModal: true, fakuanLiyou: '', fakuanJine: '', yingxiangQiangdan: true })
|
this.setData({
|
||||||
|
showFakuanModal: true,
|
||||||
|
fakuanLiyou: '',
|
||||||
|
fakuanJine: '',
|
||||||
|
yingxiangQiangdan: true,
|
||||||
|
fakuanEvidenceLocal: [],
|
||||||
|
})
|
||||||
|
},
|
||||||
|
closeFakuanModal() {
|
||||||
|
this.setData({ showFakuanModal: false, fakuanEvidenceLocal: [] })
|
||||||
|
},
|
||||||
|
chooseFakuanEvidence() {
|
||||||
|
const remain = 9 - this.data.fakuanEvidenceLocal.length
|
||||||
|
if (remain <= 0) return
|
||||||
|
wx.chooseMedia({
|
||||||
|
count: remain,
|
||||||
|
mediaType: ['image'],
|
||||||
|
sourceType: ['album', 'camera'],
|
||||||
|
success: (res) => {
|
||||||
|
const paths = (res.tempFiles || []).map((f) => f.tempFilePath)
|
||||||
|
this.setData({
|
||||||
|
fakuanEvidenceLocal: this.data.fakuanEvidenceLocal.concat(paths).slice(0, 9),
|
||||||
|
})
|
||||||
|
},
|
||||||
|
})
|
||||||
|
},
|
||||||
|
deleteFakuanEvidence(e) {
|
||||||
|
const idx = e.currentTarget.dataset.index
|
||||||
|
const arr = this.data.fakuanEvidenceLocal.slice()
|
||||||
|
arr.splice(idx, 1)
|
||||||
|
this.setData({ fakuanEvidenceLocal: arr })
|
||||||
|
},
|
||||||
|
previewFakuanEvidence(e) {
|
||||||
|
const url = e.currentTarget.dataset.url
|
||||||
|
const urls = this.data.fakuanEvidenceLocal || []
|
||||||
|
wx.previewImage({ current: url, urls: urls.length ? urls : [url] })
|
||||||
|
},
|
||||||
|
async uploadFakuanEvidenceDraft(localPaths, dingdanId) {
|
||||||
|
if (!localPaths.length) return []
|
||||||
|
const credRes = await request({
|
||||||
|
url: '/dingdan/dsscpz',
|
||||||
|
method: 'POST',
|
||||||
|
data: { dingdan_id: dingdanId, yongtu: 'fakuan_evidence_draft' },
|
||||||
|
})
|
||||||
|
if (!credRes || !credRes.data || credRes.data.code !== 0) {
|
||||||
|
throw new Error((credRes && credRes.data && credRes.data.msg) || '上传凭证失败')
|
||||||
|
}
|
||||||
|
const tokenData = credRes.data.data
|
||||||
|
const credentials = tokenData.credentials || tokenData
|
||||||
|
const COS = require('../../utils/cos-wx-sdk-v5.min.js')
|
||||||
|
const cos = new COS({
|
||||||
|
SimpleUploadMethod: 'putObject',
|
||||||
|
getAuthorization: (_, callback) => {
|
||||||
|
callback({
|
||||||
|
TmpSecretId: credentials.tmpSecretId,
|
||||||
|
TmpSecretKey: credentials.tmpSecretKey,
|
||||||
|
SecurityToken: credentials.sessionToken || '',
|
||||||
|
StartTime: tokenData.startTime,
|
||||||
|
ExpiredTime: tokenData.expiredTime,
|
||||||
|
})
|
||||||
|
},
|
||||||
|
})
|
||||||
|
const bucket = tokenData.bucket || 'julebu-1361527063'
|
||||||
|
const region = tokenData.region || 'ap-shanghai'
|
||||||
|
const uid = wx.getStorageSync('uid') || '0000000'
|
||||||
|
const keys = []
|
||||||
|
for (let i = 0; i < localPaths.length; i++) {
|
||||||
|
const key = `fakuan/shangjiafakuan/zhengju/${uid}_${dingdanId}_draft_${Date.now() + i}.jpg`
|
||||||
|
await new Promise((resolve, reject) => {
|
||||||
|
cos.uploadFile(
|
||||||
|
{ Bucket: bucket, Region: region, Key: key, FilePath: localPaths[i] },
|
||||||
|
(err) => (err ? reject(err) : resolve()),
|
||||||
|
)
|
||||||
|
})
|
||||||
|
keys.push(key)
|
||||||
|
}
|
||||||
|
return keys
|
||||||
},
|
},
|
||||||
closeFakuanModal() { this.setData({ showFakuanModal: false }) },
|
|
||||||
inputFakuanLiyou(e) { this.setData({ fakuanLiyou: e.detail.value.slice(0, 50) }) },
|
inputFakuanLiyou(e) { this.setData({ fakuanLiyou: e.detail.value.slice(0, 50) }) },
|
||||||
inputFakuanJine(e) { this.setData({ fakuanJine: e.detail.value }) },
|
inputFakuanJine(e) { this.setData({ fakuanJine: e.detail.value }) },
|
||||||
toggleQiangdan() { this.setData({ yingxiangQiangdan: !this.data.yingxiangQiangdan }) },
|
toggleQiangdan() { this.setData({ yingxiangQiangdan: !this.data.yingxiangQiangdan }) },
|
||||||
@@ -474,14 +550,22 @@ Page({
|
|||||||
return (jine * this.data.fenhongLilv).toFixed(2)
|
return (jine * this.data.fenhongLilv).toFixed(2)
|
||||||
},
|
},
|
||||||
async tijiaoFakuan() {
|
async tijiaoFakuan() {
|
||||||
const { fakuanLiyou, fakuanJine, jibenShuju, dashouInfo } = this.data
|
const { fakuanLiyou, fakuanJine, jibenShuju, dashouInfo, fakuanEvidenceLocal } = this.data
|
||||||
if (!fakuanLiyou.trim()) { wx.showToast({ title: '请输入罚款原因', icon: 'none' }); return }
|
if (!fakuanLiyou.trim()) { wx.showToast({ title: '请输入罚款原因', icon: 'none' }); return }
|
||||||
const jineNum = parseFloat(fakuanJine)
|
const jineNum = parseFloat(fakuanJine)
|
||||||
if (isNaN(jineNum) || jineNum <= 0) { wx.showToast({ title: '请输入正确的罚款金额', icon: 'none' }); return }
|
if (isNaN(jineNum) || jineNum <= 0) { wx.showToast({ title: '请输入正确的罚款金额', icon: 'none' }); return }
|
||||||
|
if (!fakuanEvidenceLocal.length) {
|
||||||
|
wx.showToast({ title: '请至少上传1张证据图片', icon: 'none' })
|
||||||
|
return
|
||||||
|
}
|
||||||
if (this.data.isFakuanLoading) return
|
if (this.data.isFakuanLoading) return
|
||||||
this.setData({ isFakuanLoading: true })
|
this.setData({ isFakuanLoading: true })
|
||||||
wx.showLoading({ title: '提交中...', mask: true })
|
wx.showLoading({ title: '提交中...', mask: true })
|
||||||
try {
|
try {
|
||||||
|
const evidenceUrls = await this.uploadFakuanEvidenceDraft(
|
||||||
|
fakuanEvidenceLocal,
|
||||||
|
jibenShuju.dingdan_id,
|
||||||
|
)
|
||||||
const res = await request({
|
const res = await request({
|
||||||
url: isStaffMode() ? STAFF_API.penaltyApply : '/dingdan/sjfksq',
|
url: isStaffMode() ? STAFF_API.penaltyApply : '/dingdan/sjfksq',
|
||||||
method: 'POST',
|
method: 'POST',
|
||||||
@@ -490,7 +574,8 @@ Page({
|
|||||||
chufa_liyou: fakuanLiyou,
|
chufa_liyou: fakuanLiyou,
|
||||||
fakuanjine: jineNum.toFixed(2),
|
fakuanjine: jineNum.toFixed(2),
|
||||||
yingxiang_qiangdan: this.data.yingxiangQiangdan ? 1 : 0,
|
yingxiang_qiangdan: this.data.yingxiangQiangdan ? 1 : 0,
|
||||||
dashou_id: dashouInfo.yonghuid
|
dashou_id: dashouInfo.yonghuid,
|
||||||
|
evidence_urls: evidenceUrls,
|
||||||
},
|
},
|
||||||
header: { 'content-type': 'application/json' }
|
header: { 'content-type': 'application/json' }
|
||||||
})
|
})
|
||||||
@@ -498,7 +583,7 @@ Page({
|
|||||||
this.setData({ isFakuanLoading: false })
|
this.setData({ isFakuanLoading: false })
|
||||||
if (res && res.data.code === 0) {
|
if (res && res.data.code === 0) {
|
||||||
wx.showToast({ title: '罚款申请已提交', icon: 'success' })
|
wx.showToast({ title: '罚款申请已提交', icon: 'success' })
|
||||||
this.setData({ showFakuanModal: false })
|
this.setData({ showFakuanModal: false, fakuanEvidenceLocal: [] })
|
||||||
this.jiazaiXiangxiShuju(jibenShuju.dingdan_id)
|
this.jiazaiXiangxiShuju(jibenShuju.dingdan_id)
|
||||||
} else {
|
} else {
|
||||||
wx.showToast({ title: res?.data?.msg || '提交失败', icon: 'none' })
|
wx.showToast({ title: res?.data?.msg || '提交失败', icon: 'none' })
|
||||||
@@ -506,7 +591,7 @@ Page({
|
|||||||
} catch (err) {
|
} catch (err) {
|
||||||
wx.hideLoading()
|
wx.hideLoading()
|
||||||
this.setData({ isFakuanLoading: false })
|
this.setData({ isFakuanLoading: false })
|
||||||
wx.showToast({ title: '网络错误', icon: 'none' })
|
wx.showToast({ title: (err && err.message) || '网络错误', icon: 'none' })
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
|
|||||||
@@ -245,6 +245,16 @@
|
|||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
<view class="fenhong-tip">此次罚款应得分红:¥{{jisuanFenhong()}}(利率 {{fenhongLilv*100}}%)</view>
|
<view class="fenhong-tip">此次罚款应得分红:¥{{jisuanFenhong()}}(利率 {{fenhongLilv*100}}%)</view>
|
||||||
|
<text class="modal-tip">证据图片(至少1张,最多9张)</text>
|
||||||
|
<view class="img-grid-mini">
|
||||||
|
<block wx:for="{{fakuanEvidenceLocal}}" wx:key="*this">
|
||||||
|
<view class="img-box-mini">
|
||||||
|
<image class="img-mini" src="{{item}}" mode="aspectFill" bindtap="previewFakuanEvidence" data-url="{{item}}"/>
|
||||||
|
<view class="img-del-mini" catchtap="deleteFakuanEvidence" data-index="{{index}}">×</view>
|
||||||
|
</view>
|
||||||
|
</block>
|
||||||
|
<view wx:if="{{fakuanEvidenceLocal.length < 9}}" class="img-add-mini" bindtap="chooseFakuanEvidence">+</view>
|
||||||
|
</view>
|
||||||
</view>
|
</view>
|
||||||
<view class="modal-btns">
|
<view class="modal-btns">
|
||||||
<view class="modal-btn cancel" bindtap="closeFakuanModal">取消</view>
|
<view class="modal-btn cancel" bindtap="closeFakuanModal">取消</view>
|
||||||
|
|||||||
@@ -178,6 +178,45 @@ page { background: #fff8e1; }
|
|||||||
border-top: 1rpx dashed rgba(245, 213, 99, 0.5);
|
border-top: 1rpx dashed rgba(245, 213, 99, 0.5);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.img-grid-mini {
|
||||||
|
display: flex;
|
||||||
|
flex-wrap: wrap;
|
||||||
|
gap: 16rpx;
|
||||||
|
margin: 16rpx 0 24rpx;
|
||||||
|
}
|
||||||
|
.img-box-mini, .img-add-mini {
|
||||||
|
width: 140rpx;
|
||||||
|
height: 140rpx;
|
||||||
|
border-radius: 12rpx;
|
||||||
|
position: relative;
|
||||||
|
overflow: hidden;
|
||||||
|
}
|
||||||
|
.img-mini {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
.img-add-mini {
|
||||||
|
border: 2rpx dashed #ccc;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
font-size: 48rpx;
|
||||||
|
color: #999;
|
||||||
|
}
|
||||||
|
.img-del-mini {
|
||||||
|
position: absolute;
|
||||||
|
top: 0;
|
||||||
|
right: 0;
|
||||||
|
width: 36rpx;
|
||||||
|
height: 36rpx;
|
||||||
|
background: rgba(0,0,0,0.55);
|
||||||
|
color: #fff;
|
||||||
|
text-align: center;
|
||||||
|
line-height: 36rpx;
|
||||||
|
font-size: 24rpx;
|
||||||
|
border-radius: 0 0 0 8rpx;
|
||||||
|
}
|
||||||
|
|
||||||
/* ========== 新增:教程按钮样式 ========== */
|
/* ========== 新增:教程按钮样式 ========== */
|
||||||
.tutorial-btn {
|
.tutorial-btn {
|
||||||
position: fixed;
|
position: fixed;
|
||||||
|
|||||||
@@ -417,33 +417,9 @@ Page(createPage({
|
|||||||
},
|
},
|
||||||
|
|
||||||
async onRegister() {
|
async onRegister() {
|
||||||
const { inviteCode } = this.data;
|
// 龙先生:商家由后台开通,禁止前端邀请码自助注册
|
||||||
await this.registerWithInviteCode({
|
wx.showToast({ title: '请联系客服开通商家', icon: 'none' });
|
||||||
inviteCode,
|
this.setData({ isAutoRegistering: false });
|
||||||
apiUrl: '/yonghu/shangjiahuce',
|
|
||||||
role: 'shangjia',
|
|
||||||
statusKey: 'shangjiastatus',
|
|
||||||
successMsg: '商家注册成功',
|
|
||||||
onSuccess: (userData) => {
|
|
||||||
app.globalData.shangjia = userData;
|
|
||||||
const chenghaoList = userData.chenghao_list || [];
|
|
||||||
this.setData({
|
|
||||||
isShangjia: true,
|
|
||||||
nicheng: userData.nicheng || '',
|
|
||||||
sjyue: userData.sjyue || '0.00',
|
|
||||||
fabu: userData.fabu || 0,
|
|
||||||
tuikuan: userData.tuikuan || 0,
|
|
||||||
jinriliushui: userData.jinriliushui || '0.00',
|
|
||||||
jinyueliushui: userData.jinyueliushui || '0.00',
|
|
||||||
jinridingdan: userData.jinridingdan || 0,
|
|
||||||
chenghaoList: chenghaoList,
|
|
||||||
isAutoRegistering: false,
|
|
||||||
});
|
|
||||||
this.loadAvatar();
|
|
||||||
ensureRoleOnCenterPage(this, 'shangjia');
|
|
||||||
lockPrimaryRole('shangjia');
|
|
||||||
},
|
|
||||||
});
|
|
||||||
},
|
},
|
||||||
|
|
||||||
previewAvatar() {
|
previewAvatar() {
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
{
|
{
|
||||||
"navigationBarTitleText": "星之界",
|
"navigationBarTitleText": "龙先生电竞",
|
||||||
"usingComponents": {
|
"usingComponents": {
|
||||||
"global-notification": "/components/global-notification/global-notification",
|
"global-notification": "/components/global-notification/global-notification",
|
||||||
"tab-bar": "/tab-bar/index"
|
"tab-bar": "/tab-bar/index"
|
||||||
|
|||||||
@@ -193,6 +193,11 @@ Page(createPage({
|
|||||||
goToAuth(e) {
|
goToAuth(e) {
|
||||||
const type = e.currentTarget.dataset.type;
|
const type = e.currentTarget.dataset.type;
|
||||||
if (!type || !['dashou', 'shangjia'].includes(type)) return;
|
if (!type || !['dashou', 'shangjia'].includes(type)) return;
|
||||||
|
// 龙先生:商家只能后台开通,前端禁止自助认证
|
||||||
|
if (type === 'shangjia' && !isRoleStatusActive(wx.getStorageSync('shangjiastatus'))) {
|
||||||
|
wx.showToast({ title: '请联系客服开通商家', icon: 'none' });
|
||||||
|
return;
|
||||||
|
}
|
||||||
ensureLogin({ silent: false, page: this })
|
ensureLogin({ silent: false, page: this })
|
||||||
.then(() => restoreStaffContextAfterAuth())
|
.then(() => restoreStaffContextAfterAuth())
|
||||||
.then(() => {
|
.then(() => {
|
||||||
|
|||||||
@@ -2,7 +2,8 @@
|
|||||||
"usingComponents": {
|
"usingComponents": {
|
||||||
"global-notification": "/components/global-notification/global-notification",
|
"global-notification": "/components/global-notification/global-notification",
|
||||||
"tab-bar": "/tab-bar/index",
|
"tab-bar": "/tab-bar/index",
|
||||||
"pindao-modal": "/components/pindao-modal/pindao-modal"
|
"pindao-modal": "/components/pindao-modal/pindao-modal",
|
||||||
|
"tousu-float": "/components/tousu-float/tousu-float"
|
||||||
},
|
},
|
||||||
"navigationBarTitleText": "个人中心",
|
"navigationBarTitleText": "个人中心",
|
||||||
"navigationBarBackgroundColor": "#F7F3ED",
|
"navigationBarBackgroundColor": "#F7F3ED",
|
||||||
|
|||||||
@@ -66,10 +66,6 @@
|
|||||||
<view class="icon-bg"><image src="{{kefuIcon}}" mode="aspectFit" class="icon-color icon-size" /></view>
|
<view class="icon-bg"><image src="{{kefuIcon}}" mode="aspectFit" class="icon-color icon-size" /></view>
|
||||||
<text class="service-name">在线客服</text>
|
<text class="service-name">在线客服</text>
|
||||||
</view>
|
</view>
|
||||||
<view class="service-unit" bindtap="goToGuanzhuA">
|
|
||||||
<view class="icon-bg"><image src="{{guanzhualongIcon}}" mode="aspectFit" class="icon-color icon-size" /></view>
|
|
||||||
<text class="service-name">关注快手</text>
|
|
||||||
</view>
|
|
||||||
<view class="service-unit" wx:if="{{showPindaoEntry}}" bindtap="openPindaoModal">
|
<view class="service-unit" wx:if="{{showPindaoEntry}}" bindtap="openPindaoModal">
|
||||||
<view class="icon-bg"><image src="{{pindaoIcon}}" mode="aspectFit" class="icon-color icon-size" /></view>
|
<view class="icon-bg"><image src="{{pindaoIcon}}" mode="aspectFit" class="icon-color icon-size" /></view>
|
||||||
<text class="service-name">频道</text>
|
<text class="service-name">频道</text>
|
||||||
@@ -77,7 +73,7 @@
|
|||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
<!-- 身份认证(与更多服务同款紧凑布局) -->
|
<!-- 身份:仅接单员 + 商家客服;已开通商家才显示「进入商家」 -->
|
||||||
<view class="section">
|
<view class="section">
|
||||||
<view class="title-line gradient-bg">
|
<view class="title-line gradient-bg">
|
||||||
<text class="title-text">身份认证</text>
|
<text class="title-text">身份认证</text>
|
||||||
@@ -90,13 +86,6 @@
|
|||||||
<text class="service-name">接单员</text>
|
<text class="service-name">接单员</text>
|
||||||
<text class="auth-tag {{dashouCertified ? 'auth-tag-done' : ''}}">{{dashouCertified ? '已认证' : '去认证'}}</text>
|
<text class="auth-tag {{dashouCertified ? 'auth-tag-done' : ''}}">{{dashouCertified ? '已认证' : '去认证'}}</text>
|
||||||
</view>
|
</view>
|
||||||
<view class="service-unit" bindtap="goToAuth" data-type="shangjia">
|
|
||||||
<view class="icon-bg icon-bg-sm">
|
|
||||||
<image src="{{shangjiaIcon}}" mode="aspectFit" class="icon-dark icon-size-sm" />
|
|
||||||
</view>
|
|
||||||
<text class="service-name">商家</text>
|
|
||||||
<text class="auth-tag {{shangjiaCertified ? 'auth-tag-done' : ''}}">{{shangjiaCertified ? '已认证' : '去认证'}}</text>
|
|
||||||
</view>
|
|
||||||
<view class="service-unit" bindtap="goToStaffJoin">
|
<view class="service-unit" bindtap="goToStaffJoin">
|
||||||
<view class="icon-bg icon-bg-sm">
|
<view class="icon-bg icon-bg-sm">
|
||||||
<image src="{{kefuIcon}}" mode="aspectFit" class="icon-dark icon-size-sm" />
|
<image src="{{kefuIcon}}" mode="aspectFit" class="icon-dark icon-size-sm" />
|
||||||
@@ -104,6 +93,13 @@
|
|||||||
<text class="service-name">商家客服</text>
|
<text class="service-name">商家客服</text>
|
||||||
<text class="auth-tag {{staffCertified ? 'auth-tag-done' : ''}}">{{staffTag}}</text>
|
<text class="auth-tag {{staffCertified ? 'auth-tag-done' : ''}}">{{staffTag}}</text>
|
||||||
</view>
|
</view>
|
||||||
|
<view class="service-unit" wx:if="{{shangjiaCertified}}" bindtap="goToAuth" data-type="shangjia">
|
||||||
|
<view class="icon-bg icon-bg-sm">
|
||||||
|
<image src="{{shangjiaIcon}}" mode="aspectFit" class="icon-dark icon-size-sm" />
|
||||||
|
</view>
|
||||||
|
<text class="service-name">进入商家</text>
|
||||||
|
<text class="auth-tag auth-tag-done">已开通</text>
|
||||||
|
</view>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
@@ -121,7 +117,7 @@
|
|||||||
|
|
||||||
<!-- 底部 -->
|
<!-- 底部 -->
|
||||||
<view class="footer">
|
<view class="footer">
|
||||||
<text class="copyright">© 2026 星阙网络技术</text>
|
<text class="copyright">© 2026 龙先生电竞</text>
|
||||||
<text class="divider">|</text>
|
<text class="divider">|</text>
|
||||||
<text class="coop" bindtap="goToCustomService">我要做同款</text>
|
<text class="coop" bindtap="goToCustomService">我要做同款</text>
|
||||||
</view>
|
</view>
|
||||||
@@ -130,6 +126,7 @@
|
|||||||
</view>
|
</view>
|
||||||
|
|
||||||
<tab-bar />
|
<tab-bar />
|
||||||
|
<tousu-float />
|
||||||
<global-notification id="global-notification" />
|
<global-notification id="global-notification" />
|
||||||
<pindao-modal
|
<pindao-modal
|
||||||
visible="{{pindaoVisible}}"
|
visible="{{pindaoVisible}}"
|
||||||
|
|||||||
@@ -38,6 +38,12 @@ Page(createPage({
|
|||||||
|
|
||||||
onLoad(options) {
|
onLoad(options) {
|
||||||
const type = options.type || ''
|
const type = options.type || ''
|
||||||
|
// 龙先生:商家仅后台开通,禁止前端自助认证
|
||||||
|
if (type === 'shangjia') {
|
||||||
|
wx.showToast({ title: '请联系客服开通商家', icon: 'none' })
|
||||||
|
setTimeout(() => wx.navigateBack({ fail: () => wx.switchTab({ url: '/pages/mine/mine' }) }), 500)
|
||||||
|
return
|
||||||
|
}
|
||||||
if (!API_MAP[type]) {
|
if (!API_MAP[type]) {
|
||||||
wx.showToast({ title: '认证类型错误', icon: 'none' })
|
wx.showToast({ title: '认证类型错误', icon: 'none' })
|
||||||
setTimeout(() => wx.navigateBack(), 1500)
|
setTimeout(() => wx.navigateBack(), 1500)
|
||||||
|
|||||||
@@ -1,440 +1,440 @@
|
|||||||
// pages/withdraw/components/mode1/mode1.js — 收款码手动审核纯提现
|
// pages/withdraw/components/mode1/mode1.js — 收款码手动审核纯提现
|
||||||
import request from '../../../../utils/request.js';
|
import request from '../../../../utils/request.js';
|
||||||
import upload from '../../../../utils/upload.js';
|
import upload from '../../../../utils/upload.js';
|
||||||
import PopupService from '../../../../services/popupService.js';
|
import PopupService from '../../../../services/popupService.js';
|
||||||
|
|
||||||
const app = getApp();
|
const app = getApp();
|
||||||
|
|
||||||
const ASSET_TYPES = {
|
const ASSET_TYPES = {
|
||||||
dashou_yue: { leixing: 1, label: '接单员佣金' },
|
dashou_yue: { leixing: 1, label: '接单员佣金' },
|
||||||
dashou_yajin: { leixing: 5, label: '接单员保证金' },
|
dashou_yajin: { leixing: 5, label: '接单员保证金' },
|
||||||
shangjia_yue: { leixing: 6, label: '商家余额' },
|
shangjia_yue: { leixing: 6, label: '商家余额' },
|
||||||
guanshi_fenyong: { leixing: 2, label: '管事分红' },
|
guanshi_fenyong: { leixing: 2, label: '管事分红' },
|
||||||
zuzhang_fenyong: { leixing: 3, label: '组长分红' },
|
zuzhang_fenyong: { leixing: 3, label: '组长分红' },
|
||||||
kaoheguan_fenyong: { leixing: 4, label: '考核官分佣' },
|
kaoheguan_fenyong: { leixing: 4, label: '考核官分佣' },
|
||||||
};
|
};
|
||||||
|
|
||||||
const FROM_ASSET_MAP = {
|
const FROM_ASSET_MAP = {
|
||||||
dashou: 'dashou_yue',
|
dashou: 'dashou_yue',
|
||||||
guanshi: 'guanshi_fenyong',
|
guanshi: 'guanshi_fenyong',
|
||||||
zuzhang: 'zuzhang_fenyong',
|
zuzhang: 'zuzhang_fenyong',
|
||||||
kaoheguan: 'kaoheguan_fenyong',
|
kaoheguan: 'kaoheguan_fenyong',
|
||||||
kaohe: 'kaoheguan_fenyong',
|
kaohe: 'kaoheguan_fenyong',
|
||||||
shangjia: 'shangjia_yue',
|
shangjia: 'shangjia_yue',
|
||||||
yajin: 'dashou_yajin',
|
yajin: 'dashou_yajin',
|
||||||
};
|
};
|
||||||
|
|
||||||
Component({
|
Component({
|
||||||
properties: { options: { type: Object, value: {} } },
|
properties: { options: { type: Object, value: {} } },
|
||||||
data: {
|
data: {
|
||||||
imgUrls: { iconWechat: '', iconAlipay: '' },
|
imgUrls: { iconWechat: '', iconAlipay: '' },
|
||||||
assetList: [],
|
assetList: [],
|
||||||
displayAssetList: [],
|
displayAssetList: [],
|
||||||
totalAmount: '0.00',
|
totalAmount: '0.00',
|
||||||
canWithdraw: false,
|
canWithdraw: false,
|
||||||
isLoadingAssets: false,
|
isLoadingAssets: false,
|
||||||
selectedAsset: null,
|
selectedAsset: null,
|
||||||
tixianAmount: '',
|
tixianAmount: '',
|
||||||
feeRateText: '--',
|
feeRateText: '--',
|
||||||
currentRate: '0%',
|
currentRate: '0%',
|
||||||
shouxufei: '0.00',
|
shouxufei: '0.00',
|
||||||
shijidaozhang: '0.00',
|
shijidaozhang: '0.00',
|
||||||
showTixianModal: false,
|
showTixianModal: false,
|
||||||
submitting: false,
|
submitting: false,
|
||||||
txfangshi: null,
|
txfangshi: null,
|
||||||
txdianhua: '',
|
txdianhua: '',
|
||||||
txzh: '',
|
txzh: '',
|
||||||
txtupian: '',
|
txtupian: '',
|
||||||
showSkfsModal: false,
|
showSkfsModal: false,
|
||||||
tempTxfangshi: null,
|
tempTxfangshi: null,
|
||||||
tempTxPhone: '',
|
tempTxPhone: '',
|
||||||
tempTxAccount: '',
|
tempTxAccount: '',
|
||||||
tempTxImage: '',
|
tempTxImage: '',
|
||||||
choosingImage: false,
|
choosingImage: false,
|
||||||
},
|
},
|
||||||
|
|
||||||
attached() {
|
attached() {
|
||||||
this.initImageUrls();
|
this.initImageUrls();
|
||||||
this.loadAllAssets();
|
this.loadAllAssets();
|
||||||
this.loadWithdrawMethod();
|
this.loadWithdrawMethod();
|
||||||
},
|
},
|
||||||
|
|
||||||
pageLifetimes: {
|
pageLifetimes: {
|
||||||
show() {
|
show() {
|
||||||
this.registerNotification();
|
this.registerNotification();
|
||||||
this.loadAllAssets();
|
this.loadAllAssets();
|
||||||
PopupService.checkAndShow(this, 'tixian');
|
PopupService.checkAndShow(this, 'tixian');
|
||||||
},
|
},
|
||||||
hide() {
|
hide() {
|
||||||
const popup = this.selectComponent('#popupNotice');
|
const popup = this.selectComponent('#popupNotice');
|
||||||
popup?.cleanup?.();
|
popup?.cleanup?.();
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
|
||||||
methods: {
|
methods: {
|
||||||
formatRatePercent(rate) {
|
formatRatePercent(rate) {
|
||||||
const r = parseFloat(rate) || 0;
|
const r = parseFloat(rate) || 0;
|
||||||
if (r <= 1 && r > 0) return `${(r * 100).toFixed(0)}%`;
|
if (r <= 1 && r > 0) return `${(r * 100).toFixed(0)}%`;
|
||||||
return `${r}%`;
|
return `${r}%`;
|
||||||
},
|
},
|
||||||
|
|
||||||
registerNotification() {
|
registerNotification() {
|
||||||
const comp = this.selectComponent('#global-notification');
|
const comp = this.selectComponent('#global-notification');
|
||||||
if (comp?.showNotification) {
|
if (comp?.showNotification) {
|
||||||
app.globalData.globalNotification = {
|
app.globalData.globalNotification = {
|
||||||
show: (data) => comp.showNotification(data),
|
show: (data) => comp.showNotification(data),
|
||||||
hide: () => comp.hideNotification(),
|
hide: () => comp.hideNotification(),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
initImageUrls() {
|
initImageUrls() {
|
||||||
const ossBase = app.globalData.ossImageUrl || '';
|
const ossBase = app.globalData.ossImageUrl || '';
|
||||||
const imgDir = `${ossBase}beijing/tixian/`;
|
const imgDir = `${ossBase}beijing/tixian/`;
|
||||||
this.setData({
|
this.setData({
|
||||||
imgUrls: {
|
imgUrls: {
|
||||||
iconWechat: `${imgDir}icon_wechat.png`,
|
iconWechat: `${imgDir}icon_wechat.png`,
|
||||||
iconAlipay: `${imgDir}icon_alipay.png`,
|
iconAlipay: `${imgDir}icon_alipay.png`,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
/** 顶部展示:不含保证金的可提现合计 */
|
/** 顶部展示:不含保证金的可提现合计 */
|
||||||
calcDisplayTotal(assets) {
|
calcDisplayTotal(assets) {
|
||||||
let total = 0;
|
let total = 0;
|
||||||
(assets || []).forEach((item) => {
|
(assets || []).forEach((item) => {
|
||||||
if (item.type === 'dashou_yajin') return;
|
if (item.type === 'dashou_yajin') return;
|
||||||
total += parseFloat(item.amount) || 0;
|
total += parseFloat(item.amount) || 0;
|
||||||
});
|
});
|
||||||
return total;
|
return total;
|
||||||
},
|
},
|
||||||
|
|
||||||
hasAnyWithdrawable(assets) {
|
hasAnyWithdrawable(assets) {
|
||||||
return (assets || []).some((item) => parseFloat(item.amount) > 0);
|
return (assets || []).some((item) => parseFloat(item.amount) > 0);
|
||||||
},
|
},
|
||||||
|
|
||||||
applyRouteOptions(assets) {
|
applyRouteOptions(assets) {
|
||||||
const opts = this.properties.options || {};
|
const opts = this.properties.options || {};
|
||||||
const fromKey = FROM_ASSET_MAP[opts.from];
|
const fromKey = FROM_ASSET_MAP[opts.from];
|
||||||
let selected = null;
|
let selected = null;
|
||||||
if (fromKey) {
|
if (fromKey) {
|
||||||
selected = assets.find((a) => a.type === fromKey) || null;
|
selected = assets.find((a) => a.type === fromKey) || null;
|
||||||
} else if (assets.length === 1) {
|
} else if (assets.length === 1) {
|
||||||
selected = assets[0];
|
selected = assets[0];
|
||||||
}
|
}
|
||||||
const patch = {};
|
const patch = {};
|
||||||
if (selected) {
|
if (selected) {
|
||||||
patch.selectedAsset = selected;
|
patch.selectedAsset = selected;
|
||||||
patch.feeRateText = selected.rateText;
|
patch.feeRateText = selected.rateText;
|
||||||
}
|
}
|
||||||
if (opts.amount && parseFloat(opts.amount) > 0) {
|
if (opts.amount && parseFloat(opts.amount) > 0) {
|
||||||
const amt = parseFloat(opts.amount);
|
const amt = parseFloat(opts.amount);
|
||||||
const max = selected ? parseFloat(selected.amount) : amt;
|
const max = selected ? parseFloat(selected.amount) : amt;
|
||||||
patch.tixianAmount = Math.min(amt, max).toFixed(2);
|
patch.tixianAmount = Math.min(amt, max).toFixed(2);
|
||||||
}
|
}
|
||||||
if (Object.keys(patch).length) {
|
if (Object.keys(patch).length) {
|
||||||
this.setData(patch, () => {
|
this.setData(patch, () => {
|
||||||
this.recalcFee(this.data.tixianAmount, this.data.selectedAsset);
|
this.recalcFee(this.data.tixianAmount, this.data.selectedAsset);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
onSelectAsset(e) {
|
onSelectAsset(e) {
|
||||||
const index = e.currentTarget.dataset.index;
|
const index = e.currentTarget.dataset.index;
|
||||||
const asset = this.data.displayAssetList[index];
|
const asset = this.data.displayAssetList[index];
|
||||||
if (!asset || parseFloat(asset.amount) <= 0) {
|
if (!asset || parseFloat(asset.amount) <= 0) {
|
||||||
wx.showToast({ title: '该账户无可提余额', icon: 'none' });
|
wx.showToast({ title: '该账户无可提余额', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
let amount = this.data.tixianAmount;
|
let amount = this.data.tixianAmount;
|
||||||
const max = parseFloat(asset.amount);
|
const max = parseFloat(asset.amount);
|
||||||
if (amount && parseFloat(amount) > max) {
|
if (amount && parseFloat(amount) > max) {
|
||||||
amount = asset.amount;
|
amount = asset.amount;
|
||||||
}
|
}
|
||||||
this.setData({ selectedAsset: asset, tixianAmount: amount });
|
this.setData({ selectedAsset: asset, tixianAmount: amount });
|
||||||
this.recalcFee(amount, asset);
|
this.recalcFee(amount, asset);
|
||||||
},
|
},
|
||||||
|
|
||||||
async loadAllAssets() {
|
async loadAllAssets() {
|
||||||
this.setData({ isLoadingAssets: true, totalAmount: '0.00', canWithdraw: false, assetList: [] });
|
this.setData({ isLoadingAssets: true, totalAmount: '0.00', canWithdraw: false, assetList: [] });
|
||||||
try {
|
try {
|
||||||
const res = await request({ url: '/yonghu/tixianzichan', method: 'POST' });
|
const res = await request({ url: '/yonghu/tixianzichan', method: 'POST' });
|
||||||
if (res?.data?.code === 200 || res?.data?.code === 0) {
|
if (res?.data?.code === 200 || res?.data?.code === 0) {
|
||||||
const data = res.data.data || {};
|
const data = res.data.data || {};
|
||||||
const assets = [];
|
const assets = [];
|
||||||
const push = (type, amount, rate) => {
|
const push = (type, amount, rate) => {
|
||||||
const cfg = ASSET_TYPES[type];
|
const cfg = ASSET_TYPES[type];
|
||||||
if (!cfg || !amount || parseFloat(amount) <= 0) return;
|
if (!cfg || !amount || parseFloat(amount) <= 0) return;
|
||||||
assets.push({
|
assets.push({
|
||||||
type,
|
type,
|
||||||
leixing: cfg.leixing,
|
leixing: cfg.leixing,
|
||||||
label: cfg.label,
|
label: cfg.label,
|
||||||
amount: parseFloat(amount).toFixed(2),
|
amount: parseFloat(amount).toFixed(2),
|
||||||
rate: rate || 0,
|
rate: rate || 0,
|
||||||
rateText: this.formatRatePercent(rate || 0),
|
rateText: this.formatRatePercent(rate || 0),
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
push('dashou_yue', data.dashou_yue, data.dashou_rate);
|
push('dashou_yue', data.dashou_yue, data.dashou_rate);
|
||||||
push('dashou_yajin', data.dashou_yajin, data.dashou_yajin_rate);
|
push('dashou_yajin', data.dashou_yajin, data.dashou_yajin_rate);
|
||||||
push('shangjia_yue', data.shangjia_yue, data.shangjia_rate);
|
push('shangjia_yue', data.shangjia_yue, data.shangjia_rate);
|
||||||
push('guanshi_fenyong', data.guanshi_fenyong, data.guanshi_rate);
|
push('guanshi_fenyong', data.guanshi_fenyong, data.guanshi_rate);
|
||||||
push('zuzhang_fenyong', data.zuzhang_fenyong, data.zuzhang_rate);
|
push('zuzhang_fenyong', data.zuzhang_fenyong, data.zuzhang_rate);
|
||||||
push('kaoheguan_fenyong', data.kaoheguan_fenyong, data.kaoheguan_rate);
|
push('kaoheguan_fenyong', data.kaoheguan_fenyong, data.kaoheguan_rate);
|
||||||
|
|
||||||
const displayTotal = this.calcDisplayTotal(assets);
|
const displayTotal = this.calcDisplayTotal(assets);
|
||||||
const firstRate = assets.find((a) => a.type !== 'dashou_yajin')?.rate || 0;
|
const firstRate = assets.find((a) => a.type !== 'dashou_yajin')?.rate || 0;
|
||||||
this.setData({
|
this.setData({
|
||||||
assetList: assets,
|
assetList: assets,
|
||||||
displayAssetList: assets,
|
displayAssetList: assets,
|
||||||
totalAmount: displayTotal.toFixed(2),
|
totalAmount: displayTotal.toFixed(2),
|
||||||
canWithdraw: this.hasAnyWithdrawable(assets),
|
canWithdraw: this.hasAnyWithdrawable(assets),
|
||||||
isLoadingAssets: false,
|
isLoadingAssets: false,
|
||||||
feeRateText: displayTotal > 0 ? this.formatRatePercent(firstRate) : '--',
|
feeRateText: displayTotal > 0 ? this.formatRatePercent(firstRate) : '--',
|
||||||
}, () => this.applyRouteOptions(assets));
|
}, () => this.applyRouteOptions(assets));
|
||||||
if (!this.data.selectedAsset) {
|
if (!this.data.selectedAsset) {
|
||||||
this.recalcFee(this.data.tixianAmount, null);
|
this.recalcFee(this.data.tixianAmount, null);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
throw new Error(res?.data?.msg || '获取资产失败');
|
throw new Error(res?.data?.msg || '获取资产失败');
|
||||||
}
|
}
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
console.error('loadAllAssets', err);
|
console.error('loadAllAssets', err);
|
||||||
this.setData({ isLoadingAssets: false, totalAmount: '0.00', canWithdraw: false, assetList: [] });
|
this.setData({ isLoadingAssets: false, totalAmount: '0.00', canWithdraw: false, assetList: [] });
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
async loadWithdrawMethod() {
|
async loadWithdrawMethod() {
|
||||||
const txzh = wx.getStorageSync('txzh') || '';
|
const txzh = wx.getStorageSync('txzh') || '';
|
||||||
const txtupian = wx.getStorageSync('txtupian') || '';
|
const txtupian = wx.getStorageSync('txtupian') || '';
|
||||||
const txfangshi = wx.getStorageSync('txfangshi') || null;
|
const txfangshi = wx.getStorageSync('txfangshi') || null;
|
||||||
const txdianhua = wx.getStorageSync('txdianhua') || '';
|
const txdianhua = wx.getStorageSync('txdianhua') || '';
|
||||||
if (txzh || txtupian || txfangshi) {
|
if (txzh || txtupian || txfangshi) {
|
||||||
this.setData({ txzh, txtupian, txfangshi, txdianhua });
|
this.setData({ txzh, txtupian, txfangshi, txdianhua });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
const res = await request({ url: '/yonghu/tixianhq', method: 'POST' });
|
const res = await request({ url: '/yonghu/tixianhq', method: 'POST' });
|
||||||
if (res?.data?.code === 0) {
|
if (res?.data?.code === 0) {
|
||||||
const data = res.data.data;
|
const data = res.data.data;
|
||||||
this.setData({
|
this.setData({
|
||||||
txzh: data.txzh || '',
|
txzh: data.txzh || '',
|
||||||
txtupian: data.txtupian || '',
|
txtupian: data.txtupian || '',
|
||||||
txfangshi: data.txfangshi || null,
|
txfangshi: data.txfangshi || null,
|
||||||
txdianhua: data.txdianhua || '',
|
txdianhua: data.txdianhua || '',
|
||||||
});
|
});
|
||||||
wx.setStorageSync('txzh', data.txzh || '');
|
wx.setStorageSync('txzh', data.txzh || '');
|
||||||
wx.setStorageSync('txtupian', data.txtupian || '');
|
wx.setStorageSync('txtupian', data.txtupian || '');
|
||||||
wx.setStorageSync('txfangshi', data.txfangshi || null);
|
wx.setStorageSync('txfangshi', data.txfangshi || null);
|
||||||
wx.setStorageSync('txdianhua', data.txdianhua || '');
|
wx.setStorageSync('txdianhua', data.txdianhua || '');
|
||||||
}
|
}
|
||||||
} catch (err) { /* ignore */ }
|
} catch (err) { /* ignore */ }
|
||||||
},
|
},
|
||||||
|
|
||||||
recalcFee(amountStr, asset) {
|
recalcFee(amountStr, asset) {
|
||||||
const amount = parseFloat(amountStr);
|
const amount = parseFloat(amountStr);
|
||||||
if (!amountStr || isNaN(amount) || amount <= 0 || !asset) {
|
if (!amountStr || isNaN(amount) || amount <= 0 || !asset) {
|
||||||
this.setData({
|
this.setData({
|
||||||
shouxufei: '0.00',
|
shouxufei: '0.00',
|
||||||
shijidaozhang: '0.00',
|
shijidaozhang: '0.00',
|
||||||
feeRateText: asset ? asset.rateText : this.data.feeRateText,
|
feeRateText: asset ? asset.rateText : this.data.feeRateText,
|
||||||
});
|
});
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const rate = parseFloat(asset.rate) || 0;
|
const rate = parseFloat(asset.rate) || 0;
|
||||||
const fee = amount * rate;
|
const fee = amount * rate;
|
||||||
this.setData({
|
this.setData({
|
||||||
shouxufei: fee.toFixed(2),
|
shouxufei: fee.toFixed(2),
|
||||||
shijidaozhang: (amount - fee).toFixed(2),
|
shijidaozhang: (amount - fee).toFixed(2),
|
||||||
feeRateText: asset.rateText,
|
feeRateText: asset.rateText,
|
||||||
currentRate: asset.rateText,
|
currentRate: asset.rateText,
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
onAmountInput(e) {
|
onAmountInput(e) {
|
||||||
let val = e.detail.value;
|
let val = e.detail.value;
|
||||||
if (val && !/^\d*\.?\d{0,2}$/.test(val)) return;
|
if (val && !/^\d*\.?\d{0,2}$/.test(val)) return;
|
||||||
this.setData({ tixianAmount: val });
|
this.setData({ tixianAmount: val });
|
||||||
this.recalcFee(val, this.data.selectedAsset);
|
this.recalcFee(val, this.data.selectedAsset);
|
||||||
},
|
},
|
||||||
|
|
||||||
onWithdrawAll() {
|
onWithdrawAll() {
|
||||||
const { selectedAsset } = this.data;
|
const { selectedAsset } = this.data;
|
||||||
if (!selectedAsset) {
|
if (!selectedAsset) {
|
||||||
wx.showToast({ title: '请先选择提现账户', icon: 'none' });
|
wx.showToast({ title: '请先选择提现账户', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const max = selectedAsset.amount;
|
const max = selectedAsset.amount;
|
||||||
this.setData({ tixianAmount: max });
|
this.setData({ tixianAmount: max });
|
||||||
this.recalcFee(max, selectedAsset);
|
this.recalcFee(max, selectedAsset);
|
||||||
},
|
},
|
||||||
|
|
||||||
onTapWithdraw() {
|
onTapWithdraw() {
|
||||||
if (this.data.submitting) return;
|
if (this.data.submitting) return;
|
||||||
if (!this.hasAnyWithdrawable(this.data.assetList)) {
|
if (!this.hasAnyWithdrawable(this.data.assetList)) {
|
||||||
wx.showToast({ title: '暂无可提现余额', icon: 'none' });
|
wx.showToast({ title: '暂无可提现余额', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const { selectedAsset, tixianAmount } = this.data;
|
const { selectedAsset, tixianAmount } = this.data;
|
||||||
if (!selectedAsset) {
|
if (!selectedAsset) {
|
||||||
wx.showToast({ title: '请先选择要提现的账户', icon: 'none' });
|
wx.showToast({ title: '请先选择要提现的账户', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const amount = parseFloat(tixianAmount);
|
const amount = parseFloat(tixianAmount);
|
||||||
if (isNaN(amount) || amount <= 0) {
|
if (isNaN(amount) || amount <= 0) {
|
||||||
wx.showToast({ title: '请输入有效金额', icon: 'none' });
|
wx.showToast({ title: '请输入有效金额', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (amount > parseFloat(selectedAsset.amount)) {
|
if (amount > parseFloat(selectedAsset.amount)) {
|
||||||
wx.showToast({ title: `超过${selectedAsset.label}可提余额`, icon: 'none' });
|
wx.showToast({ title: `超过${selectedAsset.label}可提余额`, icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const { txfangshi, txzh, txtupian } = this.data;
|
const { txfangshi, txzh, txtupian } = this.data;
|
||||||
if (!txfangshi || (!txzh && !txtupian)) {
|
if (!txfangshi || (!txzh && !txtupian)) {
|
||||||
wx.showToast({ title: '请先设置收款方式', icon: 'none' });
|
wx.showToast({ title: '请先设置收款方式', icon: 'none' });
|
||||||
this.onSetSkfs();
|
this.onSetSkfs();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
this.applyIdentityAndConfirm(selectedAsset);
|
this.applyIdentityAndConfirm(selectedAsset);
|
||||||
},
|
},
|
||||||
|
|
||||||
applyIdentityAndConfirm(asset) {
|
applyIdentityAndConfirm(asset) {
|
||||||
this.recalcFee(this.data.tixianAmount, asset);
|
this.recalcFee(this.data.tixianAmount, asset);
|
||||||
this.setData({ selectedAsset: asset, showTixianModal: true });
|
this.setData({ selectedAsset: asset, showTixianModal: true });
|
||||||
},
|
},
|
||||||
|
|
||||||
async onConfirmWithdraw() {
|
async onConfirmWithdraw() {
|
||||||
const { selectedAsset, tixianAmount, txfangshi, txzh, txtupian } = this.data;
|
const { selectedAsset, tixianAmount, txfangshi, txzh, txtupian } = this.data;
|
||||||
if (!selectedAsset) {
|
if (!selectedAsset) {
|
||||||
wx.showToast({ title: '请选择提现身份', icon: 'none' });
|
wx.showToast({ title: '请选择提现身份', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const amount = parseFloat(tixianAmount);
|
const amount = parseFloat(tixianAmount);
|
||||||
if (isNaN(amount) || amount <= 0) {
|
if (isNaN(amount) || amount <= 0) {
|
||||||
wx.showToast({ title: '请输入有效金额', icon: 'none' });
|
wx.showToast({ title: '请输入有效金额', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (amount > parseFloat(selectedAsset.amount)) {
|
if (amount > parseFloat(selectedAsset.amount)) {
|
||||||
wx.showToast({ title: '超过可提余额', icon: 'none' });
|
wx.showToast({ title: '超过可提余额', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const leixing = selectedAsset.leixing;
|
const leixing = selectedAsset.leixing;
|
||||||
let txskfs = 0;
|
let txskfs = 0;
|
||||||
if (txzh && txtupian) txskfs = 3;
|
if (txzh && txtupian) txskfs = 3;
|
||||||
else if (txzh) txskfs = 1;
|
else if (txzh) txskfs = 1;
|
||||||
else if (txtupian) txskfs = 2;
|
else if (txtupian) txskfs = 2;
|
||||||
|
|
||||||
this.setData({ submitting: true });
|
this.setData({ submitting: true });
|
||||||
try {
|
try {
|
||||||
const res = await request({
|
const res = await request({
|
||||||
url: '/yonghu/tixian',
|
url: '/yonghu/tixian',
|
||||||
method: 'POST',
|
method: 'POST',
|
||||||
data: { leixing, jine: amount.toFixed(2), fangshi: txfangshi, txskfs },
|
data: { leixing, jine: amount.toFixed(2), fangshi: txfangshi, txskfs },
|
||||||
});
|
});
|
||||||
if (res?.data?.code === 0) {
|
if (res?.data?.code === 0) {
|
||||||
this.setData({
|
this.setData({
|
||||||
showTixianModal: false,
|
showTixianModal: false,
|
||||||
selectedAsset: null,
|
selectedAsset: null,
|
||||||
tixianAmount: '',
|
tixianAmount: '',
|
||||||
submitting: false,
|
submitting: false,
|
||||||
});
|
});
|
||||||
await this.loadAllAssets();
|
await this.loadAllAssets();
|
||||||
wx.showModal({
|
wx.showModal({
|
||||||
title: '申请成功',
|
title: '申请成功',
|
||||||
content: '提现申请已提交,请前往「提现记录」查看审核进度。',
|
content: '提现申请已提交,请前往「提现记录」查看审核进度。',
|
||||||
confirmText: '查看提现记录',
|
confirmText: '查看提现记录',
|
||||||
cancelText: '知道了',
|
cancelText: '知道了',
|
||||||
success: (res) => {
|
success: (res) => {
|
||||||
if (res.confirm) {
|
if (res.confirm) {
|
||||||
wx.navigateTo({ url: '/pages/withdraw/withdraw-records' });
|
wx.navigateTo({ url: '/pages/withdraw/withdraw-records' });
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
wx.showToast({ title: res?.data?.msg || '提现失败', icon: 'none' });
|
wx.showToast({ title: res?.data?.msg || '提现失败', icon: 'none' });
|
||||||
this.setData({ submitting: false });
|
this.setData({ submitting: false });
|
||||||
}
|
}
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
wx.showToast({ title: '网络错误', icon: 'none' });
|
wx.showToast({ title: '网络错误', icon: 'none' });
|
||||||
this.setData({ submitting: false });
|
this.setData({ submitting: false });
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
onCloseTixianModal() {
|
onCloseTixianModal() {
|
||||||
if (this.data.submitting) return;
|
if (this.data.submitting) return;
|
||||||
this.setData({ showTixianModal: false, selectedAsset: null });
|
this.setData({ showTixianModal: false, selectedAsset: null });
|
||||||
},
|
},
|
||||||
|
|
||||||
onSetSkfs() {
|
onSetSkfs() {
|
||||||
this.setData({
|
this.setData({
|
||||||
showSkfsModal: true,
|
showSkfsModal: true,
|
||||||
tempTxfangshi: this.data.txfangshi,
|
tempTxfangshi: this.data.txfangshi,
|
||||||
tempTxPhone: this.data.txdianhua,
|
tempTxPhone: this.data.txdianhua,
|
||||||
tempTxAccount: this.data.txzh,
|
tempTxAccount: this.data.txzh,
|
||||||
tempTxImage: '',
|
tempTxImage: '',
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
onSelectFangshi(e) { this.setData({ tempTxfangshi: e.currentTarget.dataset.fangshi }); },
|
onSelectFangshi(e) { this.setData({ tempTxfangshi: e.currentTarget.dataset.fangshi }); },
|
||||||
onPhoneInput(e) { this.setData({ tempTxPhone: e.detail.value }); },
|
onPhoneInput(e) { this.setData({ tempTxPhone: e.detail.value }); },
|
||||||
onAccountInput(e) { this.setData({ tempTxAccount: e.detail.value }); },
|
onAccountInput(e) { this.setData({ tempTxAccount: e.detail.value }); },
|
||||||
|
|
||||||
onChooseImage() {
|
onChooseImage() {
|
||||||
if (this.data.choosingImage) return;
|
if (this.data.choosingImage) return;
|
||||||
this.setData({ choosingImage: true });
|
this.setData({ choosingImage: true });
|
||||||
wx.chooseMedia({
|
wx.chooseMedia({
|
||||||
count: 1,
|
count: 1,
|
||||||
mediaType: ['image'],
|
mediaType: ['image'],
|
||||||
success: (res) => { this.setData({ tempTxImage: res.tempFiles[0].tempFilePath }); },
|
success: (res) => { this.setData({ tempTxImage: res.tempFiles[0].tempFilePath }); },
|
||||||
complete: () => { this.setData({ choosingImage: false }); },
|
complete: () => { this.setData({ choosingImage: false }); },
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
onPreviewImage() {
|
onPreviewImage() {
|
||||||
if (this.data.tempTxImage) wx.previewImage({ urls: [this.data.tempTxImage] });
|
if (this.data.tempTxImage) wx.previewImage({ urls: [this.data.tempTxImage] });
|
||||||
},
|
},
|
||||||
|
|
||||||
onDeleteImage() { this.setData({ tempTxImage: '' }); },
|
onDeleteImage() { this.setData({ tempTxImage: '' }); },
|
||||||
|
|
||||||
async onConfirmSkfs() {
|
async onConfirmSkfs() {
|
||||||
const { tempTxfangshi, tempTxPhone, tempTxAccount, tempTxImage } = this.data;
|
const { tempTxfangshi, tempTxPhone, tempTxAccount, tempTxImage } = this.data;
|
||||||
if (!tempTxfangshi) { wx.showToast({ title: '请选择提现方式', icon: 'none' }); return; }
|
if (!tempTxfangshi) { wx.showToast({ title: '请选择提现方式', icon: 'none' }); return; }
|
||||||
if (!tempTxPhone) { wx.showToast({ title: '请输入收款人电话', icon: 'none' }); return; }
|
if (!tempTxPhone) { wx.showToast({ title: '请输入收款人电话', icon: 'none' }); return; }
|
||||||
if (tempTxfangshi == 1 && !tempTxImage && !this.data.txtupian) {
|
if (tempTxfangshi == 1 && !tempTxImage && !this.data.txtupian) {
|
||||||
wx.showToast({ title: '请上传微信收款码', icon: 'none' }); return;
|
wx.showToast({ title: '请上传微信收款码', icon: 'none' }); return;
|
||||||
}
|
}
|
||||||
if (tempTxfangshi == 2 && !tempTxAccount && !tempTxImage && !this.data.txzh) {
|
if (tempTxfangshi == 2 && !tempTxAccount && !tempTxImage && !this.data.txzh) {
|
||||||
wx.showToast({ title: '请填写支付宝账号或上传收款码', icon: 'none' }); return;
|
wx.showToast({ title: '请填写支付宝账号或上传收款码', icon: 'none' }); return;
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
const res = await upload({
|
const res = await upload({
|
||||||
url: '/yonghu/sksc',
|
url: '/yonghu/sksc',
|
||||||
formData: { txdianhua: tempTxPhone, txzh: tempTxAccount || '' },
|
formData: { txdianhua: tempTxPhone, txzh: tempTxAccount || '' },
|
||||||
filePath: tempTxImage || null,
|
filePath: tempTxImage || null,
|
||||||
fileName: 'file',
|
fileName: 'file',
|
||||||
});
|
});
|
||||||
if (res?.data?.code === 0) {
|
if (res?.data?.code === 0) {
|
||||||
const data = res.data.data;
|
const data = res.data.data;
|
||||||
this.setData({
|
this.setData({
|
||||||
txfangshi: tempTxfangshi,
|
txfangshi: tempTxfangshi,
|
||||||
txdianhua: tempTxPhone,
|
txdianhua: tempTxPhone,
|
||||||
txzh: data.txzh || '',
|
txzh: data.txzh || '',
|
||||||
txtupian: data.txtupian || this.data.txtupian,
|
txtupian: data.txtupian || this.data.txtupian,
|
||||||
showSkfsModal: false,
|
showSkfsModal: false,
|
||||||
});
|
});
|
||||||
wx.setStorageSync('txfangshi', tempTxfangshi);
|
wx.setStorageSync('txfangshi', tempTxfangshi);
|
||||||
wx.setStorageSync('txdianhua', tempTxPhone);
|
wx.setStorageSync('txdianhua', tempTxPhone);
|
||||||
wx.setStorageSync('txzh', data.txzh || '');
|
wx.setStorageSync('txzh', data.txzh || '');
|
||||||
wx.setStorageSync('txtupian', data.txtupian || this.data.txtupian);
|
wx.setStorageSync('txtupian', data.txtupian || this.data.txtupian);
|
||||||
wx.showToast({ title: '设置成功', icon: 'success' });
|
wx.showToast({ title: '设置成功', icon: 'success' });
|
||||||
} else {
|
} else {
|
||||||
wx.showToast({ title: res?.data?.msg || '保存失败', icon: 'none' });
|
wx.showToast({ title: res?.data?.msg || '保存失败', icon: 'none' });
|
||||||
}
|
}
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
wx.showToast({ title: '网络错误', icon: 'none' });
|
wx.showToast({ title: '网络错误', icon: 'none' });
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
onCloseSkfsModal() { this.setData({ showSkfsModal: false }); },
|
onCloseSkfsModal() { this.setData({ showSkfsModal: false }); },
|
||||||
stopPropagation() {},
|
stopPropagation() {},
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,115 +1,115 @@
|
|||||||
<!-- mode1 收款码手动审核 - 参考逍遥梦样式 -->
|
<!-- mode1 收款码手动审核 - 参考逍遥梦样式 -->
|
||||||
<view class="ref-page">
|
<view class="ref-page">
|
||||||
<view class="method-card method-card--row">
|
<view class="method-card method-card--row">
|
||||||
<view class="method-tab method-tab--active">
|
<view class="method-tab method-tab--active">
|
||||||
<image wx:if="{{txfangshi == 1}}" class="method-tab-icon" src="{{imgUrls.iconWechat}}" mode="aspectFit" />
|
<image wx:if="{{txfangshi == 1}}" class="method-tab-icon" src="{{imgUrls.iconWechat}}" mode="aspectFit" />
|
||||||
<image wx:elif="{{txfangshi == 2}}" class="method-tab-icon" src="{{imgUrls.iconAlipay}}" mode="aspectFit" />
|
<image wx:elif="{{txfangshi == 2}}" class="method-tab-icon" src="{{imgUrls.iconAlipay}}" mode="aspectFit" />
|
||||||
<view wx:else class="method-tab-icon method-tab-icon--placeholder"></view>
|
<view wx:else class="method-tab-icon method-tab-icon--placeholder"></view>
|
||||||
<text class="method-tab-text">{{txfangshi == 1 ? '微信零钱' : (txfangshi == 2 ? '收款码' : '请先设置收款')}}</text>
|
<text class="method-tab-text">{{txfangshi == 1 ? '微信零钱' : (txfangshi == 2 ? '收款码' : '请先设置收款')}}</text>
|
||||||
<view class="method-tab-line"></view>
|
<view class="method-tab-line"></view>
|
||||||
</view>
|
</view>
|
||||||
<text class="method-setting" bindtap="onSetSkfs">设置收款方式</text>
|
<text class="method-setting" bindtap="onSetSkfs">设置收款方式</text>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
<view class="account-card" wx:if="{{displayAssetList.length > 0}}">
|
<view class="account-card" wx:if="{{displayAssetList.length > 0}}">
|
||||||
<scroll-view scroll-x enable-flex class="account-scroll" show-scrollbar="{{false}}">
|
<scroll-view scroll-x enable-flex class="account-scroll" show-scrollbar="{{false}}">
|
||||||
<view
|
<view
|
||||||
wx:for="{{displayAssetList}}"
|
wx:for="{{displayAssetList}}"
|
||||||
wx:key="type"
|
wx:key="type"
|
||||||
class="account-chip {{selectedAsset.type === item.type ? 'account-chip--active' : ''}} {{item.amount <= 0 ? 'account-chip--disabled' : ''}}"
|
class="account-chip {{selectedAsset.type === item.type ? 'account-chip--active' : ''}} {{item.amount <= 0 ? 'account-chip--disabled' : ''}}"
|
||||||
bindtap="onSelectAsset"
|
bindtap="onSelectAsset"
|
||||||
data-index="{{index}}"
|
data-index="{{index}}"
|
||||||
>
|
>
|
||||||
<text class="chip-label">{{item.label}}</text>
|
<text class="chip-label">{{item.label}}</text>
|
||||||
<text class="chip-amount">¥{{item.amount}}</text>
|
<text class="chip-amount">¥{{item.amount}}</text>
|
||||||
</view>
|
</view>
|
||||||
</scroll-view>
|
</scroll-view>
|
||||||
<text wx:if="{{!selectedAsset}}" class="account-warn">请先选择上方提现账户</text>
|
<text wx:if="{{!selectedAsset}}" class="account-warn">请先选择上方提现账户</text>
|
||||||
<text wx:else class="account-ok">当前:{{selectedAsset.label}}</text>
|
<text wx:else class="account-ok">当前:{{selectedAsset.label}}</text>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
<view class="amount-card">
|
<view class="amount-card">
|
||||||
<view class="avail-row">
|
<view class="avail-row">
|
||||||
<text class="avail-label">当前可提现:</text>
|
<text class="avail-label">当前可提现:</text>
|
||||||
<text class="avail-symbol">¥</text>
|
<text class="avail-symbol">¥</text>
|
||||||
<text class="avail-amount">{{selectedAsset ? selectedAsset.amount : totalAmount}}</text>
|
<text class="avail-amount">{{selectedAsset ? selectedAsset.amount : totalAmount}}</text>
|
||||||
</view>
|
</view>
|
||||||
<view class="input-row">
|
<view class="input-row">
|
||||||
<text class="input-symbol">¥</text>
|
<text class="input-symbol">¥</text>
|
||||||
<input
|
<input
|
||||||
class="amount-input"
|
class="amount-input"
|
||||||
type="digit"
|
type="digit"
|
||||||
placeholder="请输入金额"
|
placeholder="请输入金额"
|
||||||
placeholder-class="amount-placeholder"
|
placeholder-class="amount-placeholder"
|
||||||
value="{{tixianAmount}}"
|
value="{{tixianAmount}}"
|
||||||
bindinput="onAmountInput"
|
bindinput="onAmountInput"
|
||||||
/>
|
/>
|
||||||
<text class="withdraw-all" bindtap="onWithdrawAll">全部提现</text>
|
<text class="withdraw-all" bindtap="onWithdrawAll">全部提现</text>
|
||||||
</view>
|
</view>
|
||||||
<view class="input-divider"></view>
|
<view class="input-divider"></view>
|
||||||
<view class="fee-tip">
|
<view class="fee-tip">
|
||||||
<text>提示:提现手续费</text>
|
<text>提示:提现手续费</text>
|
||||||
<text class="fee-highlight">{{feeRateText}}</text>
|
<text class="fee-highlight">{{feeRateText}}</text>
|
||||||
<text>。</text>
|
<text>。</text>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
<view class="submit-wrap">
|
<view class="submit-wrap">
|
||||||
<view class="confirm-btn {{canWithdraw && !submitting ? '' : 'confirm-btn--disabled'}}" bindtap="onTapWithdraw">
|
<view class="confirm-btn {{canWithdraw && !submitting ? '' : 'confirm-btn--disabled'}}" bindtap="onTapWithdraw">
|
||||||
<text wx:if="{{submitting}}">处理中...</text>
|
<text wx:if="{{submitting}}">处理中...</text>
|
||||||
<text wx:else>确认提现</text>
|
<text wx:else>确认提现</text>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
<view class="notice-box">
|
<view class="notice-box">
|
||||||
<view class="notice-title">📢 提现须知</view>
|
<view class="notice-title">📢 提现须知</view>
|
||||||
<view class="notice-item">🕒 提交后将进入人工审核,请耐心等待</view>
|
<view class="notice-item">🕒 提交后将进入人工审核,请耐心等待</view>
|
||||||
<view class="notice-item">📌 审核结果可在「提现记录」中查看</view>
|
<view class="notice-item">📌 审核结果可在「提现记录」中查看</view>
|
||||||
<view class="notice-item">💰 每笔只能从单个账户提现,请先选择对应账户</view>
|
<view class="notice-item">💰 每笔只能从单个账户提现,请先选择对应账户</view>
|
||||||
<view class="notice-item">✅ 请确保收款方式与收款码正确后再提交</view>
|
<view class="notice-item">✅ 请确保收款方式与收款码正确后再提交</view>
|
||||||
<view class="notice-item">🎧 如有疑问请联系客服核实处理</view>
|
<view class="notice-item">🎧 如有疑问请联系客服核实处理</view>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
<view wx:if="{{showTixianModal}}" class="modal-mask" bindtap="onCloseTixianModal">
|
<view wx:if="{{showTixianModal}}" class="modal-mask" bindtap="onCloseTixianModal">
|
||||||
<view class="modal-dialog" catchtap="stopPropagation">
|
<view class="modal-dialog" catchtap="stopPropagation">
|
||||||
<view class="modal-header">确认提现</view>
|
<view class="modal-header">确认提现</view>
|
||||||
<view class="modal-body">
|
<view class="modal-body">
|
||||||
<view class="info-row"><text>身份</text><text>{{selectedAsset.label}}</text></view>
|
<view class="info-row"><text>身份</text><text>{{selectedAsset.label}}</text></view>
|
||||||
<view class="info-row"><text>可提</text><text>¥{{selectedAsset.amount}}</text></view>
|
<view class="info-row"><text>可提</text><text>¥{{selectedAsset.amount}}</text></view>
|
||||||
<view class="info-row"><text>费率</text><text>{{currentRate}}</text></view>
|
<view class="info-row"><text>费率</text><text>{{currentRate}}</text></view>
|
||||||
<view class="info-row"><text>提现金额</text><text>¥{{tixianAmount}}</text></view>
|
<view class="info-row"><text>提现金额</text><text>¥{{tixianAmount}}</text></view>
|
||||||
<view class="fee-row"><text>手续费 ¥{{shouxufei}}</text><text>到账 ¥{{shijidaozhang}}</text></view>
|
<view class="fee-row"><text>手续费 ¥{{shouxufei}}</text><text>到账 ¥{{shijidaozhang}}</text></view>
|
||||||
<view class="info-row"><text>收款</text><text>{{txfangshi == 1 ? '微信' : (txfangshi == 2 ? '支付宝' : '未设置')}}</text></view>
|
<view class="info-row"><text>收款</text><text>{{txfangshi == 1 ? '微信' : (txfangshi == 2 ? '支付宝' : '未设置')}}</text></view>
|
||||||
</view>
|
</view>
|
||||||
<view class="modal-footer">
|
<view class="modal-footer">
|
||||||
<view class="modal-btn cancel" bindtap="onCloseTixianModal">取消</view>
|
<view class="modal-btn cancel" bindtap="onCloseTixianModal">取消</view>
|
||||||
<view class="modal-btn confirm" bindtap="onConfirmWithdraw">{{submitting ? '处理中' : '提交申请'}}</view>
|
<view class="modal-btn confirm" bindtap="onConfirmWithdraw">{{submitting ? '处理中' : '提交申请'}}</view>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
<view wx:if="{{showSkfsModal}}" class="modal-mask" bindtap="onCloseSkfsModal">
|
<view wx:if="{{showSkfsModal}}" class="modal-mask" bindtap="onCloseSkfsModal">
|
||||||
<view class="modal-dialog" catchtap="stopPropagation">
|
<view class="modal-dialog" catchtap="stopPropagation">
|
||||||
<view class="modal-header">收款方式</view>
|
<view class="modal-header">收款方式</view>
|
||||||
<view class="modal-body skfs-body">
|
<view class="modal-body skfs-body">
|
||||||
<view class="toggle-row">
|
<view class="toggle-row">
|
||||||
<view class="toggle-item {{tempTxfangshi == 1 ? 'active' : ''}}" bindtap="onSelectFangshi" data-fangshi="1">微信</view>
|
<view class="toggle-item {{tempTxfangshi == 1 ? 'active' : ''}}" bindtap="onSelectFangshi" data-fangshi="1">微信</view>
|
||||||
<view class="toggle-item {{tempTxfangshi == 2 ? 'active' : ''}}" bindtap="onSelectFangshi" data-fangshi="2">支付宝</view>
|
<view class="toggle-item {{tempTxfangshi == 2 ? 'active' : ''}}" bindtap="onSelectFangshi" data-fangshi="2">支付宝</view>
|
||||||
</view>
|
</view>
|
||||||
<input class="field-input" placeholder="手机号" value="{{tempTxPhone}}" bindinput="onPhoneInput" />
|
<input class="field-input" placeholder="手机号" value="{{tempTxPhone}}" bindinput="onPhoneInput" />
|
||||||
<view wx:if="{{tempTxfangshi == 2}}"><input class="field-input" placeholder="支付宝账号" value="{{tempTxAccount}}" bindinput="onAccountInput" /></view>
|
<view wx:if="{{tempTxfangshi == 2}}"><input class="field-input" placeholder="支付宝账号" value="{{tempTxAccount}}" bindinput="onAccountInput" /></view>
|
||||||
<view class="upload-wrap">
|
<view class="upload-wrap">
|
||||||
<view wx:if="{{!tempTxImage}}" class="upload-trigger" bindtap="onChooseImage">+ 上传收款码</view>
|
<view wx:if="{{!tempTxImage}}" class="upload-trigger" bindtap="onChooseImage">+ 上传收款码</view>
|
||||||
<view wx:else class="image-preview"><image src="{{tempTxImage}}" mode="aspectFill" /><view class="image-actions"><text bindtap="onPreviewImage">预览</text><text bindtap="onDeleteImage">删除</text></view></view>
|
<view wx:else class="image-preview"><image src="{{tempTxImage}}" mode="aspectFill" /><view class="image-actions"><text bindtap="onPreviewImage">预览</text><text bindtap="onDeleteImage">删除</text></view></view>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
<view class="modal-footer">
|
<view class="modal-footer">
|
||||||
<view class="modal-btn cancel" bindtap="onCloseSkfsModal">取消</view>
|
<view class="modal-btn cancel" bindtap="onCloseSkfsModal">取消</view>
|
||||||
<view class="modal-btn confirm" bindtap="onConfirmSkfs">保存</view>
|
<view class="modal-btn confirm" bindtap="onConfirmSkfs">保存</view>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
</view>
|
</view>
|
||||||
|
|
||||||
<global-notification id="global-notification" />
|
<global-notification id="global-notification" />
|
||||||
<popup-notice id="popupNotice" />
|
<popup-notice id="popupNotice" />
|
||||||
|
|||||||
@@ -1,85 +1,85 @@
|
|||||||
@import '../mode2/mode2.wxss';
|
@import '../mode2/mode2.wxss';
|
||||||
|
|
||||||
.method-card--row {
|
.method-card--row {
|
||||||
display: flex;
|
display: flex;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
justify-content: space-between;
|
justify-content: space-between;
|
||||||
padding-right: 24rpx;
|
padding-right: 24rpx;
|
||||||
}
|
}
|
||||||
|
|
||||||
.method-setting {
|
.method-setting {
|
||||||
font-size: 26rpx;
|
font-size: 26rpx;
|
||||||
color: #ff8c00;
|
color: #ff8c00;
|
||||||
flex-shrink: 0;
|
flex-shrink: 0;
|
||||||
padding: 16rpx 8rpx;
|
padding: 16rpx 8rpx;
|
||||||
}
|
}
|
||||||
|
|
||||||
.method-tab-icon--placeholder {
|
.method-tab-icon--placeholder {
|
||||||
background: #e0e0e0;
|
background: #e0e0e0;
|
||||||
border-radius: 8rpx;
|
border-radius: 8rpx;
|
||||||
}
|
}
|
||||||
|
|
||||||
.skfs-body .toggle-row {
|
.skfs-body .toggle-row {
|
||||||
display: flex;
|
display: flex;
|
||||||
gap: 16rpx;
|
gap: 16rpx;
|
||||||
margin-bottom: 24rpx;
|
margin-bottom: 24rpx;
|
||||||
}
|
}
|
||||||
|
|
||||||
.toggle-item {
|
.toggle-item {
|
||||||
flex: 1;
|
flex: 1;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
padding: 20rpx;
|
padding: 20rpx;
|
||||||
border-radius: 12rpx;
|
border-radius: 12rpx;
|
||||||
background: #f5f5f5;
|
background: #f5f5f5;
|
||||||
font-size: 28rpx;
|
font-size: 28rpx;
|
||||||
color: #666;
|
color: #666;
|
||||||
}
|
}
|
||||||
|
|
||||||
.toggle-item.active {
|
.toggle-item.active {
|
||||||
background: #fff8e1;
|
background: #fff8e1;
|
||||||
color: #ff8c00;
|
color: #ff8c00;
|
||||||
font-weight: 600;
|
font-weight: 600;
|
||||||
border: 2rpx solid #FFD54F;
|
border: 2rpx solid #FFD54F;
|
||||||
}
|
}
|
||||||
|
|
||||||
.field-input {
|
.field-input {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
box-sizing: border-box;
|
box-sizing: border-box;
|
||||||
padding: 24rpx;
|
padding: 24rpx;
|
||||||
margin-bottom: 16rpx;
|
margin-bottom: 16rpx;
|
||||||
background: #f8f8f8;
|
background: #f8f8f8;
|
||||||
border-radius: 12rpx;
|
border-radius: 12rpx;
|
||||||
font-size: 28rpx;
|
font-size: 28rpx;
|
||||||
}
|
}
|
||||||
|
|
||||||
.upload-wrap {
|
.upload-wrap {
|
||||||
margin-top: 16rpx;
|
margin-top: 16rpx;
|
||||||
}
|
}
|
||||||
|
|
||||||
.upload-trigger {
|
.upload-trigger {
|
||||||
padding: 48rpx;
|
padding: 48rpx;
|
||||||
text-align: center;
|
text-align: center;
|
||||||
border: 2rpx dashed #ddd;
|
border: 2rpx dashed #ddd;
|
||||||
border-radius: 12rpx;
|
border-radius: 12rpx;
|
||||||
color: #999;
|
color: #999;
|
||||||
font-size: 28rpx;
|
font-size: 28rpx;
|
||||||
}
|
}
|
||||||
|
|
||||||
.image-preview {
|
.image-preview {
|
||||||
position: relative;
|
position: relative;
|
||||||
}
|
}
|
||||||
|
|
||||||
.image-preview image {
|
.image-preview image {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
height: 320rpx;
|
height: 320rpx;
|
||||||
border-radius: 12rpx;
|
border-radius: 12rpx;
|
||||||
}
|
}
|
||||||
|
|
||||||
.image-actions {
|
.image-actions {
|
||||||
display: flex;
|
display: flex;
|
||||||
justify-content: center;
|
justify-content: center;
|
||||||
gap: 32rpx;
|
gap: 32rpx;
|
||||||
margin-top: 16rpx;
|
margin-top: 16rpx;
|
||||||
font-size: 28rpx;
|
font-size: 28rpx;
|
||||||
color: #ff8c00;
|
color: #ff8c00;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,369 +1,369 @@
|
|||||||
// pages/withdraw/components/mode2/mode2.js — 自动打款纯提现
|
// pages/withdraw/components/mode2/mode2.js — 自动打款纯提现
|
||||||
import request from '../../../../utils/request.js';
|
import request from '../../../../utils/request.js';
|
||||||
import PopupService from '../../../../services/popupService.js';
|
import PopupService from '../../../../services/popupService.js';
|
||||||
|
|
||||||
const app = getApp();
|
const app = getApp();
|
||||||
|
|
||||||
const ASSET_CONFIG = {
|
const ASSET_CONFIG = {
|
||||||
dashou_yue: { leixing: 1, label: '接单员佣金' },
|
dashou_yue: { leixing: 1, label: '接单员佣金' },
|
||||||
guanshi_fenyong: { leixing: 2, label: '管事分红' },
|
guanshi_fenyong: { leixing: 2, label: '管事分红' },
|
||||||
zuzhang_fenyong: { leixing: 3, label: '组长分红' },
|
zuzhang_fenyong: { leixing: 3, label: '组长分红' },
|
||||||
kaoheguan_fenyong: { leixing: 4, label: '考核官分佣' },
|
kaoheguan_fenyong: { leixing: 4, label: '考核官分佣' },
|
||||||
dashou_yajin: { leixing: 5, label: '接单员保证金' },
|
dashou_yajin: { leixing: 5, label: '接单员保证金' },
|
||||||
shangjia_yue: { leixing: 6, label: '商家余额' },
|
shangjia_yue: { leixing: 6, label: '商家余额' },
|
||||||
};
|
};
|
||||||
|
|
||||||
/** 页面入参 from 与资产 type 映射 */
|
/** 页面入参 from 与资产 type 映射 */
|
||||||
const FROM_ASSET_MAP = {
|
const FROM_ASSET_MAP = {
|
||||||
dashou: 'dashou_yue',
|
dashou: 'dashou_yue',
|
||||||
guanshi: 'guanshi_fenyong',
|
guanshi: 'guanshi_fenyong',
|
||||||
zuzhang: 'zuzhang_fenyong',
|
zuzhang: 'zuzhang_fenyong',
|
||||||
kaoheguan: 'kaoheguan_fenyong',
|
kaoheguan: 'kaoheguan_fenyong',
|
||||||
kaohe: 'kaoheguan_fenyong',
|
kaohe: 'kaoheguan_fenyong',
|
||||||
shangjia: 'shangjia_yue',
|
shangjia: 'shangjia_yue',
|
||||||
yajin: 'dashou_yajin',
|
yajin: 'dashou_yajin',
|
||||||
};
|
};
|
||||||
|
|
||||||
Component({
|
Component({
|
||||||
properties: { options: { type: Object, value: {} } },
|
properties: { options: { type: Object, value: {} } },
|
||||||
data: {
|
data: {
|
||||||
imgUrls: { iconWechat: '' },
|
imgUrls: { iconWechat: '' },
|
||||||
assetList: [],
|
assetList: [],
|
||||||
displayAssetList: [],
|
displayAssetList: [],
|
||||||
totalAmount: '0.00',
|
totalAmount: '0.00',
|
||||||
canWithdraw: false,
|
canWithdraw: false,
|
||||||
selectedAsset: null,
|
selectedAsset: null,
|
||||||
isLoadingAssets: false,
|
isLoadingAssets: false,
|
||||||
tixianleixing: null,
|
tixianleixing: null,
|
||||||
tixianjine: '',
|
tixianjine: '',
|
||||||
currentRate: '0.00',
|
currentRate: '0.00',
|
||||||
feeRateText: '--',
|
feeRateText: '--',
|
||||||
showTixian: false,
|
showTixian: false,
|
||||||
shouxufei: '0.00',
|
shouxufei: '0.00',
|
||||||
shijidaozhang: '0.00',
|
shijidaozhang: '0.00',
|
||||||
submitting: false,
|
submitting: false,
|
||||||
},
|
},
|
||||||
lifetimes: {
|
lifetimes: {
|
||||||
attached() {
|
attached() {
|
||||||
this.initImageUrls();
|
this.initImageUrls();
|
||||||
this.loadAllAssets();
|
this.loadAllAssets();
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
pageLifetimes: {
|
pageLifetimes: {
|
||||||
show() {
|
show() {
|
||||||
this.registerNotificationComponent();
|
this.registerNotificationComponent();
|
||||||
this.loadAllAssets();
|
this.loadAllAssets();
|
||||||
PopupService.checkAndShow(this, 'tixian');
|
PopupService.checkAndShow(this, 'tixian');
|
||||||
},
|
},
|
||||||
hide() {
|
hide() {
|
||||||
const popupComp = this.selectComponent('#popupNotice');
|
const popupComp = this.selectComponent('#popupNotice');
|
||||||
if (popupComp && popupComp.cleanup) popupComp.cleanup();
|
if (popupComp && popupComp.cleanup) popupComp.cleanup();
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
registerNotificationComponent() {
|
registerNotificationComponent() {
|
||||||
const notificationComp = this.selectComponent('#global-notification');
|
const notificationComp = this.selectComponent('#global-notification');
|
||||||
if (notificationComp && notificationComp.showNotification) {
|
if (notificationComp && notificationComp.showNotification) {
|
||||||
app.globalData.globalNotification = {
|
app.globalData.globalNotification = {
|
||||||
show: (data) => notificationComp.showNotification(data),
|
show: (data) => notificationComp.showNotification(data),
|
||||||
hide: () => notificationComp.hideNotification(),
|
hide: () => notificationComp.hideNotification(),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
gengxinYue(data, leixing) {
|
gengxinYue(data, leixing) {
|
||||||
if (!data) return;
|
if (!data) return;
|
||||||
if (data.new_yongjin !== undefined && data.new_yongjin !== null) {
|
if (data.new_yongjin !== undefined && data.new_yongjin !== null) {
|
||||||
app.globalData.yongjin = data.new_yongjin;
|
app.globalData.yongjin = data.new_yongjin;
|
||||||
}
|
}
|
||||||
if (data.new_fenyong !== undefined && data.new_fenyong !== null) {
|
if (data.new_fenyong !== undefined && data.new_fenyong !== null) {
|
||||||
app.globalData.guanshi.fenyongtixian = data.new_fenyong;
|
app.globalData.guanshi.fenyongtixian = data.new_fenyong;
|
||||||
}
|
}
|
||||||
if (data.new_yajin !== undefined && data.new_yajin !== null) {
|
if (data.new_yajin !== undefined && data.new_yajin !== null) {
|
||||||
app.globalData.yajin = data.new_yajin;
|
app.globalData.yajin = data.new_yajin;
|
||||||
}
|
}
|
||||||
if (data.new_shangjia_yue !== undefined && data.new_shangjia_yue !== null) {
|
if (data.new_shangjia_yue !== undefined && data.new_shangjia_yue !== null) {
|
||||||
if (app.globalData.shangjia) app.globalData.shangjia.sjyue = data.new_shangjia_yue;
|
if (app.globalData.shangjia) app.globalData.shangjia.sjyue = data.new_shangjia_yue;
|
||||||
}
|
}
|
||||||
if (data.current_rate !== undefined && leixing) {
|
if (data.current_rate !== undefined && leixing) {
|
||||||
const rate = parseFloat(data.current_rate);
|
const rate = parseFloat(data.current_rate);
|
||||||
const rateKeyMap = { 1: 'dashouRate', 5: 'dashou_yajin_rate', 6: 'shangjia_rate', 2: 'guanshi_rate', 3: 'zuzhang_rate', 4: 'kaoheguan_rate' };
|
const rateKeyMap = { 1: 'dashouRate', 5: 'dashou_yajin_rate', 6: 'shangjia_rate', 2: 'guanshi_rate', 3: 'zuzhang_rate', 4: 'kaoheguan_rate' };
|
||||||
const key = rateKeyMap[leixing];
|
const key = rateKeyMap[leixing];
|
||||||
if (key) wx.setStorageSync(key, rate);
|
if (key) wx.setStorageSync(key, rate);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
initImageUrls() {
|
initImageUrls() {
|
||||||
const ossBase = app.globalData.ossImageUrl || '';
|
const ossBase = app.globalData.ossImageUrl || '';
|
||||||
const imgDir = `${ossBase}beijing/tixian/`;
|
const imgDir = `${ossBase}beijing/tixian/`;
|
||||||
this.setData({
|
this.setData({
|
||||||
imgUrls: {
|
imgUrls: {
|
||||||
iconWechat: `${imgDir}icon_wechat.png`,
|
iconWechat: `${imgDir}icon_wechat.png`,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
/** 顶部展示:不含保证金的可提现合计 */
|
/** 顶部展示:不含保证金的可提现合计 */
|
||||||
calcDisplayTotal(assets) {
|
calcDisplayTotal(assets) {
|
||||||
let total = 0;
|
let total = 0;
|
||||||
(assets || []).forEach((item) => {
|
(assets || []).forEach((item) => {
|
||||||
if (item.type === 'dashou_yajin') return;
|
if (item.type === 'dashou_yajin') return;
|
||||||
total += parseFloat(item.amount) || 0;
|
total += parseFloat(item.amount) || 0;
|
||||||
});
|
});
|
||||||
return total;
|
return total;
|
||||||
},
|
},
|
||||||
|
|
||||||
hasAnyWithdrawable(assets) {
|
hasAnyWithdrawable(assets) {
|
||||||
return (assets || []).some((item) => parseFloat(item.amount) > 0);
|
return (assets || []).some((item) => parseFloat(item.amount) > 0);
|
||||||
},
|
},
|
||||||
|
|
||||||
applyRouteOptions(assets) {
|
applyRouteOptions(assets) {
|
||||||
const opts = this.properties.options || {};
|
const opts = this.properties.options || {};
|
||||||
const fromKey = FROM_ASSET_MAP[opts.from];
|
const fromKey = FROM_ASSET_MAP[opts.from];
|
||||||
let selected = null;
|
let selected = null;
|
||||||
if (fromKey) {
|
if (fromKey) {
|
||||||
selected = assets.find((a) => a.type === fromKey) || null;
|
selected = assets.find((a) => a.type === fromKey) || null;
|
||||||
} else if (assets.length === 1) {
|
} else if (assets.length === 1) {
|
||||||
selected = assets[0];
|
selected = assets[0];
|
||||||
}
|
}
|
||||||
const patch = {};
|
const patch = {};
|
||||||
if (selected) {
|
if (selected) {
|
||||||
patch.selectedAsset = selected;
|
patch.selectedAsset = selected;
|
||||||
patch.tixianleixing = selected.leixing;
|
patch.tixianleixing = selected.leixing;
|
||||||
patch.feeRateText = selected.rateText;
|
patch.feeRateText = selected.rateText;
|
||||||
}
|
}
|
||||||
if (opts.amount && parseFloat(opts.amount) > 0) {
|
if (opts.amount && parseFloat(opts.amount) > 0) {
|
||||||
const amt = parseFloat(opts.amount);
|
const amt = parseFloat(opts.amount);
|
||||||
const max = selected ? parseFloat(selected.amount) : amt;
|
const max = selected ? parseFloat(selected.amount) : amt;
|
||||||
patch.tixianjine = Math.min(amt, max).toFixed(2);
|
patch.tixianjine = Math.min(amt, max).toFixed(2);
|
||||||
}
|
}
|
||||||
if (Object.keys(patch).length) {
|
if (Object.keys(patch).length) {
|
||||||
this.setData(patch, () => {
|
this.setData(patch, () => {
|
||||||
this.recalcFee(this.data.tixianjine, this.data.selectedAsset);
|
this.recalcFee(this.data.tixianjine, this.data.selectedAsset);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
onSelectAsset(e) {
|
onSelectAsset(e) {
|
||||||
const index = e.currentTarget.dataset.index;
|
const index = e.currentTarget.dataset.index;
|
||||||
const asset = this.data.displayAssetList[index];
|
const asset = this.data.displayAssetList[index];
|
||||||
if (!asset || parseFloat(asset.amount) <= 0) {
|
if (!asset || parseFloat(asset.amount) <= 0) {
|
||||||
wx.showToast({ title: '该账户无可提余额', icon: 'none' });
|
wx.showToast({ title: '该账户无可提余额', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
let jine = this.data.tixianjine;
|
let jine = this.data.tixianjine;
|
||||||
const max = parseFloat(asset.amount);
|
const max = parseFloat(asset.amount);
|
||||||
if (jine && parseFloat(jine) > max) {
|
if (jine && parseFloat(jine) > max) {
|
||||||
jine = asset.amount;
|
jine = asset.amount;
|
||||||
}
|
}
|
||||||
this.setData({
|
this.setData({
|
||||||
selectedAsset: asset,
|
selectedAsset: asset,
|
||||||
tixianleixing: asset.leixing,
|
tixianleixing: asset.leixing,
|
||||||
tixianjine: jine,
|
tixianjine: jine,
|
||||||
});
|
});
|
||||||
this.recalcFee(jine, asset);
|
this.recalcFee(jine, asset);
|
||||||
},
|
},
|
||||||
|
|
||||||
async loadAllAssets() {
|
async loadAllAssets() {
|
||||||
this.setData({ isLoadingAssets: true, totalAmount: '0.00', canWithdraw: false, assetList: [] });
|
this.setData({ isLoadingAssets: true, totalAmount: '0.00', canWithdraw: false, assetList: [] });
|
||||||
try {
|
try {
|
||||||
const res = await request({ url: '/yonghu/tixianzichan', method: 'POST' });
|
const res = await request({ url: '/yonghu/tixianzichan', method: 'POST' });
|
||||||
if (res?.data?.code === 200 || res?.data?.code === 0) {
|
if (res?.data?.code === 200 || res?.data?.code === 0) {
|
||||||
const data = res.data.data || {};
|
const data = res.data.data || {};
|
||||||
const assets = [];
|
const assets = [];
|
||||||
const pushAsset = (type, amount, rate) => {
|
const pushAsset = (type, amount, rate) => {
|
||||||
const cfg = ASSET_CONFIG[type];
|
const cfg = ASSET_CONFIG[type];
|
||||||
if (!cfg || !amount || parseFloat(amount) <= 0) return;
|
if (!cfg || !amount || parseFloat(amount) <= 0) return;
|
||||||
assets.push({
|
assets.push({
|
||||||
type,
|
type,
|
||||||
leixing: cfg.leixing,
|
leixing: cfg.leixing,
|
||||||
label: cfg.label,
|
label: cfg.label,
|
||||||
amount: parseFloat(amount).toFixed(2),
|
amount: parseFloat(amount).toFixed(2),
|
||||||
rate: rate || 0,
|
rate: rate || 0,
|
||||||
rateText: this.formatRatePercent(rate || 0),
|
rateText: this.formatRatePercent(rate || 0),
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
pushAsset('dashou_yue', data.dashou_yue, data.dashou_rate);
|
pushAsset('dashou_yue', data.dashou_yue, data.dashou_rate);
|
||||||
pushAsset('dashou_yajin', data.dashou_yajin, data.dashou_yajin_rate);
|
pushAsset('dashou_yajin', data.dashou_yajin, data.dashou_yajin_rate);
|
||||||
pushAsset('shangjia_yue', data.shangjia_yue, data.shangjia_rate);
|
pushAsset('shangjia_yue', data.shangjia_yue, data.shangjia_rate);
|
||||||
pushAsset('guanshi_fenyong', data.guanshi_fenyong, data.guanshi_rate);
|
pushAsset('guanshi_fenyong', data.guanshi_fenyong, data.guanshi_rate);
|
||||||
pushAsset('zuzhang_fenyong', data.zuzhang_fenyong, data.zuzhang_rate);
|
pushAsset('zuzhang_fenyong', data.zuzhang_fenyong, data.zuzhang_rate);
|
||||||
pushAsset('kaoheguan_fenyong', data.kaoheguan_fenyong, data.kaoheguan_rate);
|
pushAsset('kaoheguan_fenyong', data.kaoheguan_fenyong, data.kaoheguan_rate);
|
||||||
|
|
||||||
const displayTotal = this.calcDisplayTotal(assets);
|
const displayTotal = this.calcDisplayTotal(assets);
|
||||||
const firstRate = assets.find((a) => a.type !== 'dashou_yajin')?.rate || 0;
|
const firstRate = assets.find((a) => a.type !== 'dashou_yajin')?.rate || 0;
|
||||||
this.setData({
|
this.setData({
|
||||||
assetList: assets,
|
assetList: assets,
|
||||||
displayAssetList: assets,
|
displayAssetList: assets,
|
||||||
totalAmount: displayTotal.toFixed(2),
|
totalAmount: displayTotal.toFixed(2),
|
||||||
canWithdraw: this.hasAnyWithdrawable(assets),
|
canWithdraw: this.hasAnyWithdrawable(assets),
|
||||||
isLoadingAssets: false,
|
isLoadingAssets: false,
|
||||||
feeRateText: displayTotal > 0 ? this.formatRatePercent(firstRate) : '--',
|
feeRateText: displayTotal > 0 ? this.formatRatePercent(firstRate) : '--',
|
||||||
}, () => this.applyRouteOptions(assets));
|
}, () => this.applyRouteOptions(assets));
|
||||||
if (!this.data.selectedAsset) {
|
if (!this.data.selectedAsset) {
|
||||||
this.recalcFee(this.data.tixianjine, null);
|
this.recalcFee(this.data.tixianjine, null);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
throw new Error(res?.data?.msg || '获取资产失败');
|
throw new Error(res?.data?.msg || '获取资产失败');
|
||||||
}
|
}
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
console.error('loadAllAssets', err);
|
console.error('loadAllAssets', err);
|
||||||
this.setData({ isLoadingAssets: false, totalAmount: '0.00', canWithdraw: false, assetList: [] });
|
this.setData({ isLoadingAssets: false, totalAmount: '0.00', canWithdraw: false, assetList: [] });
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
formatRatePercent(rate) {
|
formatRatePercent(rate) {
|
||||||
const r = parseFloat(rate) || 0;
|
const r = parseFloat(rate) || 0;
|
||||||
if (r <= 1 && r > 0) return `${(r * 100).toFixed(0)}%`;
|
if (r <= 1 && r > 0) return `${(r * 100).toFixed(0)}%`;
|
||||||
return `${r}%`;
|
return `${r}%`;
|
||||||
},
|
},
|
||||||
|
|
||||||
recalcFee(amountStr, asset) {
|
recalcFee(amountStr, asset) {
|
||||||
const amount = parseFloat(amountStr);
|
const amount = parseFloat(amountStr);
|
||||||
if (!amountStr || isNaN(amount) || amount <= 0 || !asset) {
|
if (!amountStr || isNaN(amount) || amount <= 0 || !asset) {
|
||||||
this.setData({
|
this.setData({
|
||||||
shouxufei: '0.00',
|
shouxufei: '0.00',
|
||||||
shijidaozhang: '0.00',
|
shijidaozhang: '0.00',
|
||||||
feeRateText: asset ? this.formatRatePercent(asset.rate) : this.data.feeRateText,
|
feeRateText: asset ? this.formatRatePercent(asset.rate) : this.data.feeRateText,
|
||||||
});
|
});
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const rate = parseFloat(asset.rate) || 0;
|
const rate = parseFloat(asset.rate) || 0;
|
||||||
const fee = amount * rate;
|
const fee = amount * rate;
|
||||||
const actual = amount - fee;
|
const actual = amount - fee;
|
||||||
this.setData({
|
this.setData({
|
||||||
shouxufei: fee.toFixed(2),
|
shouxufei: fee.toFixed(2),
|
||||||
shijidaozhang: actual.toFixed(2),
|
shijidaozhang: actual.toFixed(2),
|
||||||
feeRateText: this.formatRatePercent(rate),
|
feeRateText: this.formatRatePercent(rate),
|
||||||
currentRate: this.formatRatePercent(rate),
|
currentRate: this.formatRatePercent(rate),
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
onJineInput(e) {
|
onJineInput(e) {
|
||||||
const val = e.detail.value;
|
const val = e.detail.value;
|
||||||
this.setData({ tixianjine: val });
|
this.setData({ tixianjine: val });
|
||||||
this.recalcFee(val, this.data.selectedAsset);
|
this.recalcFee(val, this.data.selectedAsset);
|
||||||
},
|
},
|
||||||
|
|
||||||
onWithdrawAll() {
|
onWithdrawAll() {
|
||||||
const { selectedAsset } = this.data;
|
const { selectedAsset } = this.data;
|
||||||
if (!selectedAsset) {
|
if (!selectedAsset) {
|
||||||
wx.showToast({ title: '请先选择提现账户', icon: 'none' });
|
wx.showToast({ title: '请先选择提现账户', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const max = selectedAsset.amount;
|
const max = selectedAsset.amount;
|
||||||
this.setData({ tixianjine: max });
|
this.setData({ tixianjine: max });
|
||||||
this.recalcFee(max, selectedAsset);
|
this.recalcFee(max, selectedAsset);
|
||||||
},
|
},
|
||||||
|
|
||||||
onTapWithdraw() {
|
onTapWithdraw() {
|
||||||
if (this.data.submitting) return;
|
if (this.data.submitting) return;
|
||||||
if (!this.hasAnyWithdrawable(this.data.assetList)) {
|
if (!this.hasAnyWithdrawable(this.data.assetList)) {
|
||||||
wx.showToast({ title: '暂无可提现余额', icon: 'none' });
|
wx.showToast({ title: '暂无可提现余额', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const { selectedAsset, tixianjine } = this.data;
|
const { selectedAsset, tixianjine } = this.data;
|
||||||
if (!selectedAsset) {
|
if (!selectedAsset) {
|
||||||
wx.showToast({ title: '请先选择要提现的账户', icon: 'none' });
|
wx.showToast({ title: '请先选择要提现的账户', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const jineValue = parseFloat(tixianjine);
|
const jineValue = parseFloat(tixianjine);
|
||||||
if (!tixianjine || isNaN(jineValue) || jineValue <= 0) {
|
if (!tixianjine || isNaN(jineValue) || jineValue <= 0) {
|
||||||
wx.showToast({ title: '请输入有效金额', icon: 'none' });
|
wx.showToast({ title: '请输入有效金额', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (jineValue <= 0.1) {
|
if (jineValue <= 0.1) {
|
||||||
wx.showToast({ title: '提现金额须大于0.1元', icon: 'none' });
|
wx.showToast({ title: '提现金额须大于0.1元', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (jineValue > parseFloat(selectedAsset.amount)) {
|
if (jineValue > parseFloat(selectedAsset.amount)) {
|
||||||
wx.showToast({ title: `超过${selectedAsset.label}可提余额`, icon: 'none' });
|
wx.showToast({ title: `超过${selectedAsset.label}可提余额`, icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
this.applyIdentityAndConfirm(selectedAsset);
|
this.applyIdentityAndConfirm(selectedAsset);
|
||||||
},
|
},
|
||||||
|
|
||||||
applyIdentityAndConfirm(asset) {
|
applyIdentityAndConfirm(asset) {
|
||||||
this.recalcFee(this.data.tixianjine, asset);
|
this.recalcFee(this.data.tixianjine, asset);
|
||||||
this.setData({
|
this.setData({
|
||||||
selectedAsset: asset,
|
selectedAsset: asset,
|
||||||
tixianleixing: asset.leixing,
|
tixianleixing: asset.leixing,
|
||||||
currentRate: this.formatRatePercent(asset.rate),
|
currentRate: this.formatRatePercent(asset.rate),
|
||||||
showTixian: true,
|
showTixian: true,
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
async onConfirmTixian() {
|
async onConfirmTixian() {
|
||||||
if (this.data.submitting) return;
|
if (this.data.submitting) return;
|
||||||
const { tixianleixing, tixianjine, selectedAsset } = this.data;
|
const { tixianleixing, tixianjine, selectedAsset } = this.data;
|
||||||
if (!tixianleixing || !selectedAsset) {
|
if (!tixianleixing || !selectedAsset) {
|
||||||
wx.showToast({ title: '请选择提现身份', icon: 'none' });
|
wx.showToast({ title: '请选择提现身份', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const jineValue = parseFloat(tixianjine);
|
const jineValue = parseFloat(tixianjine);
|
||||||
if (!tixianjine || isNaN(jineValue) || jineValue <= 0) {
|
if (!tixianjine || isNaN(jineValue) || jineValue <= 0) {
|
||||||
wx.showToast({ title: '请输入有效金额', icon: 'none' });
|
wx.showToast({ title: '请输入有效金额', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (jineValue > parseFloat(selectedAsset.amount)) {
|
if (jineValue > parseFloat(selectedAsset.amount)) {
|
||||||
wx.showToast({ title: `超过${selectedAsset.label}可提余额`, icon: 'none' });
|
wx.showToast({ title: `超过${selectedAsset.label}可提余额`, icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
this.setData({ submitting: true });
|
this.setData({ submitting: true });
|
||||||
try {
|
try {
|
||||||
const res = await request({
|
const res = await request({
|
||||||
url: '/yonghu/zddksh',
|
url: '/yonghu/zddksh',
|
||||||
method: 'POST',
|
method: 'POST',
|
||||||
data: { leixing: tixianleixing, jine: jineValue.toFixed(2) },
|
data: { leixing: tixianleixing, jine: jineValue.toFixed(2) },
|
||||||
});
|
});
|
||||||
if (res.statusCode === 200 && res.data && res.data.code === 0) {
|
if (res.statusCode === 200 && res.data && res.data.code === 0) {
|
||||||
const data = res.data.data || {};
|
const data = res.data.data || {};
|
||||||
this.gengxinYue(data, tixianleixing);
|
this.gengxinYue(data, tixianleixing);
|
||||||
this.setData({
|
this.setData({
|
||||||
showTixian: false,
|
showTixian: false,
|
||||||
submitting: false,
|
submitting: false,
|
||||||
selectedAsset: null,
|
selectedAsset: null,
|
||||||
tixianjine: '',
|
tixianjine: '',
|
||||||
shouxufei: '0.00',
|
shouxufei: '0.00',
|
||||||
shijidaozhang: '0.00',
|
shijidaozhang: '0.00',
|
||||||
});
|
});
|
||||||
await this.loadAllAssets();
|
await this.loadAllAssets();
|
||||||
wx.showModal({
|
wx.showModal({
|
||||||
title: '申请成功',
|
title: '申请成功',
|
||||||
content: '提现申请已提交,请前往「提现记录」查看进度;审核通过后可在该页点击「收款」确认到账。',
|
content: '提现申请已提交,请前往「提现记录」查看进度;审核通过后可在该页点击「收款」确认到账。',
|
||||||
confirmText: '查看提现记录',
|
confirmText: '查看提现记录',
|
||||||
cancelText: '知道了',
|
cancelText: '知道了',
|
||||||
success: (res) => {
|
success: (res) => {
|
||||||
if (res.confirm) {
|
if (res.confirm) {
|
||||||
wx.navigateTo({ url: '/pages/withdraw/withdraw-records' });
|
wx.navigateTo({ url: '/pages/withdraw/withdraw-records' });
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
wx.showModal({ title: '提现申请失败', content: res.data?.msg || '未知错误', showCancel: false });
|
wx.showModal({ title: '提现申请失败', content: res.data?.msg || '未知错误', showCancel: false });
|
||||||
this.setData({ submitting: false });
|
this.setData({ submitting: false });
|
||||||
}
|
}
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
wx.showModal({ title: '网络错误', content: '网络连接失败,请稍后重试', showCancel: false });
|
wx.showModal({ title: '网络错误', content: '网络连接失败,请稍后重试', showCancel: false });
|
||||||
this.setData({ submitting: false });
|
this.setData({ submitting: false });
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
onCloseTixian() {
|
onCloseTixian() {
|
||||||
if (this.data.submitting) {
|
if (this.data.submitting) {
|
||||||
wx.showToast({ title: '正在处理中,请稍后', icon: 'none' });
|
wx.showToast({ title: '正在处理中,请稍后', icon: 'none' });
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
this.setData({
|
this.setData({
|
||||||
showTixian: false,
|
showTixian: false,
|
||||||
selectedAsset: null,
|
selectedAsset: null,
|
||||||
tixianleixing: null,
|
tixianleixing: null,
|
||||||
shouxufei: '0.00',
|
shouxufei: '0.00',
|
||||||
shijidaozhang: '0.00',
|
shijidaozhang: '0.00',
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
stopPropagation() {},
|
stopPropagation() {},
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -356,6 +356,15 @@ Component({
|
|||||||
collectConfirmRecord: record,
|
collectConfirmRecord: record,
|
||||||
});
|
});
|
||||||
this.tiaoqiWeixinQueRen(data.package_info);
|
this.tiaoqiWeixinQueRen(data.package_info);
|
||||||
|
} else if (res.data && res.data.code === 12) {
|
||||||
|
wx.showModal({
|
||||||
|
title: '收款处理中',
|
||||||
|
content: (res.data.msg || '请等待几秒后再次点击「收款」') + ',无需重新申请提现。',
|
||||||
|
showCancel: false,
|
||||||
|
complete: () => {
|
||||||
|
this.setData({ submitting: false, collectConfirmRecord: null });
|
||||||
|
},
|
||||||
|
});
|
||||||
} else {
|
} else {
|
||||||
wx.showModal({ title: '收款失败', content: res.data?.msg || '无法发起收款,请稍后重试', showCancel: false });
|
wx.showModal({ title: '收款失败', content: res.data?.msg || '无法发起收款,请稍后重试', showCancel: false });
|
||||||
this.setData({ submitting: false, collectConfirmRecord: null });
|
this.setData({ submitting: false, collectConfirmRecord: null });
|
||||||
|
|||||||
@@ -1,40 +1,40 @@
|
|||||||
/* pages/withdraw/withdraw.wxss */
|
/* pages/withdraw/withdraw.wxss */
|
||||||
.tixian-container {
|
.tixian-container {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
min-height: 100vh;
|
min-height: 100vh;
|
||||||
background: #f5f5f5;
|
background: #f5f5f5;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* 加载状态 */
|
/* 加载状态 */
|
||||||
.loading-center, .error-center {
|
.loading-center, .error-center {
|
||||||
height: 100vh;
|
height: 100vh;
|
||||||
display: flex;
|
display: flex;
|
||||||
flex-direction: column;
|
flex-direction: column;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
justify-content: center;
|
justify-content: center;
|
||||||
color: #666;
|
color: #666;
|
||||||
background: #f5f5f5;
|
background: #f5f5f5;
|
||||||
}
|
}
|
||||||
|
|
||||||
.loading-spinner {
|
.loading-spinner {
|
||||||
border: 4rpx solid rgba(157, 78, 221, 0.3);
|
border: 4rpx solid rgba(157, 78, 221, 0.3);
|
||||||
border-top-color: #9d4edd;
|
border-top-color: #9d4edd;
|
||||||
margin-bottom: 30rpx;
|
margin-bottom: 30rpx;
|
||||||
}
|
}
|
||||||
|
|
||||||
.loading-text {
|
.loading-text {
|
||||||
font-size: 28rpx;
|
font-size: 28rpx;
|
||||||
color: rgba(255, 255, 255, 0.7);
|
color: rgba(255, 255, 255, 0.7);
|
||||||
}
|
}
|
||||||
|
|
||||||
.error-text {
|
.error-text {
|
||||||
font-size: 28rpx;
|
font-size: 28rpx;
|
||||||
margin-bottom: 30rpx;
|
margin-bottom: 30rpx;
|
||||||
}
|
}
|
||||||
|
|
||||||
.retry-btn {
|
.retry-btn {
|
||||||
padding: 20rpx 60rpx;
|
padding: 20rpx 60rpx;
|
||||||
background: linear-gradient(90deg, #6a11cb, #2575fc);
|
background: linear-gradient(90deg, #6a11cb, #2575fc);
|
||||||
color: white;
|
color: white;
|
||||||
font-size: 28rpx;
|
font-size: 28rpx;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -62,6 +62,6 @@
|
|||||||
],
|
],
|
||||||
"include": []
|
"include": []
|
||||||
},
|
},
|
||||||
"appid": "wxdefa454152e78a03",
|
"appid": "wx7ff90e9d024fcdb8",
|
||||||
"simulatorPluginLibVersion": {}
|
"simulatorPluginLibVersion": {}
|
||||||
}
|
}
|
||||||
@@ -9,6 +9,7 @@ const DEFAULT_CLUB_ID = CONFIG_CLUB_ID || 'xq';
|
|||||||
|
|
||||||
export const CLUB_API = {
|
export const CLUB_API = {
|
||||||
wechatLogin: '/jituan/auth/wechat-login',
|
wechatLogin: '/jituan/auth/wechat-login',
|
||||||
|
refreshWxBind: '/jituan/auth/refresh-wx-bind',
|
||||||
dashouRegister: '/jituan/auth/dashou-register',
|
dashouRegister: '/jituan/auth/dashou-register',
|
||||||
clubList: '/jituan/club/list',
|
clubList: '/jituan/club/list',
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -10,6 +10,30 @@ import { CLUB_API, getClubId, setClubId, buildClubHeaders } from './club-context
|
|||||||
|
|
||||||
const app = getApp();
|
const app = getApp();
|
||||||
|
|
||||||
|
/** 有 token 时静默刷新当前小程序 openid 绑定(支付 AppID 对齐) */
|
||||||
|
function silentRefreshWxBind(app) {
|
||||||
|
const token = getSessionToken(app);
|
||||||
|
if (!token) return;
|
||||||
|
wx.login({
|
||||||
|
success: (loginRes) => {
|
||||||
|
if (!loginRes.code || !app.globalData.apiBaseUrl) return;
|
||||||
|
wx.request({
|
||||||
|
url: app.globalData.apiBaseUrl + CLUB_API.refreshWxBind,
|
||||||
|
method: 'POST',
|
||||||
|
data: {
|
||||||
|
code: loginRes.code,
|
||||||
|
club_id: getClubId(app),
|
||||||
|
app_id: app.globalData.appId || '',
|
||||||
|
},
|
||||||
|
header: buildClubHeaders({
|
||||||
|
'content-type': 'application/json',
|
||||||
|
Authorization: 'Bearer ' + token,
|
||||||
|
}),
|
||||||
|
});
|
||||||
|
},
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
export function ensureLogin(options = {}) {
|
export function ensureLogin(options = {}) {
|
||||||
const silent = options.silent !== false;
|
const silent = options.silent !== false;
|
||||||
const page = options.page || null;
|
const page = options.page || null;
|
||||||
@@ -17,6 +41,7 @@ export function ensureLogin(options = {}) {
|
|||||||
if (token) {
|
if (token) {
|
||||||
backfillUserProfileCache(app);
|
backfillUserProfileCache(app);
|
||||||
restoreStaffContextAfterAuth();
|
restoreStaffContextAfterAuth();
|
||||||
|
silentRefreshWxBind(app);
|
||||||
return Promise.resolve(true);
|
return Promise.resolve(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -36,6 +36,7 @@ export const ICON_KEYS = {
|
|||||||
FIGHTER_RECHARGE_ADVANTAGE_2: 'fighter_recharge_advantage_2',
|
FIGHTER_RECHARGE_ADVANTAGE_2: 'fighter_recharge_advantage_2',
|
||||||
FIGHTER_RECHARGE_ADVANTAGE_3: 'fighter_recharge_advantage_3',
|
FIGHTER_RECHARGE_ADVANTAGE_3: 'fighter_recharge_advantage_3',
|
||||||
FIGHTER_RECHARGE_ADVANTAGE_4: 'fighter_recharge_advantage_4',
|
FIGHTER_RECHARGE_ADVANTAGE_4: 'fighter_recharge_advantage_4',
|
||||||
|
FIGHTER_COMPLAINT_RECORD: 'fighter_complaint_record',
|
||||||
FIGHTER_ORDER_PENDING: 'fighter_order_pending',
|
FIGHTER_ORDER_PENDING: 'fighter_order_pending',
|
||||||
FIGHTER_ORDER_SETTLING: 'fighter_order_settling',
|
FIGHTER_ORDER_SETTLING: 'fighter_order_settling',
|
||||||
FIGHTER_ORDER_DONE: 'fighter_order_done',
|
FIGHTER_ORDER_DONE: 'fighter_order_done',
|
||||||
|
|||||||
Reference in New Issue
Block a user