Sfoglia il codice sorgente

支付宝接入自定义金额支付

mht 1 mese fa
parent
commit
c53e18b6e5
2 ha cambiato i file con 126 aggiunte e 12 eliminazioni
  1. 71 7
      src/views/Recharge.vue
  2. 55 5
      src/views/Search.vue

+ 71 - 7
src/views/Recharge.vue

@@ -41,7 +41,7 @@
       
       <div class="recharge-grid">
         <div 
-          v-for="(item, index) in rechargeOptions" 
+          v-for="(item, index) in rechargeOptionsWithCustom" 
           :key="index"
           class="recharge-item"
           :class="{ active: selectedRecharge === index }"
@@ -50,10 +50,26 @@
           <div class="diamond-icon">
             <img src="@/assets/images/recharge_zuanshi.png" alt="钻石" class="diamond-img" />
           </div>
-          <div class="recharge-amount">{{ item.amount }}</div>
-          <div class="recharge-price">¥{{ item.price }}</div>
+          <template v-if="!item.isCustom">
+            <div class="recharge-amount">{{ item.amount }}</div>
+            <div class="recharge-price">¥{{ item.price }}</div>
+          </template>
+          <template v-else>
+            <div class="recharge-amount">自定义金额</div>
+            <div class="recharge-price">点击输入</div>
+          </template>
         </div>
       </div>
+
+      <div v-if="isCustomSelected" class="custom-input">
+        <van-field
+          v-model="customAmount"
+          type="number"
+          input-align="center"
+          placeholder="请输入自定义金额(元)"
+          clearable
+        />
+      </div>
     </div>
     
     <!-- 支付方式 -->
