Commit 0b1e5da8090e563987c03a88cd0a8b560b1bce16

Authored by lxf
1 parent bd988dfd

fix: 支付计划

@@ -116,6 +116,14 @@ module.exports = (vm) => { @@ -116,6 +116,14 @@ module.exports = (vm) => {
116 audit: params => vm.$u.http.post(freightAPI + '/freightPayApply/audit', params,{custom: {toast:true}}), // 审核 116 audit: params => vm.$u.http.post(freightAPI + '/freightPayApply/audit', params,{custom: {toast:true}}), // 审核
117 getCount: params => vm.$u.http.get(freightAPI + '/freightPayApply/getCount', {params}), // 总数 117 getCount: params => vm.$u.http.get(freightAPI + '/freightPayApply/getCount', {params}), // 总数
118 }, 118 },
  119 + // 支付计划
  120 + paymentPlan: {
  121 + page: params => vm.$u.http.post(freightAPI + '/freightPayPlan/page', params),
  122 + getCount: params => vm.$u.http.get(freightAPI + '/freightPayPlan/getCount', {params}), // 总数
  123 + getApplyDetailByIds: params => vm.$u.http.post(freightAPI + '/freightPayPlan/getApplyDetailByIds', params,{custom: {toast:true}}), // 查询支付明细信息
  124 + checkPayPassword: data => vm.$u.http.post(freightAPI + '/account/checkPayPassword', data), // 校验密码
  125 + pay: data => vm.$u.http.post(freightAPI + '/freightPayPlan/pay', data), // 支付
  126 + },
