多租户商城-商户小程序端
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

387 lines
9.7 KiB

2 years ago
  1. <!--
  2. * @FileDescription: 阿里花呗分期支付
  3. * @Author: kahu
  4. * @Date: 2022/11/21
  5. * @LastEditors: kahu
  6. * @LastEditTime: 2022/11/21
  7. -->
  8. <template>
  9. <view class="ali-hb-pay-content">
  10. <u-popup
  11. class="pay-type-popup"
  12. v-model="showPopup"
  13. mode="bottom"
  14. border-radius="14"
  15. close-icon-pos="top-right"
  16. close-icon-size="20"
  17. >
  18. <view class="pay-type-item">
  19. <radio-group
  20. @change="payTypeChange"
  21. v-model="flowerObj.paymentMode"
  22. >
  23. <view class="pay-type-radio">
  24. <view class="pay-type-img">
  25. <img
  26. class="pay-type-img-inner"
  27. src="https://ceres.zkthink.com/static/images/alipay.png"
  28. />
  29. </view>
  30. <label class="pay-type-label">支付宝支付</label>
  31. <radio
  32. class="pay-type-radio-item"
  33. style="transform:scale(0.7)"
  34. :checked="flowerObj.paymentMode === '2'"
  35. value="2"
  36. />
  37. </view>
  38. <view class="pay-type-radio">
  39. <view class="pay-type-img">
  40. <img
  41. class="pay-type-img-inner"
  42. src="https://ceres.zkthink.com/static/images/huabei.png"
  43. />
  44. </view>
  45. <label class="pay-type-label">花呗分期</label>
  46. <radio
  47. class="pay-type-radio-item"
  48. style="transform:scale(0.7)"
  49. :disabled="totalPrice < 0.03"
  50. :checked="flowerObj.paymentMode === '3'"
  51. value="3"
  52. />
  53. </view>
  54. </radio-group>
  55. <view class="huabei-detail" v-if="flowerObj.paymentMode==='3'">
  56. <radio-group
  57. @change="handleChangePeriods"
  58. v-model="flowerObj.hbByStagesPeriods"
  59. >
  60. <view class="period-radio" v-for="stages in flowerObj.hbByStagesList">
  61. <view class="period-amount">
  62. <label class="period-each"> {{ stages.price }}x{{ stages.numberOfStages }}</label>
  63. <label class="period-each-charge">手续费{{ stages.serviceCharge}}/</label>
  64. </view>
  65. <radio
  66. class="period-type-radio-item"
  67. style="transform:scale(0.7)"
  68. :disabled="stages.disabled"
  69. :checked="Number(flowerObj.hbByStagesPeriods) === stages.numberOfStages"
  70. :value="stages.numberOfStages+''"
  71. />
  72. </view>
  73. </radio-group>
  74. </view>
  75. </view>
  76. <view class="paytype-confirm">
  77. <view
  78. class="fenqi-total-amount"
  79. v-if="totalPrice >= 0.03 && flowerObj.paymentMode === '3'"
  80. >
  81. <label class="fenqi-all">分期总额 {{ totalPrice }}</label>
  82. <label class="charge-fee-all">手续费 {{ flowerObj.hbServiceChargeTotal }}</label>
  83. </view>
  84. <view
  85. class="fenqi-total-amount"
  86. v-if="flowerObj.paymentMode === '2'"
  87. >
  88. <label class="order-amount">订单总额 {{ totalPrice }}</label>
  89. </view>
  90. <view class="fenqi-confirm">
  91. <text
  92. class="btn active"
  93. @click="handleAliPayConfirm"
  94. >确认
  95. </text>
  96. </view>
  97. </view>
  98. </u-popup>
  99. </view>
  100. </template>
  101. <script>
  102. import NET from "../../utils/request";
  103. import API from "../../config/api";
  104. import { handleDoPay } from "../../utils/payUtil";
  105. export default {
  106. name: "AliHbPay",
  107. data() {
  108. return {
  109. // 花呗相关
  110. flowerObj: {
  111. paymentMode: '2',// 支付方式 1-微信支付 2-支付宝支付 3-花呗分期
  112. hbChargeType: 1,// 花呗手续费支付方式 1-商户支付 2-用户支付 后端接口返回
  113. hbByStagesPeriods: '-1', // 花呗分期期数 3 6 12
  114. hbByStagesList: [
  115. {
  116. rate: 0,
  117. price: 0,
  118. numberOfStages: 3,
  119. serviceCharge: 0,
  120. disabled: false
  121. },
  122. {
  123. rate: 0,
  124. price: 0,
  125. numberOfStages: 6,
  126. serviceCharge: 0,
  127. disabled: false
  128. },
  129. {
  130. rate: 0,
  131. price: 0,
  132. numberOfStages: 12,
  133. serviceCharge: 0,
  134. disabled: false
  135. }
  136. ], // 花呗手续费比例列表 【{3期},{6期},{12期}】
  137. hbServiceChargeTotal: 0, // 花呗支付总手续费
  138. },
  139. }
  140. },
  141. props:{
  142. totalPrice:{
  143. type:Number | String,
  144. default:()=>0
  145. },
  146. show:{
  147. type:Boolean,
  148. default:false
  149. },
  150. alipayInfo:{
  151. type:Object,
  152. default:()=>({})
  153. }
  154. },
  155. computed:{
  156. showPopup:{
  157. get(){
  158. return this.show
  159. },
  160. set(value){
  161. this.$emit('change',value)
  162. }
  163. }
  164. },
  165. model:{
  166. prop:'show',
  167. event:'change'
  168. },
  169. mounted(){
  170. this.getTheFlowerConfig()
  171. },
  172. methods: {
  173. /**
  174. * 获取花呗分期配置
  175. */
  176. async getTheFlowerConfig() {
  177. const {data} = await NET.request(API.GetHuabeiConfig, {}, 'GET')
  178. const {flowerObj} = this
  179. flowerObj.hbChargeType = data.huabeiChargeType
  180. // 如果后端返回的是用户支付手续费,设置费率信息
  181. if (data.huabeiChargeType === 2) {
  182. data.huabeiFeeRateList.forEach((rate, index) => {
  183. flowerObj.hbByStagesList[index].rate = rate
  184. })
  185. }
  186. },
  187. /**
  188. * 处理花呗期数选择
  189. * @param event
  190. */
  191. handleChangePeriods(event) {
  192. this.flowerObj.hbByStagesPeriods = event
  193. this.handleHbStagesAndPrice()
  194. },
  195. /**
  196. * 处理支付宝支付方式选择逻辑
  197. * @param event
  198. */
  199. payTypeChange(event) {
  200. const flowerObj = this.flowerObj
  201. const paymentMode = flowerObj.paymentMode = event.target.value;
  202. if (paymentMode === '2') {
  203. // 支付宝支付,取消分期选择
  204. flowerObj.hbByStagesPeriods = '-1'
  205. // 3 6 12 全部禁止
  206. flowerObj.hbByStagesList.map(item => {
  207. item.disabled = true
  208. })
  209. } else {
  210. // 分期支付,默认选三期
  211. flowerObj.hbByStagesPeriods = '3'
  212. }
  213. this.handleHbStagesAndPrice()
  214. },
  215. /**
  216. * 处理花呗价格和手续费显示
  217. */
  218. handleHbStagesAndPrice() {
  219. const {flowerObj, totalPrice} = this
  220. if (flowerObj.paymentMode !== '3') return
  221. flowerObj.hbByStagesList.forEach(stages => {
  222. // 根据价格填充每一期价格和手续费信息
  223. stages.price = ((totalPrice * (1 + stages.rate / 100)) / stages.numberOfStages).toFixed(2) // 每一期价格
  224. stages.serviceCharge = ((totalPrice * (stages.rate / 100)) / stages.numberOfStages).toFixed(2) // 每一期手续费
  225. // 计算总手续费
  226. if (stages.numberOfStages === Number(flowerObj.hbByStagesPeriods)) {
  227. flowerObj.hbServiceChargeTotal = (totalPrice * (stages.rate / 100)).toFixed(2)
  228. }
  229. // 处理允许分期的区间,公式为总价格要大于分期数/100
  230. if (this.totalPrice < stages.numberOfStages / 100) {
  231. stages.disabled = true
  232. }
  233. })
  234. },
  235. /**
  236. * 确认支付宝支付
  237. * @return {Promise<void>}
  238. */
  239. async handleAliPayConfirm() {
  240. const payInfo = Object.assign({}, this.alipayInfo, {
  241. 'paymentMode': this.flowerObj.paymentMode,
  242. 'huabeiPeriod': this.flowerObj.hbByStagesPeriods
  243. });
  244. await handleDoPay.call(this, payInfo)
  245. this.$emit('confirm',{
  246. 'paymentMode': this.flowerObj.paymentMode,
  247. 'huabeiPeriod': this.flowerObj.hbByStagesPeriods
  248. })
  249. }
  250. }
  251. }
  252. </script>
  253. <style
  254. lang="scss"
  255. scoped
  256. >
  257. .pay-type-item {
  258. .pay-type-radio {
  259. background-color: white;
  260. border-bottom: 1upx solid #EDEDED;
  261. margin-bottom: 20upx;
  262. padding: 24upx 20upx 24upx 20upx;
  263. .pay-type-img {
  264. display: inline-block;
  265. .pay-type-img-inner {
  266. width: 50upx;
  267. height: 50upx;
  268. vertical-align: middle;
  269. }
  270. }
  271. .pay-type-label {
  272. vertical-align: middle;
  273. margin-left: 30upx;
  274. }
  275. .pay-type-radio-item {
  276. float: right;
  277. margin-right: 20upx;
  278. width: 50upx;
  279. height: 50upx;
  280. }
  281. }
  282. .huabei-detail {
  283. margin-top: 20upx;
  284. .fenqi-wenzi {
  285. display: inline-block;
  286. margin-left: 64upx;
  287. }
  288. .fenqi-amount {
  289. display: block;
  290. margin-left: 64upx;
  291. margin-top: 14upx;
  292. color: #BABBBC;
  293. }
  294. .fenqi-charge-fee {
  295. float: right;
  296. margin-right: 68upx;
  297. color: #BABBBC;
  298. }
  299. .fenqi-modal {
  300. width: 40upx;
  301. height: 40upx;
  302. margin-left: 20upx;
  303. float: right;
  304. position: relative;
  305. top: -80upx;
  306. }
  307. }
  308. }
  309. .paytype-confirm {
  310. height: 120upx;
  311. padding: 0upx 108upx 0upx 32upx;
  312. .fenqi-all {
  313. display: inline-block;
  314. width: 100%;
  315. }
  316. .fenqi-total-amount {
  317. width: 65%;
  318. float: left;
  319. }
  320. .fenqi-confirm {
  321. float: right;
  322. width: 160upx;
  323. padding: 0upx 20upx;
  324. .btn {
  325. width: 216upx;
  326. height: 80upx;
  327. line-height: 80upx;
  328. border-radius: 40upx;
  329. font-size: 28upx;
  330. text-align: center;
  331. background: linear-gradient(90deg, rgba(255, 162, 0, 1), rgba(255, 121, 17, 1));
  332. color: #fff;
  333. display: inline-block;
  334. margin-right: 66upx;
  335. }
  336. }
  337. }
  338. .period-radio {
  339. margin: 30upx;
  340. padding-right: 100upx;
  341. width: 95%;
  342. border-bottom: 1px solid #EFEFEF;
  343. .period-amount {
  344. display: inline-block;
  345. .period-each-charge {
  346. display: inline-block;
  347. margin-top: 12upx;
  348. margin-left: 6upx;
  349. font-size: 26upx;
  350. color: #b7b7b7;
  351. margin-bottom: 13upx;
  352. }
  353. }
  354. .period-each {
  355. display: block;
  356. }
  357. .period-type-radio-item {
  358. float: right;
  359. }
  360. }
  361. </style>