@@ -132,12 +148,22 @@ export default {
       paymentMethod: 'alipay',
       isLoading: false,
       agreementChecked: false,
-      agreementVisible: false
+      agreementVisible: false,
+      // 自定义金额
+      customAmount: ''
     }
   },
   computed: {
     selectedRechargeOption() {
-      return this.rechargeOptions[this.selectedRecharge] || null
+      return this.rechargeOptionsWithCustom[this.selectedRecharge] || null
+    },
+    // 显示列表 = 产品列表 + 自定义
+    rechargeOptionsWithCustom() {
+      return [...(this.rechargeOptions || []), { isCustom: true }]
+    },
+    // 是否选择了自定义
+    isCustomSelected() {
+      return this.selectedRecharge === this.rechargeOptionsWithCustom.length - 1
     }
   },
   created() {
@@ -239,8 +265,17 @@ export default {
         this.$toast('请阅读并同意充值协议')
         return
       }
+
+      // 自定义金额校验
+      if (this.isCustomSelected) {
+        const amountNumber = Number(this.customAmount)
+        if (!this.customAmount || Number.isNaN(amountNumber) || amountNumber <= 0) {
+          this.$toast('请输入有效的自定义金额')
+          return
+        }
+      }
       
-      const selectedOption = this.rechargeOptions[this.selectedRecharge]
+      const selectedOption = this.selectedRechargeOption
       
       // 使用二次确认弹窗
       this.$dialog.confirm({
@@ -287,7 +322,12 @@ export default {
         // 构建支付参数
         const payData = {
           userId: this.userInfo.id,
-          productId: product.id
+          productId: product && product.isCustom ? 1018 : product.id
+        }
+        
+        // 自定义金额时追加 amount
+        if (product && product.isCustom) {
+          payData.amount = Number(this.customAmount)
         }
         
         // 调用支付宝H5支付接口
@@ -295,6 +335,25 @@ export default {
         this.$toast.clear()
         this.isLoading = false
         
+        // 优先尝试解析服务端 JSON 错误并提示
+        try {
+          if (typeof res === 'string') {
+            const trimmed = res.trim()
+            if (trimmed.startsWith('{') || trimmed.startsWith('[')) {
+              const json = JSON.parse(trimmed)
+              if (json && typeof json === 'object' && json.code !== undefined && json.code !== 200) {
+                this.$toast.fail(json.message || '支付请求失败')
+                return
+              }
+            }
+          } else if (res && typeof res === 'object' && res.code !== undefined && res.code !== 200) {
+            this.$toast.fail(res.message || '支付请求失败')
+            return
+          }
+        } catch (e) {
+          // 忽略解析错误,继续后续流程
+        }
+        
         // 处理HTML表单响应
         if (typeof res === 'string' && res.includes('<form')) {
           // 创建一个div来放置表单
@@ -559,6 +618,11 @@ export default {
   color: #666;
 }
 
+.custom-input {
+  margin-top: 8px;
+  padding: 0 2px;
+}
+
 /* 支付方式样式 */
 .payment-section {
   padding: 0 8px;

+ 55 - 5
src/views/Search.vue

@@ -33,7 +33,7 @@
       
       <div class="recharge-grid">
         <div 
-          v-for="(item, index) in coinOptions" 
+          v-for="(item, index) in coinOptionsWithCustom" 
           :key="index"
           class="recharge-item"
           :class="{ active: selectedRecharge === index }"
@@ -42,10 +42,26 @@
           <div class="diamond-icon">
             <img src="@/assets/images/recharge_zuanshi.png" alt="钻石" class="diamond-img" />
           </div>
-          <div class="recharge-amount">{{ item.amount }}</div>
-          <div class="recharge-price">¥{{ item.price }}</div>
+          <template v-if="!item.isCustom">
+            <div class="recharge-amount">{{ item.amount }}</div>
+            <div class="recharge-price">¥{{ item.price }}</div>
+          </template>
+          <template v-else>
+            <div class="recharge-amount">自定义金额</div>
+            <div class="recharge-price">点击输入</div>
+          </template>
         </div>
       </div>
+
+      <div v-if="isCustomSelected" class="custom-input">
+        <van-field
+          v-model="customAmount"
+          type="number"
+          input-align="center"
+          placeholder="请输入自定义金额(元)"
+          clearable
+        />
+      </div>
     </div>
     
     <!-- 支付方式 -->
@@ -119,13 +135,28 @@ export default {
       selectedRecharge: 0,
       paymentMethod: 'alipay',
       agreementChecked: false,
-      agreementVisible: false
+      agreementVisible: false,
+      // 自定义金额
+      customAmount: ''
     }
   },
   created() {
     // 获取产品列表
     this.fetchProductList()
   },
+  computed: {
+    selectedRechargeOption() {
+      return this.coinOptionsWithCustom[this.selectedRecharge] || null
+    },
+    // 显示列表 = 产品列表 + 自定义
+    coinOptionsWithCustom() {
+      return [...(this.coinOptions || []), { isCustom: true }]
+    },
+    // 是否选择了自定义
+    isCustomSelected() {
+      return this.selectedRecharge === this.coinOptionsWithCustom.length - 1
+    }
+  },
   methods: {
     // 获取产品列表
     async fetchProductList() {
@@ -208,13 +239,27 @@ export default {
         this.$toast('请阅读并同意充值协议')
         return
       }
+
+      // 自定义金额校验
+      if (this.isCustomSelected) {
+        const amountNumber = Number(this.customAmount)
+        if (!this.customAmount || Number.isNaN(amountNumber) || amountNumber <= 0) {
+          this.$toast('请输入有效的自定义金额')
+          return
+        }
+      }
+      
+      const selectedOption = this.selectedRechargeOption
+      const priceToShow = selectedOption && selectedOption.isCustom
+        ? (Number(this.customAmount) || 0)
+        : (selectedOption?.price || 0)
       
       // 使用二次确认弹窗
       this.$dialog.confirm({
         title: '支付确认',
         message: `
           <div class="confirm-dialog-content">
-            <div class="confirm-price">¥${this.coinOptions[this.selectedRecharge]?.price || 0}</div>
+            <div class="confirm-price">¥${priceToShow}</div>
             <div class="confirm-tip">请核实并确认ID是否正确,请提防:</div>
             <div class="warning-list">
               <div class="warning-item">刷单赚取佣金</div>
@@ -447,6 +492,11 @@ export default {
   color: #666;
 }
 
+.custom-input {
+  margin-top: 8px;
+  padding: 0 2px;
+}
+
 /* 支付方式样式 */
 .payment-section {
   padding: 0 8px;