119 // 订单管理-网货货运-new 127 // 订单管理-网货货运-new
120 freightOrder: { 128 freightOrder: {
121 add: params => vm.$u.http.post(freightAPI + '/freightOrder/maAdd', params,{custom: {toast:true}}), // 下单 129 add: params => vm.$u.http.post(freightAPI + '/freightOrder/maAdd', params,{custom: {toast:true}}), // 下单
@@ -196,6 +196,30 @@ @@ -196,6 +196,30 @@
196 } 196 }
197 } 197 }
198 ] 198 ]
  199 + },
  200 + {
  201 + "root":"pages/payPlan",
  202 + "pages":[
  203 + {
  204 + "path": "list",
  205 + "style": {
  206 + "navigationBarTitleText": "支付计划",
  207 + "enablePullDownRefresh": true
  208 + }
  209 + },
  210 + {
  211 + "path": "filter",
  212 + "style": {
  213 + "navigationBarTitleText": "筛选器"
  214 + }
  215 + },
  216 + {
  217 + "path": "paySubmit",
  218 + "style": {
  219 + "navigationBarTitleText": "支付信息确认"
  220 + }
  221 + }
  222 + ]
199 } 223 }
200 ], 224 ],
201 "globalStyle": { 225 "globalStyle": {
pages/me/index.vue
@@ -43,6 +43,11 @@ @@ -43,6 +43,11 @@
43 <!-- #endif --> 43 <!-- #endif -->
44 </view> 44 </view>
45 </view> 45 </view>
  46 + <view class="page-my__list">
  47 + <u-cell-group>
  48 + <u-cell v-if="$permission('/settlement/paymentPlan')" label="支付计划" is-link url="/pages/payPlan/list"> </u-cell>
  49 + </u-cell-group>
  50 + </view>
46 <view class="page-my__login"> 51 <view class="page-my__login">
47 <u-button shape="circle" @click="handleRefreshVersion">检测更新</u-button> 52 <u-button shape="circle" @click="handleRefreshVersion">检测更新</u-button>
48 <template v-if="authed"> 53 <template v-if="authed">
@@ -64,8 +69,10 @@ @@ -64,8 +69,10 @@
64 import cache from '@/utils/cache'; 69 import cache from '@/utils/cache';
65 import { mapState, mapGetters } from 'vuex'; 70 import { mapState, mapGetters } from 'vuex';
66 import { version } from '@/config'; 71 import { version } from '@/config';
  72 +import page from '@/mixins/page';
67 73
68 export default { 74 export default {
  75 + mixins: [page],
69 data() { 76 data() {
70 return { 77 return {
71 loading: false, 78 loading: false,
@@ -217,6 +224,11 @@ export default { @@ -217,6 +224,11 @@ export default {
217 background-color: rgba($color-primary, 0.3); 224 background-color: rgba($color-primary, 0.3);
218 } 225 }
219 } 226 }
  227 + &__list {
  228 + margin: $padding-md;
  229 + background: $color-white;
  230 + border-radius: $radius-md;
  231 + }
220 &__login { 232 &__login {
221 position: absolute; 233 position: absolute;
222 width: 100%; 234 width: 100%;
pages/order/card.vue
@@ -43,13 +43,16 @@ @@ -43,13 +43,16 @@
43 <view class="tag--paying" v-if="item.driverCertifiedStatus === 'CERTIFYING'">司机认证中</view> 43 <view class="tag--paying" v-if="item.driverCertifiedStatus === 'CERTIFYING'">司机认证中</view>
44 <view class="tag--warning" v-if="item.payeeMobile && item.bindBankCardNoFlag === false">收款人未绑卡</view> 44 <view class="tag--warning" v-if="item.payeeMobile && item.bindBankCardNoFlag === false">收款人未绑卡</view>
45 <view class="tag--warning" v-if="item.vehicleLicenseNum && item.vehicleCertifiedStatus === 'NOT_CERTIFIED' && !item.trailerLicenseNum">车辆未认证</view> 45 <view class="tag--warning" v-if="item.vehicleLicenseNum && item.vehicleCertifiedStatus === 'NOT_CERTIFIED' && !item.trailerLicenseNum">车辆未认证</view>
46 - <view class="tag--paying" v-if="item.vehicleLicenseNum && item.vehicleCertifiedStatus === 'CERTIFYING' && !item.trailerLicenseNum">车辆认证中</view>  
47 - <view class="tag--warning" v-if="item.vehicleLicenseNum && item.vehicleCertifiedStatus === 'NOT_CERTIFIED' && item.trailerLicenseNum">车头未认证</view>  
48 - <view class="tag--paying" v-if="item.vehicleLicenseNum && item.vehicleCertifiedStatus === 'CERTIFYING' && item.trailerLicenseNum">车头认证中</view>  
49 - <view class="tag--warning" v-if="item.trailerLicenseNum && !item.extraTrailerFlag && item.trailerVehicleCertifiedStatus === 'NOT_CERTIFIED'">车挂未认证</view>  
50 - <view class="tag--paying" v-if="item.trailerLicenseNum && !item.extraTrailerFlag && item.trailerVehicleCertifiedStatus === 'CERTIFYING'">车挂认证中</view> 46 + <view class="tag--paying" v-else-if="item.vehicleLicenseNum && item.vehicleCertifiedStatus === 'CERTIFYING' && !item.trailerLicenseNum">车辆认证中</view>
  47 + <view class="tag--warning" v-else-if="item.vehicleLicenseNum && item.vehicleCertifiedStatus === 'NOT_CERTIFIED' && item.trailerLicenseNum">车头未认证</view>
  48 + <view class="tag--paying" v-else-if="item.vehicleLicenseNum && item.vehicleCertifiedStatus === 'CERTIFYING' && item.trailerLicenseNum">车头认证中</view>
  49 + <view class="tag--paying" v-else-if="item.vehicleLicenseNum && item.vehicleExpiredFlag && item.vehicleCertifiedStatus === 'CERTIFIED'">车头证件过期</view>
  50 +
51 <text class="tag--warning" v-if="item.extraTrailerFlag">多车挂</text> 51 <text class="tag--warning" v-if="item.extraTrailerFlag">多车挂</text>
52 - <text class="tag--warning" v-if="item.missTrailerFlag">缺车挂</text> 52 + <text class="tag--warning" v-else-if="item.missTrailerFlag">缺车挂</text>
  53 + <view class="tag--warning" v-else-if="item.trailerLicenseNum && !item.extraTrailerFlag && item.trailerVehicleCertifiedStatus === 'NOT_CERTIFIED'">车挂未认证</view>
  54 + <view class="tag--paying" v-else-if="item.trailerLicenseNum && !item.extraTrailerFlag && item.trailerVehicleCertifiedStatus === 'CERTIFYING'">车挂认证中</view>
  55 + <text class="tag--warning" v-else-if="item.trailerLicenseNum && item.trailerExpiredFlag && item.trailerVehicleCertifiedStatus === 'CERTIFIED'">车挂证件过期</text>
53 </view> 56 </view>
54 <view class="card-order__footer"> 57 <view class="card-order__footer">
55 <view class="amount"> 58 <view class="amount">
pages/payPlan/card.vue 0 → 100644
@@ -0,0 +1,193 @@ @@ -0,0 +1,193 @@
  1 +<template>
  2 + <view class="payment-card" @mousedown="mousedown" @mouseup="mouseup" @touchstart="mousedown" @touchend="mouseup" @tap="choseFun">
  3 + <view class="title">
  4 + <view class="code">
  5 + <field-copy :value="item.payCode" v-if="item.payCode">{{ item.payCode }} </field-copy>
  6 + </view>
  7 + <view style="display: flex">
  8 + <render-dict v-if="item.payStatus" class="status" :style="{ color: colorMap[item.payStatus] }" dict="ONLINE_FREIGHT_ORDER_PAY_STATUS" :value="item.payStatus"></render-dict>
  9 + <template v-if="choseMore">
  10 + <u-radio-group :value="choseIds.includes(item.id) ? item.id : ''">
  11 + <u-radio :name="item.id"></u-radio>
  12 + </u-radio-group>
  13 + <!-- <u-icon v-if="choseIds.includes(item.id)" name="checkmark-circle-fill" size="20" color="#1E7B6B"></u-icon>-->
  14 + </template>
  15 + </view>
  16 + </view>
  17 + <view class="title-sub">{{ item.projectName ? item.projectName : '' }}{{ item.loadTime ? '|' + item.loadTime + '装货' : '' }}</view>
  18 + <view class="item">
  19 + <view class="label">
  20 + <render-dict v-if="item.feeType" dict="ONLINE_FREIGHT_ORDER_FEE_TYPE" :value="item.feeType"></render-dict>
  21 + </view>
  22 + <view class="content">
  23 + <text class="amount">¥{{ item.feeAmount ? item.feeAmount : '' }}</text>
  24 + </view>
  25 + </view>
  26 + <view class="item">
  27 + <view class="label">承运司机</view>
  28 + <view class="content">
  29 + <text>{{ item.driverName ? item.driverName : '' }}</text>
  30 + <text>{{ item.driverMobile ? item.driverMobile : '' }}</text>
  31 + </view>
  32 + </view>
  33 + <view class="item">
  34 + <view class="label">收款人</view>
  35 + <view class="content">
  36 + <text>{{ item.recAccountName ? item.recAccountName : '' }}</text>
  37 + <text>{{ item.recMobile ? item.recMobile : '' }}</text>
  38 + </view>
  39 + </view>
  40 + <view class="item">
  41 + <view class="label">承运车辆</view>
  42 + <view class="content">{{ item.vehicleLicenseNum ? item.vehicleLicenseNum : '' }}{{ item.trailerLicenseNum ? '·' + item.trailerLicenseNum : '' }}</view>
  43 + </view>
  44 + <view class="item">
  45 + <view class="label">订单号</view>
  46 + <view class="content">
  47 + <text>{{ item.orderCode }}</text>
  48 + <text v-if="!!item.waitHandleExceptionNumber" class="content--warning">{{ item.waitHandleExceptionNumber || '0' }}个异常待处理</text>
  49 + </view>
  50 + </view>
  51 + <view class="item">
  52 + <view class="label">线路名称</view>
  53 + <view class="content">{{ item.lineName ? item.lineName : '' }}</view>
  54 + </view>
  55 + <view class="item" v-if="!choseMore && ['NOT_PAY', 'PAY_FAILED'].includes(item.payStatus)">
  56 + <u-button v-if="$permission('/freightPayPlan/apply')" type="primary" @tap="paymentFun">{{ item.payStatus === 'PAY_FAILED' ? '重新支付' : '提交支付' }}</u-button>
  57 + </view>
  58 + </view>
  59 +</template>
  60 +<script>
  61 +import FieldCopy from '../../components/field/field-copy.vue';
  62 +import UButton from '../../uni_modules/uview-ui/components/u-button/u-button.vue';
  63 +import page from '../../mixins/page';
  64 +export default {
  65 + name: 'payment-card',
  66 + mixins: [page],
  67 + components: { UButton, FieldCopy },
  68 + props: {
  69 + choseMore: Boolean,
  70 + choseIds: {
  71 + type: Array,
  72 + default() {
  73 + return [];
  74 + },
  75 + },
  76 + item: {
  77 + type: Object,
  78 + default() {
  79 + return {};
  80 + },
  81 + },
  82 + },
  83 + data() {
  84 + return {
  85 + visible: false,
  86 + pressTimer: '',
  87 + isLongClick: false,
  88 + colorMap: {
  89 + NOT_PAY: '#ff4f3b',
  90 + PAYING: '#0000FF',
  91 + PAY_FAILED: '#999999',
  92 + PAY_SUCCESS: '#00B87A',
  93 + },
  94 + };
  95 + },
  96 + methods: {
  97 + paymentFun() {
  98 + if (!this.isLongClick) {
  99 + this.$emit('payment', this.item.id);
  100 + }
  101 + },
  102 + choseFun() {
  103 + if (!this.isLongClick) {
  104 + this.$emit('chose', this.item.id);
  105 + }
  106 + },
  107 + mousedown() {
  108 + if (this.choseMore) return;
  109 + this.pressTimer = setTimeout(() => {
  110 + this.isLongClick = true;
  111 + this.$emit('longClick', this.item.id);
  112 + }, 1000);
  113 + },
  114 + mouseup() {
  115 + clearTimeout(this.pressTimer);
  116 + setTimeout(() => {
  117 + this.isLongClick = false;
  118 + }, 100);
  119 + },
  120 + },
  121 +};
  122 +</script>
  123 +
  124 +<style scoped lang="scss">
  125 +.payment-card {
  126 + background-color: $color-white;
  127 + color: $color-text;
  128 + padding: $padding-sm;
  129 + margin-bottom: $padding-sm;
  130 + border-radius: $radius-md;
  131 + box-shadow: $shadow-normal;
  132 + font-size: $font-md;
  133 + .title {
  134 + padding-bottom: $padding-sm;
  135 + display: flex;
  136 + justify-content: space-between;
  137 + .code {
  138 + font-weight: 500;
  139 + font-size: 30upx;
  140 + color: #2b2a27;
  141 + line-height: 34upx;
  142 + text-align: left;
  143 + font-style: normal;
  144 + }
  145 + border-bottom: 1px solid $color-border;
  146 + }
  147 + .title-sub {
  148 + margin-top: $padding-sm;
  149 + font-weight: 400;
  150 + font-size: 26upx;
  151 + color: #5d5d5d;
  152 + line-height: 37upx;
  153 + text-align: left;
  154 + font-style: normal;
  155 + }
  156 + .item {
  157 + margin-top: $padding-sm;
  158 + display: flex;
  159 + .label {
  160 + width: 170upx;
  161 + font-weight: 400;
  162 + font-size: 28upx;
  163 + color: #999999;
  164 + line-height: 28upx;
  165 + text-align: left;
  166 + font-style: normal;
  167 + }
  168 + .content {
  169 + font-weight: 400;
  170 + font-size: 28upx;
  171 + color: #2b2a27;
  172 + line-height: 28upx;
  173 + text-align: left;
  174 + font-style: normal;
  175 + text + text {
  176 + margin-left: $padding-sm;
  177 + }
  178 + .amount {
  179 + color: #ff4f3b;
  180 + }
  181 + &--warning {
  182 + color: #f52723;
  183 + font-size: 20rpx;
  184 + margin-left: 20upx;
  185 + padding-left: 10upx;
  186 + padding-right: 10upx;
  187 + border-radius: 8upx;
  188 + border: 2rpx solid #f52723;
  189 + }
  190 + }
  191 + }
  192 +}
  193 +</style>
pages/payPlan/filter.vue 0 → 100644
@@ -0,0 +1,140 @@ @@ -0,0 +1,140 @@
  1 +<template>
  2 + <Page name="payPlan-filter" flank>
  3 + <template #content>
  4 + <u-form :model="searchForm" ref="uForm" labelWidth="100">
  5 + <view class="card">
  6 + <u-form-item label="订单号"><u-input v-model="searchForm.orderCode" placeholder="请输入" /></u-form-item>
  7 + </view>
  8 + <view class="card">
  9 + <u-form-item label="司机姓名"><u-input v-model="searchForm.driverName" placeholder="请输入" /></u-form-item>
  10 + </view>
  11 + <view class="card">
  12 + <u-form-item label="司机手机号"><u-input v-model="searchForm.driverMobile" placeholder="请输入" /></u-form-item>
  13 + </view>
  14 + <view class="card">
  15 + <u-form-item label="车牌号"><u-input v-model="searchForm.vehicleLicenseNum" placeholder="请输入" /></u-form-item>
  16 + </view>
  17 + <view class="card">
  18 + <u-form-item label="存在未处理异常" labelWidth="130">
  19 + <u-radio-group v-model="searchForm.unHandledExceptionFlag">
  20 + <u-radio v-for="(item, index) in radioList" :key="index" :name="item.value">
  21 + {{ item.text }}
  22 + </u-radio>
  23 + </u-radio-group>
  24 + </u-form-item>
  25 + </view>
  26 + </u-form>
  27 + </template>
  28 + <template #footer>
  29 + <view class="footer">
  30 + <view class="reset" @click="resetChange">重置</view>
  31 + <view class="inquiry" @click="inquiryChange">查询</view>
  32 + </view>
  33 + </template>
  34 + </Page>
  35 +</template>
  36 +
  37 +<script>
  38 +import { urlParam } from '@/utils/param';
  39 +export default {
  40 + name: 'payPlanFilter',
  41 + props: {
  42 + searchModel: {
  43 + type: Object,
  44 + default: () => {
  45 + return {};
  46 + },
  47 + },
  48 + },
  49 + data() {
  50 + return {
  51 + radioList: [
  52 + { text: '是', value: 'true' },
  53 + { text: '否', value: 'false' },
  54 + ],
  55 + searchForm: {
  56 + orderCode: '', // 订单号
  57 + driverName: '',
  58 + driverMobile: '', //
  59 + vehicleLicenseNum: '',
  60 + unHandledExceptionFlag: '', // 存在异常
  61 + },
  62 + };
  63 + },
  64 + onLoad(option) {
  65 + Object.keys(option).forEach(i => {
  66 + this.searchForm[i] = option[i];
  67 + });
  68 + },
  69 + methods: {
  70 + // 重置
  71 + resetChange() {
  72 + this.searchForm = {
  73 + orderCode: '', // 订单号
  74 + startCityCode: '',
  75 + startCityName: '',
  76 + endCityCode: '',
  77 + endCityName: '',
  78 + projectCode: '',
  79 + projectName: '',
  80 + feeType: '',
  81 + feeTypeName: '',
  82 + driverName: '',
  83 + driverMobile: '', //
  84 + vehicleLicenseNum: '',
  85 + unHandledExceptionFlag: '', // 存在异常
  86 + };
  87 + },
  88 + // 查询
  89 + inquiryChange() {
  90 + this.getOpenerEventChannel().emit('refreshData', this.searchForm);
  91 + setTimeout(() => uni.navigateBack(), 500);
  92 + },
  93 + },
  94 +};
  95 +</script>
  96 +
  97 +<style lang="scss">
  98 +.page-payPlan-filter {
  99 + &__content {
  100 + .card {
  101 + background-color: $color-white;
  102 + padding-left: $padding-xs;
  103 + padding-right: $padding-xs;
  104 + border-radius: $radius-md;
  105 + box-shadow: $shadow-normal;
  106 + margin-bottom: $padding-sm;
  107 + }
  108 + }
  109 + &__footer {
  110 + background: $color-white;
  111 + .footer {
  112 + display: flex;
  113 + justify-content: space-between;
  114 + .reset {
  115 + text-align: center;
  116 + width: 236upx;
  117 + height: 82upx;
  118 + line-height: 82upx;
  119 + margin-right: 20upx;
  120 + background: #dfebff;
  121 + border-radius: 14upx;
  122 + font-size: 30upx;
  123 + font-weight: 500;
  124 + color: $color-primary;
  125 + }
  126 + .inquiry {
  127 + text-align: center;
  128 + width: 450upx;
  129 + height: 82upx;
  130 + line-height: 82upx;
  131 + background: $color-primary;
  132 + border-radius: 14upx;
  133 + font-size: 30upx;
  134 + font-weight: 500;
  135 + color: #ffffff;
  136 + }
  137 + }
  138 + }
  139 +}
  140 +</style>
pages/payPlan/list.vue 0 → 100644
@@ -0,0 +1,532 @@ @@ -0,0 +1,532 @@
  1 +<template>
  2 + <Page name="settlement" flank>
  3 + <template #header>
  4 + <u-tabs :current="activeTab" :list="tabList" @click="onTabChange" :activeStyle="{ color: '#1E7B6B' }"> </u-tabs>
  5 + <view class="line"></view>
  6 + <view class="quick-tag">
  7 + <view class="quick-tag-group">
  8 + <view class="quick-tag-item" :class="searchForm.feeType ? 'active' : ''" @click="selectQuickTag({ key: 'feeType', value: searchForm.feeType })">
  9 + <text>{{ searchForm.feeTypeName || '款项类型' }}</text>
  10 + <view class="sx-img">
  11 + <image v-if="searchForm.feeType" class="sx-image" :src="formatImagePath('active-down')"></image>
  12 + <image v-else class="sx-image" :src="formatImagePath('down')"></image>
  13 + </view>
  14 + </view>
  15 + <view class="quick-tag-item" :class="searchForm.projectCode ? 'active' : ''" @click="selectQuickTag({ key: 'projectCode', value: searchForm.projectCode })">
  16 + <text>{{ searchForm.projectName || '所属项目' }}</text>
  17 + <view class="sx-img">
  18 + <image v-if="searchForm.projectCode" class="sx-image" :src="formatImagePath('active-down')"></image>
  19 + <image v-else class="sx-image" :src="formatImagePath('down')"></image>
  20 + </view>
  21 + </view>
  22 + <view class="quick-tag-item" :class="searchForm.startCityCode ? 'active' : ''" @click="selectQuickTag({ key: 'startCityCode', value: searchForm.startCityCode })">
  23 + <text>{{ searchForm.startCityName || '始发地' }}</text>
  24 + <view class="sx-img">
  25 + <image v-if="searchForm.startCityCode" class="sx-image" :src="formatImagePath('active-down')"></image>
  26 + <image v-else class="sx-image" :src="formatImagePath('down')"></image>
  27 + </view>
  28 + </view>
  29 + <view class="quick-tag-item" :class="searchForm.endCityCode ? 'active' : ''" @click="selectQuickTag({ key: 'endCityCode', value: searchForm.endCityCode })">
  30 + <text>{{ searchForm.endCityName || '目的地' }}</text>
  31 + <view class="sx-img">
  32 + <image v-if="searchForm.startCityCode" class="sx-image" :src="formatImagePath('active-down')"></image>
  33 + <image v-else class="sx-image" :src="formatImagePath('down')"></image>
  34 + </view>
  35 + </view>
  36 + </view>
  37 + <view class="quick-screen" @click="openFilter">
  38 + <image class="search-image" :src="formatImagePath('search')"></image>
  39 + </view>
  40 + </view>
  41 + </template>
  42 + <template #content>
  43 + <List ref="list" v-model="list" :api="orderAPI" @update:loading="e => (loading = e)" :verify="true">
  44 + <template v-for="(item, index) in list">
  45 + <card @payment="onePaymentPlanFun" @longClick="longClick" @chose="choseItemFun" :key="index" :item="item" :choseIds="selection" :choseMore="longClickFlag"></card>
  46 + </template>
  47 + <template #empty>
  48 + <Empty tips="暂无数据" />
  49 + </template>
  50 + </List>
  51 + </template>
  52 + <template v-if="longClickFlag">
  53 + <view class="foot-submit">
  54 + <view class="foot-but">
  55 + <view style="flex: 1">
  56 + <text style="color: #999999">已选中:</text>
  57 + <text class="color-red">{{ choseWaybillNum }}</text>
  58 + 个订单,
  59 + <text class="color-red">{{ selection.length }}</text>
  60 + 笔款项
  61 + </view>
  62 + <view class="but-view">
  63 + <u-button type="primary" size="small" @click="toPayUrl">去支付</u-button>
  64 + </view>
  65 + </view>
  66 + <u-safe-bottom></u-safe-bottom>
  67 + </view>
  68 + </template>
  69 + <u-popup :show="popShow" @close="popShow = false" closeable mode="center" :round="10">
  70 + <view class="popup">
  71 + <view class="title">支付信息确认</view>
  72 + <view class="alert"><u-icon name="error-circle" size="12"> </u-icon>列表长按可以批量选择支付哦~ </view>
  73 + <view>
  74 + <view class="row"><view class="text">订单号:</view>{{ payPlanForm.detail[0].orderCode }}</view>
  75 + <view class="row"><view class="text">车牌号:</view>{{ payPlanForm.detail[0].vehicleLicenseNum }}</view>
  76 + <view class="row"><view class="text">收款人:</view>{{ payPlanForm.detail[0].recAccountName }}{{ payPlanForm.detail[0].recMobile }}</view>
  77 + <view class="row"><view class="text">运费:</view>{{ payPlanForm.detail[0].feeAmount }}元</view>
  78 + <view class="row"><view class="text">服务费:</view>{{ payPlanForm.detail[0].serviceAmount }}元</view>
  79 + <view class="row"><view class="text">总额:</view>{{ payPlanForm.detail[0].payAmount }}元</view>
  80 + </view>
  81 + <view class="but">
  82 + <u-button @tap="popShow = false">取消</u-button>
  83 + <u-button type="primary" @tap="(popShow = false), (pwdShow = true)">继续支付</u-button>
  84 + </view>
  85 + </view>
  86 + </u-popup>
  87 + <u-popup :show="pwdShow" :closeable="false" mode="center" :round="10">
  88 + <view class="popup">
  89 + <view class="title">输入密码</view>
  90 + <view class="row">
  91 + <u-input v-model="pwdStr" type="password" input-align="center" placeholder="请输入支付密码"></u-input>
  92 + </view>
  93 + <view class="but">
  94 + <u-button @tap="(pwdShow = false), (popShow = true)">取消</u-button>
  95 + <u-button type="primary" @tap="onSubmit">确定支付</u-button>
  96 + </view>
  97 + </view>
  98 + </u-popup>
  99 + <u-toast ref="uToast"></u-toast>
  100 + </Page>
  101 +</template>
  102 +<script>
  103 +import { urlParam } from '@/utils/param';
  104 +import card from './card.vue';
  105 +import UFormItem from '../../uni_modules/uview-ui/components/u-form-item/u-form-item.vue';
  106 +import page from '@/mixins/page';
  107 +export default {
  108 + name: 'payPlan',
  109 + components: { UFormItem, card },
  110 + data() {
  111 + return {
  112 + longClickFlag: false,
  113 + pwdStr: '',
  114 + pwdShow: false,
  115 + loading: false,
  116 + popShow: false,
  117 + payPlanForm: {
  118 + oilRate: '',
  119 + payCount: '',
  120 + serviceRate: '',
  121 + totalFeeAmount: '',
  122 + totalPayAmount: '',
  123 + totalServiceAmount: '',
  124 + detail: [
  125 + {
  126 + customerOrderCode: '',
  127 + driverMobile: '',
  128 + driverName: '',
  129 + feeAmount: '',
  130 + feeType: '',
  131 + orderCode: '',
  132 + payAmount: '',
  133 + payCode: '',
  134 + recAccountName: '',
  135 + recMobile: '',
  136 + serviceAmount: '',
  137 + vehicleLicenseNum: '',
  138 + },
  139 + ],
  140 + },
  141 + searchForm: {
  142 + payStatus: '', // 支付状态
  143 + feeType: '', // 费用类型
  144 + feeTypeName: '', // 费用类型
  145 + projectCode: '',
  146 + projectName: '',
  147 + startCityCode: '',
  148 + startCityName: '',
  149 + endCityCode: '',
  150 + endCityName: '',
  151 + orderCode: '', // 订单号
  152 + driverName: '',
  153 + driverMobile: '', //
  154 + vehicleLicenseNum: '',
  155 + unHandledExceptionFlag: '', // 存在异常
  156 + },
  157 + activeTab: 0,
  158 + count: {},
  159 + list: [],
  160 + selection: [],
  161 + };
  162 + },
  163 + onPullDownRefresh() {
  164 + this.onSearch();
  165 + },
  166 + computed: {
  167 + tabList() {
  168 + let res = [
  169 + { name: '未支付', value: 'NOT_PAY', key: 'notPayCount' },
  170 + { name: '支付中', value: 'PAYING', key: 'payingCount' },
  171 + { name: '支付失败', value: 'PAY_FAILED', key: 'payFailedCount' },
  172 + { name: '支付成功', value: 'PAY_SUCCESS', key: 'paySuccessCount' },
  173 + ];
  174 + return Object.keys(this.count).length > 0
  175 + ? res.map(item => {
  176 + return { ...item, name: `${item.name}(${this.count[item.key] || 0})`, disabled: this.loading };
  177 + })
  178 + : res;
  179 + },
  180 + choseWaybillNum() {
  181 + if (this.list.length === 0 || this.selection.length === 0) {
  182 + return 0;
  183 + } else {
  184 + let orderList = this.list.filter(i => this.selection.includes(i.id)).map(i2 => i2.orderCode);
  185 + return new Set(orderList).size;
  186 + }
  187 + },
  188 + },
  189 + methods: {
  190 + onTabChange({ index }) {
  191 + if (this.loading) {
  192 + return;
  193 + }
  194 + this.activeTab = index;
  195 + this.list = [];
  196 + this.onSearch();
  197 + },
  198 + orderAPI(params) {
  199 + let format = {
  200 + ...this.searchForm,
  201 + payStatus: this.tabList[this.activeTab].value,
  202 + };
  203 + this.getAggregateType(format);
  204 + return uni.$u.api.paymentPlan.page({
  205 + ...format,
  206 + ...params,
  207 + });
  208 + },
  209 + // 获取聚合数量
  210 + getAggregateType() {
  211 + uni.$u.api.paymentPlan.getCount({}).then(res => {
  212 + this.count = res?.result || {};
  213 + });
  214 + },
  215 + selectQuickTag({ key, value }) {
  216 + this.searchForm = Object.assign(this.searchForm, { [key]: value });
  217 + if (key == 'feeType') {
  218 + uni.$once('select-dict', option => {
  219 + this.searchForm.feeType = option.valueCode;
  220 + this.searchForm.feeTypeName = option.valueName;
  221 + this.onSearch();
  222 + });
  223 + uni.navigateTo({
  224 + url: `/pages/global/search-dict${urlParam({
  225 + title: '款项类型',
  226 + dict: 'ONLINE_FREIGHT_ORDER_FEE_TYPE',
  227 + })}`,
  228 + });
  229 + } else if (key == 'startCityCode') {
  230 + uni.$once('select-city', option => {
  231 + this.searchForm.startCityCode = option.code;
  232 + this.searchForm.startCityName = option.shortName;
  233 + this.onSearch();
  234 + });
  235 + uni.navigateTo({ url: '/pages/global/search-city' });
  236 + } else if (key == 'endCityCode') {
  237 + uni.$once('select-city', option => {
  238 + this.searchForm.endCityCode = option.code;
  239 + this.searchForm.endCityName = option.shortName;
  240 + this.onSearch();
  241 + });
  242 + uni.navigateTo({ url: '/pages/global/search-city' });
  243 + } else if (key == 'projectCode') {
  244 + uni.$once('select-common', option => {
  245 + this.searchForm.projectCode = option.code;
  246 + this.searchForm.projectName = option.name;
  247 + this.onSearch();
  248 + });
  249 + uni.navigateTo({
  250 + url: `/pages/global/search-common${urlParam({
  251 + mode: 'select',
  252 + url: 'projectCode',
  253 + title: '项目',
  254 + label: 'name',
  255 + value: '',
  256 + })}`,
  257 + });
  258 + }
  259 + },
  260 + // 筛选
  261 + openFilter() {
  262 + uni.navigateTo({
  263 + url: `/pages/payPlan/filter${urlParam(this.searchForm)}`,
  264 + events: {
  265 + refreshData: option => {
  266 + this.searchForm = { ...this.searchForm, ...option };
  267 + this.onSearch();
  268 + },
  269 + },
  270 + });
  271 + },
  272 + choseItemFun(id) {
  273 + if (this.longClickFlag) {
  274 + if (this.selection.includes(id)) {
  275 + this.selection = this.selection.filter(i => i !== id);
  276 + } else {
  277 + this.selection.push(id);
  278 + }
  279 + if (this.selection.length === 0) {
  280 + this.longClickFlag = false;
  281 + }
  282 + }
  283 + },
  284 + longClick(id) {
  285 + this.selection = [id];
  286 + this.longClickFlag = true;
  287 + },
  288 + onePaymentPlanFun(id) {
  289 + uni.showLoading({ title: '加载中' });
  290 + this.selection = [id];
  291 + uni.$u.api.paymentPlan
  292 + .getApplyDetailByIds([id])
  293 + .then(res => {
  294 + uni.hideLoading();
  295 + this.payPlanForm = res.result || {};
  296 + this.popShow = true;
  297 + })
  298 + .catch(res => {
  299 + uni.hideLoading();
  300 + this.$refs.uToast.default(res);
  301 + });
  302 + },
  303 + onSubmit() {
  304 + if (this.loading) {
  305 + return;
  306 + }
  307 + if (!this.pwdStr) {
  308 + uni.showToast({ title: '支付密码不能为空' });
  309 + return;
  310 + }
  311 + this.loading = true;
  312 + uni.$u.api.paymentPlan
  313 + .checkPayPassword({ payPassword: this.pwdStr })
  314 + .then(res => {
  315 + uni.$u.api.paymentPlan.pay(this.selection).then(res => {
  316 + this.loading = false;
  317 + this.pwdStr = '';
  318 + uni.showToast({ title: '提交成功' });
  319 + this.search();
  320 + this.pwdShow = false;
  321 + this.popShow = false;
  322 + });
  323 + })
  324 + .catch(() => {
  325 + this.loading = false;
  326 + });
  327 + },
  328 + toPayUrl() {
  329 + uni.showLoading({ title: '加载中' });
  330 + let selection = this.selection;
  331 + uni.$u.api.paymentPlan
  332 + .getApplyDetailByIds(this.selection)
  333 + .then(resp => {
  334 + uni.navigateTo({
  335 + url: '/pages/payPlan/paySubmit',
  336 + events: {
  337 + refreshData: () => {
  338 + this.selection = [];
  339 + this.longClickFlag = false;
  340 + this.onSearch();
  341 + },
  342 + },
  343 + success(res) {
  344 + res.eventChannel.emit('payPlanDate', { form: resp.result, selection });
  345 + },
  346 + });
  347 + })
  348 + .catch(res => {
  349 + this.$refs.uToast.default(res);
  350 + })
  351 + .finally(() => {
  352 + uni.hideLoading();
  353 + });
  354 + },
  355 + },
  356 +};
  357 +</script>
  358 +<style lang="scss">
  359 +.page-settlement {
  360 + &__header {
  361 + padding: 0 !important;
  362 +
  363 + .line {
  364 + height: 1rpx;
  365 + background: #f6f6f6;
  366 + position: relative;
  367 + top: -5rpx;
  368 + }
  369 +
  370 + .quick-tag {
  371 + display: flex;
  372 + padding: 15upx 22upx;
  373 + box-sizing: border-box;
  374 + position: relative;
  375 +
  376 + .quick-cover {
  377 + width: 25upx;
  378 + height: 90upx;
  379 + position: absolute;
  380 + right: 122upx;
  381 + top: 0;
  382 +
  383 + .cover-image {
  384 + width: 100%;
  385 + height: 100%;
  386 + }
  387 + }
  388 +
  389 + .quick-screen {
  390 + width: 100upx;
  391 + display: flex;
  392 + align-items: center;
  393 + justify-content: center;
  394 +
  395 + .search-image {
  396 + width: 42upx;
  397 + height: 42upx;
  398 + }
  399 + }
  400 +
  401 + .quick-tag-group {
  402 + flex: 1;
  403 + display: flex;
  404 + align-items: center;
  405 + background-color: #fff;
  406 + padding-left: $padding-xs !important;
  407 + padding-right: $padding-xs !important;
  408 + overflow-y: auto;
  409 +
  410 + .quick-tag-item {
  411 + flex-shrink: 0;
  412 + min-width: 158upx;
  413 + height: 58upx;
  414 + background: #f6f6f6;
  415 + border-radius: 8upx;
  416 + font-size: 28upx;
  417 + font-weight: 400;
  418 + color: #2b2a27;
  419 + display: flex;
  420 + align-items: center;
  421 + justify-content: center;
  422 + padding: 0 10upx;
  423 + box-sizing: border-box;
  424 +
  425 + &:not(:last-child) {
  426 + margin-right: 18upx;
  427 + }
  428 +
  429 + &.active {
  430 + background: #ffffff;
  431 + border-radius: 8upx;
  432 + border: 2upx solid #2673fb;
  433 + font-size: 28upx;
  434 + font-family:
  435 + PingFangSC,
  436 + PingFang SC;
  437 + font-weight: 400;
  438 + color: #2673fb;
  439 + }
  440 +
  441 + .sx-img {
  442 + height: 12upx;
  443 + width: 14upx;
  444 + position: relative;
  445 + margin-left: 12upx;
  446 +
  447 + .sx-image {
  448 + width: 100%;
  449 + height: 100%;
  450 + position: absolute;
  451 + top: 0;
  452 + left: 0;
  453 + }
  454 + }
  455 + }
  456 +
  457 + .z-dropdown__text .text {
  458 + word-break: keep-all;
  459 + }
  460 + }
  461 + }
  462 + }
  463 + .add-order {
  464 + right: 34upx;
  465 + bottom: 34upx;
  466 + height: 106upx;
  467 + width: 106upx;
  468 + position: fixed;
  469 + .sx-image {
  470 + width: 100%;
  471 + height: 100%;
  472 + position: absolute;
  473 + top: 0;
  474 + left: 0;
  475 + }
  476 + }
  477 + .popup {
  478 + padding-left: $padding-md;
  479 + padding-right: $padding-md;
  480 + width: 70vw;
  481 + .title {
  482 + padding-top: $padding-xs;
  483 + padding-bottom: $padding-xs;
  484 + display: flex;
  485 + align-content: center;
  486 + justify-content: center;
  487 + font-weight: 400;
  488 + font-size: 32rpx;
  489 + color: #2b2a27;
  490 + line-height: 45px;
  491 + text-align: left;
  492 + font-style: normal;
  493 + }
  494 + .alert {
  495 + color: orange;
  496 + font-size: 24rpx;
  497 + display: flex;
  498 + padding-bottom: 20rpx;
  499 + }
  500 + .row {
  501 + display: flex;
  502 + padding: 10upx 0;
  503 + .text {
  504 + width: 130rpx;
  505 + }
  506 + }
  507 + .but {
  508 + margin-top: $padding-md;
  509 + display: flex;
  510 + gap: 20px;
  511 + }
  512 + }
  513 + &__content {
  514 + padding-bottom: 100px !important;
  515 + }
  516 + .foot-submit {
  517 + position: fixed;
  518 + width: 100vw;
  519 + bottom: 0;
  520 + background: white;
  521 + .foot-but {
  522 + display: flex;
  523 + align-items: center;
  524 + justify-content: space-between;
  525 + padding: 10px;
  526 + .but-view {
  527 + max-width: 100px;
  528 + }
  529 + }
  530 + }
  531 +}
  532 +</style>
pages/payPlan/paySubmit.vue 0 → 100644
@@ -0,0 +1,239 @@ @@ -0,0 +1,239 @@
  1 +<template>
  2 + <Page name="paySubmit" flank>
  3 + <template #header>
  4 + <view class="row">
  5 + <view class="label">支付数量:</view>
  6 + <view>合计运费:{{ form.totalFeeAmount }},合计服务费:{{ form.totalServiceAmount }},支付总额:{{ form.totalPayAmount }}</view>
  7 + </view>
  8 + <view class="row" style="justify-content: space-between; color: #999999">
  9 + <view>服务费率:{{ form.serviceRate }}</view>
  10 + <view>油卡返点率:{{ form.oilRate }}</view>
  11 + </view>
  12 + </template>
  13 + <template #content>
  14 + <view class="card" v-for="(item, key) in form.detail" :key="key">
  15 + <view class="item">
  16 + <view class="label"><render-dict dict="ONLINE_FREIGHT_ORDER_FEE_TYPE" :value="item.feeType"></render-dict></view>
  17 + <view class="content"
  18 + ><text class="amount">¥{{ item.feeAmount }}</text></view
  19 + >
  20 + </view>
  21 + <view class="item">
  22 + <view class="label">服务费</view>
  23 + <view class="content"
  24 + ><text class="amount">¥{{ item.serviceAmount }}</text></view
  25 + >
  26 + </view>
  27 + <view class="item">
  28 + <view class="label">支付总额</view>
  29 + <view class="content"
  30 + ><text class="amount">¥{{ item.payAmount }}</text></view
  31 + >
  32 + </view>
  33 + <view class="item">
  34 + <view class="label">承运司机</view>
  35 + <view class="content">{{ item.driverName }}{{ item.driverMobile }}</view>
  36 + </view>
  37 + <view class="item">
  38 + <view class="label">收款人</view>
  39 + <view class="content">{{ item.recAccountName }}{{ item.recMobile }}</view>
  40 + </view>
  41 + <view class="item">
  42 + <view class="label">承运车辆</view>
  43 + <view class="content">{{ item.vehicleLicenseNum }}</view>
  44 + </view>
  45 + <view class="item">
  46 + <view class="label">订单号</view>
  47 + <view class="content" style="color: #0066ff">{{ item.orderCode }}</view>
  48 + </view>
  49 + </view>
  50 + </template>
  51 + <template #footer>
  52 + <u-button :loading="loading" type="primary" @tap="pwdShow = true">继续支付</u-button>
  53 + </template>
  54 + <u-popup :show="pwdShow" :closeable="false" mode="center" :round="10">
  55 + <view class="popup">
  56 + <view class="title">输入密码</view>
  57 + <view class="row">
  58 + <u-input v-model="pwdStr" type="password" input-align="center" placeholder="请输入支付密码"></u-input>
  59 + </view>
  60 + <view class="but">
  61 + <u-button @tap="pwdShow = false">取消</u-button>
  62 + <u-button :loading="loading" type="primary" @tap="onSubmit">确定支付</u-button>
  63 + </view>
  64 + </view>
  65 + </u-popup>
  66 + </Page>
  67 +</template>
  68 +<script>
  69 +export default {
  70 + name: 'paySubmit',
  71 + data() {
  72 + return {
  73 + loading: false,
  74 + pwdShow: false,
  75 + pwdStr: '',
  76 + selection: [],
  77 + form: {
  78 + oilRate: '',
  79 + payCount: '',
  80 + serviceRate: '',
  81 + totalFeeAmount: '',
  82 + totalPayAmount: '',
  83 + totalServiceAmount: '',
  84 + detail: [
  85 + {
  86 + customerOrderCode: '',
  87 + driverMobile: '',
  88 + driverName: '',
  89 + feeAmount: '',
  90 + feeType: '',
  91 + orderCode: '',
  92 + payAmount: '',
  93 + payCode: '',
  94 + recAccountName: '',
  95 + recMobile: '',
  96 + serviceAmount: '',
  97 + vehicleLicenseNum: '',
  98 + },
  99 + ],
  100 + },
  101 + };
  102 + },
  103 + onLoad() {
  104 + const eventChannel = this.getOpenerEventChannel();
  105 + eventChannel.on('payPlanDate', data => {
  106 + this.form = data.form || {};
  107 + this.selection = data.selection || [];
  108 + });
  109 + },
  110 + methods: {
  111 + onSubmit() {
  112 + if (this.loading) {
  113 + return;
  114 + }
  115 + if (!this.pwdStr) {
  116 + uni.showToast({ title: '支付密码不能为空' });
  117 + return;
  118 + }
  119 + this.loading = true;
  120 + uni.$u.api.paymentPlan
  121 + .checkPayPassword({ payPassword: this.pwdStr })
  122 + .then(res => {
  123 + uni.$u.api.paymentPlan
  124 + .pay(this.selection)
  125 + .then(res => {
  126 + this.pwdShow = false;
  127 + uni.showToast({ title: '提交成功' });
  128 + this.getOpenerEventChannel().emit('refreshData');
  129 + setTimeout(() => uni.navigateBack(), 500);
  130 + })
  131 + .catch(() => {
  132 + this.loading = false;
  133 + });
  134 + })
  135 + .catch(() => {
  136 + this.loading = false;
  137 + });
  138 + },
  139 + },
  140 +};
  141 +</script>
  142 +<style lang="scss">
  143 +.page-paySubmit {
  144 + &__header {
  145 + padding: 0 !important;
  146 + .row {
  147 + margin: 10px;
  148 + display: flex;
  149 + .label {
  150 + width: 140rpx;
  151 + }
  152 + }
  153 + }
  154 + &__content {
  155 + .card {
  156 + background-color: $color-white;
  157 + color: $color-text;
  158 + padding: $padding-base $padding-sm;
  159 + margin-bottom: $padding-sm;
  160 + border-radius: $radius-md;
  161 + box-shadow: $shadow-normal;
  162 + font-size: $font-md;
  163 + .item {
  164 + margin: $padding-sm 0;
  165 + display: flex;
  166 + justify-content: space-between;
  167 + .label {
  168 + width: 170upx;
  169 + font-weight: 400;
  170 + font-size: 28upx;
  171 + color: #999999;
  172 + line-height: 28upx;
  173 + text-align: left;
  174 + font-style: normal;
  175 + }
  176 + .content {
  177 + font-weight: 400;
  178 + font-size: 28upx;
  179 + color: #2b2a27;
  180 + line-height: 28upx;
  181 + text-align: right;
  182 + font-style: normal;
  183 + .amount {
  184 + color: #ff4f3b;
  185 + }
  186 + &--warning {
  187 + color: #f52723;
  188 + font-size: 20rpx;
  189 + margin-left: 20upx;
  190 + padding-left: 10upx;
  191 + padding-right: 10upx;
  192 + border-radius: 8upx;
  193 + border: 2rpx solid #f52723;
  194 + }
  195 + }
  196 + }
  197 + }
  198 + }
  199 + &__footer {
  200 + background-color: $color-white;
  201 + }
  202 + .popup {
  203 + padding-left: $padding-md;
  204 + padding-right: $padding-md;
  205 + width: 70vw;
  206 + .title {
  207 + padding-top: $padding-xs;
  208 + padding-bottom: $padding-xs;
  209 + display: flex;
  210 + align-content: center;
  211 + justify-content: center;
  212 + font-weight: 400;
  213 + font-size: 32rpx;
  214 + color: #2b2a27;
  215 + line-height: 45px;
  216 + text-align: left;
  217 + font-style: normal;
  218 + }
  219 + .alert {
  220 + color: orange;
  221 + font-size: 24rpx;
  222 + display: flex;
  223 + padding-bottom: 20rpx;
  224 + }
  225 + .row {
  226 + display: flex;
  227 + padding: 10upx 0;
  228 + .text {
  229 + width: 130rpx;
  230 + }
  231 + }
  232 + .but {
  233 + margin-top: $padding-md;
  234 + display: flex;
  235 + gap: 20px;
  236 + }
  237 + }
  238 +}
  239 +</style>