pay.vue 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814
  1. <template>
  2. <!--
  3. H5 向供货商付款页(支付宝收款风格)
  4. 用途:扫码后输入金额并用支付宝支付;展示待结与余额入口
  5. -->
  6. <view class="pay-page">
  7. <!-- 收款方信息 -->
  8. <view class="pay-merchant">
  9. <view class="pay-merchant__avatar">
  10. <text class="pay-merchant__avatar-text">{{ merchantInitial }}</text>
  11. </view>
  12. <view class="pay-merchant__meta">
  13. <text class="pay-merchant__name">{{ merchantName }}</text>
  14. </view>
  15. </view>
  16. <!-- 金额主视觉 -->
  17. <view class="pay-amount-card">
  18. <view class="pay-amount-card__head">
  19. <text class="pay-amount-card__title">付款金额</text>
  20. <text v-if="canPay" class="pay-amount-card__clear" @click="changeAmount(0)">清空</text>
  21. </view>
  22. <view class="pay-amount-row">
  23. <text class="pay-amount-row__currency">¥</text>
  24. <text class="pay-amount-row__value" :class="{ 'pay-amount-row__value--placeholder': !canPay }">{{ amountText }}</text>
  25. <view class="pay-amount-row__cursor"></view>
  26. </view>
  27. <!-- 待结提示:点按可填入金额 -->
  28. <view
  29. v-if="hasOutstanding"
  30. class="pay-debt-tip"
  31. @click="fillOutstanding">
  32. <view class="pay-debt-tip__left">
  33. <text class="pay-debt-tip__label">待结金额</text>
  34. <text class="pay-debt-tip__value">¥{{ outstandingAmount }}</text>
  35. </view>
  36. <view class="pay-debt-tip__btn">
  37. <text class="pay-debt-tip__action">一键填入</text>
  38. </view>
  39. </view>
  40. <!-- 有可用余额时展示当前账户余额 -->
  41. <view v-else-if="hasPositiveBalance" class="pay-balance-tip">
  42. <text class="pay-balance-tip__label">当前账户余额</text>
  43. <text class="pay-balance-tip__value">¥{{ accountBalance }}</text>
  44. </view>
  45. </view>
  46. <!-- 账户与明细:独立信息卡,居中排版 -->
  47. <view class="pay-extra-card">
  48. <view v-if="displayCustomName" class="pay-account">
  49. <view class="pay-account__meta">
  50. <text class="pay-account__name">付款人:{{ displayCustomName }}</text>
  51. </view>
  52. </view>
  53. <view
  54. class="pay-action-row"
  55. :class="{
  56. 'pay-action-row--single': !showGatheringBtn,
  57. 'pay-action-row--with-account': !!displayCustomName
  58. }">
  59. <view
  60. v-if="showGatheringBtn"
  61. class="pay-action-chip pay-action-chip--debt"
  62. @click="goGathering">
  63. <text class="pay-action-chip__text">查看待结订单</text>
  64. </view>
  65. <view
  66. class="pay-action-chip"
  67. :class="{ 'pay-action-chip--disabled': !id }"
  68. @click="goBalanceChange">
  69. <text class="pay-action-chip__text">查看余额明细</text>
  70. </view>
  71. </view>
  72. </view>
  73. <!-- 底部:支付宝式数字键盘 + 右侧付款键 -->
  74. <view class="pay-keyboard-wrap">
  75. <view class="pay-keyboard">
  76. <view class="pay-keyboard__keys">
  77. <view
  78. v-for="(key, index) in flatKeys"
  79. :key="index"
  80. class="pay-key"
  81. :class="{ 'pay-key--del': key.type === 'delete' }"
  82. @click="handleKeyPress(key)">
  83. <view class="pay-key__inner">
  84. <text v-if="key.type === 'delete'" class="pay-key__del">⌫</text>
  85. <text v-else class="pay-key__num">{{ key.value }}</text>
  86. </view>
  87. </view>
  88. </view>
  89. <view
  90. class="pay-key-pay"
  91. :class="{ 'pay-key-pay--disabled': !canPay }"
  92. @click="handlePay">
  93. <text class="pay-key-pay__text">付款</text>
  94. </view>
  95. </view>
  96. <view class="pay-safe-area"></view>
  97. </view>
  98. </view>
  99. </template>
  100. <script>
  101. import { getGhsData } from '@/api/ghs'
  102. import { rechargeFn } from '@/api/custom-recharge'
  103. const KEY_TYPES = {
  104. NUMBER: 'number',
  105. DELETE: 'delete',
  106. DOT: 'dot',
  107. CONFIRM: 'confirm'
  108. }
  109. const MAX_INTEGER_LENGTH = 8
  110. const MAX_DECIMAL_LENGTH = 2
  111. export default {
  112. name: 'pay',
  113. data() {
  114. return {
  115. currentAmount: '0',
  116. displayAmount: '0',
  117. keyboardKeys: [
  118. [
  119. { type: KEY_TYPES.NUMBER, value: '1' },
  120. { type: KEY_TYPES.NUMBER, value: '2' },
  121. { type: KEY_TYPES.NUMBER, value: '3' }
  122. ],
  123. [
  124. { type: KEY_TYPES.NUMBER, value: '4' },
  125. { type: KEY_TYPES.NUMBER, value: '5' },
  126. { type: KEY_TYPES.NUMBER, value: '6' }
  127. ],
  128. [
  129. { type: KEY_TYPES.NUMBER, value: '7' },
  130. { type: KEY_TYPES.NUMBER, value: '8' },
  131. { type: KEY_TYPES.NUMBER, value: '9' }
  132. ],
  133. [
  134. { type: KEY_TYPES.DOT, value: '.' },
  135. { type: KEY_TYPES.NUMBER, value: '0' },
  136. { type: KEY_TYPES.DELETE, value: '' }
  137. ]
  138. ],
  139. amountBuffer: '0',
  140. updateScheduled: false,
  141. updateTimer: null,
  142. id: 0,
  143. salt: '',
  144. ghsInfo: {},
  145. customInfo: {},
  146. payWay: 1
  147. }
  148. },
  149. computed: {
  150. canPay() {
  151. return parseFloat(this.currentAmount) > 0
  152. },
  153. /** 金额展示:输入中保留原始缓冲,避免过早补零打断输入 */
  154. amountText() {
  155. if (!this.canPay && this.amountBuffer === '0') {
  156. return '0.00'
  157. }
  158. return this.amountBuffer
  159. },
  160. displayCustomName() {
  161. const name = (this.customInfo && this.customInfo.name) ? String(this.customInfo.name) : ''
  162. if (!name) {
  163. return ''
  164. }
  165. if (name.length > 7) {
  166. return name.slice(0, 7) + '...'
  167. }
  168. return name
  169. },
  170. merchantName() {
  171. const name = (this.ghsInfo && this.ghsInfo.name) ? String(this.ghsInfo.name) : '供货商'
  172. if (name.length > 12) {
  173. return name.slice(0, 12) + '...'
  174. }
  175. return name
  176. },
  177. merchantInitial() {
  178. const name = (this.ghsInfo && this.ghsInfo.name) ? String(this.ghsInfo.name) : '商'
  179. return name.charAt(0) || '商'
  180. },
  181. outstandingAmount() {
  182. const info = this.customInfo || {}
  183. const remain = parseFloat(info.remainDebtAmount || 0)
  184. if (remain > 0) {
  185. return parseFloat(remain.toFixed(2))
  186. }
  187. const bal = parseFloat(info.balance || 0)
  188. return bal < 0 ? parseFloat(Math.abs(bal).toFixed(2)) : 0
  189. },
  190. hasOutstanding() {
  191. return this.outstandingAmount > 0
  192. },
  193. /** 净 balance 为正时的可用余额 */
  194. accountBalance() {
  195. const bal = parseFloat((this.customInfo && this.customInfo.balance) || 0)
  196. return bal > 0 ? parseFloat(bal.toFixed(2)) : 0
  197. },
  198. hasPositiveBalance() {
  199. return this.accountBalance > 0
  200. },
  201. showGatheringBtn() {
  202. return this.hasOutstanding && !!this.id
  203. },
  204. /** 键盘扁平化为 12 键网格,配合右侧付款柱 */
  205. flatKeys() {
  206. const keys = []
  207. this.keyboardKeys.forEach((row) => {
  208. row.forEach((key) => {
  209. keys.push(key)
  210. })
  211. })
  212. return keys
  213. }
  214. },
  215. onLoad(options) {
  216. if (options.id) {
  217. this.id = options.id
  218. }
  219. if (options.salt) {
  220. this.salt = options.salt
  221. }
  222. if (this.id && this.salt) {
  223. getGhsData({ id: this.id, salt: this.salt }).then(res => {
  224. if (res.data && res.data.ghs) {
  225. this.ghsInfo = res.data.ghs
  226. this.customInfo = res.data.custom ? res.data.custom : {}
  227. if (this.hasOutstanding) {
  228. this.fillOutstanding()
  229. }
  230. }
  231. })
  232. }
  233. },
  234. methods: {
  235. /** 同步缓冲与展示金额 */
  236. changeAmount(amount) {
  237. const num = parseFloat(amount)
  238. if (!num || num <= 0) {
  239. this.amountBuffer = '0'
  240. this.currentAmount = '0'
  241. this.displayAmount = '0'
  242. return
  243. }
  244. const amountStr = parseFloat(num.toFixed(2)).toString()
  245. this.amountBuffer = amountStr
  246. this.currentAmount = amountStr
  247. this.updateDisplay()
  248. },
  249. /** 一键填入待结金额 */
  250. fillOutstanding() {
  251. if (!this.hasOutstanding) {
  252. return
  253. }
  254. this.changeAmount(this.outstandingAmount)
  255. },
  256. handleTouchStart() {},
  257. handleTouchEnd() {},
  258. handleKeyPress(key) {
  259. if (this.updateTimer) {
  260. clearTimeout(this.updateTimer)
  261. }
  262. if (key.type === KEY_TYPES.NUMBER) {
  263. this.addNumber(key.value)
  264. } else if (key.type === KEY_TYPES.DELETE) {
  265. this.deleteNumber()
  266. } else if (key.type === KEY_TYPES.DOT) {
  267. this.addDecimal()
  268. }
  269. this.scheduleUpdate()
  270. },
  271. scheduleUpdate() {
  272. if (!this.updateScheduled) {
  273. this.updateScheduled = true
  274. requestAnimationFrame(() => {
  275. this.updateDisplay()
  276. this.updateScheduled = false
  277. })
  278. }
  279. },
  280. addNumber(num) {
  281. const buffer = this.amountBuffer
  282. if (buffer === '0' && num !== '.') {
  283. this.amountBuffer = num
  284. this.currentAmount = num
  285. return
  286. }
  287. const parts = buffer.split('.')
  288. const integerPart = parts[0]
  289. const decimalPart = parts[1]
  290. if (!decimalPart && integerPart.length >= MAX_INTEGER_LENGTH) {
  291. uni.showToast({ title: '金额不能超过8位数', icon: 'none', duration: 1500 })
  292. return
  293. }
  294. if (decimalPart && decimalPart.length >= MAX_DECIMAL_LENGTH) {
  295. uni.showToast({ title: '最多支持2位小数', icon: 'none', duration: 1500 })
  296. return
  297. }
  298. this.amountBuffer = buffer + num
  299. this.currentAmount = this.amountBuffer
  300. },
  301. addDecimal() {
  302. if (!this.amountBuffer.includes('.')) {
  303. this.amountBuffer += '.'
  304. this.currentAmount = this.amountBuffer
  305. }
  306. },
  307. deleteNumber() {
  308. const buffer = this.amountBuffer
  309. if (buffer.length > 1) {
  310. this.amountBuffer = buffer.slice(0, -1)
  311. } else {
  312. this.amountBuffer = '0'
  313. }
  314. this.currentAmount = this.amountBuffer
  315. },
  316. updateDisplay() {
  317. let amount = this.currentAmount
  318. if (typeof amount !== 'string') {
  319. amount = amount.toString()
  320. }
  321. if (amount === '0') {
  322. this.displayAmount = '0'
  323. return
  324. }
  325. if (amount.includes('.')) {
  326. const numAmount = parseFloat(amount) || 0
  327. this.displayAmount = numAmount.toFixed(2)
  328. } else {
  329. this.displayAmount = amount
  330. }
  331. },
  332. setAmount(amount) {
  333. this.changeAmount(amount)
  334. },
  335. handlePay() {
  336. if (!this.canPay) {
  337. return
  338. }
  339. const amount = parseFloat(this.currentAmount)
  340. if (amount <= 0) {
  341. uni.showToast({ title: '请输入金额!', icon: 'none', duration: 2000 })
  342. return false
  343. }
  344. const params = {
  345. actPrice: amount,
  346. payWay: this.payWay,
  347. ghsId: this.id,
  348. salt: this.salt
  349. }
  350. uni.showLoading({ title: '跳转中...', mask: true })
  351. rechargeFn(params).then(res => {
  352. uni.hideLoading()
  353. if (res.code == 0) {
  354. uni.showToast({ title: res.msg, icon: 'none', duration: 2000 })
  355. return false
  356. }
  357. uni.showToast({ title: '正在跳转支付...', icon: 'success', duration: 1500 })
  358. setTimeout(() => {
  359. window.location.href = res.data.url
  360. }, 300)
  361. }).catch(() => {
  362. uni.hideLoading()
  363. uni.showToast({ title: '请求失败,请重试', icon: 'none', duration: 2000 })
  364. })
  365. },
  366. goBack() {
  367. uni.navigateBack({ delta: 1 })
  368. },
  369. goGathering() {
  370. if (!this.id) {
  371. uni.showToast({ title: '供货商信息加载中,请稍后再试', icon: 'none' })
  372. return
  373. }
  374. uni.navigateTo({
  375. url: `/pagesPurchase/gathering?id=${this.id}&salt=${this.salt}`
  376. })
  377. },
  378. /** 跳转余额变动明细(与小程序共用接口,salt 访客可查) */
  379. goBalanceChange() {
  380. if (!this.id) {
  381. uni.showToast({ title: '供货商信息加载中,请稍后再试', icon: 'none' })
  382. return
  383. }
  384. uni.navigateTo({
  385. url: `/admin/ghs/balanceChange?ghsId=${this.id}&salt=${this.salt}`
  386. })
  387. }
  388. }
  389. }
  390. </script>
  391. <style lang="scss" scoped>
  392. .pay-page {
  393. min-height: 100vh;
  394. background: #f5f5f5;
  395. box-sizing: border-box;
  396. padding-bottom: 560upx;
  397. }
  398. /* 收款方:简洁头像 + 名称 */
  399. .pay-merchant {
  400. display: flex;
  401. flex-direction: row;
  402. align-items: center;
  403. justify-content: center;
  404. padding: 56upx 40upx 28upx;
  405. }
  406. .pay-merchant__avatar {
  407. width: 72upx;
  408. height: 72upx;
  409. border-radius: 16upx;
  410. background: #1677ff;
  411. display: flex;
  412. align-items: center;
  413. justify-content: center;
  414. flex-shrink: 0;
  415. }
  416. .pay-merchant__avatar-text {
  417. color: #fff;
  418. font-size: 34upx;
  419. font-weight: 600;
  420. line-height: 1;
  421. }
  422. .pay-merchant__meta {
  423. margin-left: 20upx;
  424. display: flex;
  425. flex-direction: column;
  426. min-width: 0;
  427. }
  428. .pay-merchant__label {
  429. font-size: 24upx;
  430. color: #999;
  431. line-height: 32upx;
  432. }
  433. .pay-merchant__name {
  434. margin-top: 4upx;
  435. font-size: 32upx;
  436. font-weight: 600;
  437. color: #222;
  438. line-height: 44upx;
  439. }
  440. /* 金额白卡 */
  441. .pay-amount-card {
  442. margin: 0 24upx;
  443. padding: 36upx 32upx 28upx;
  444. background: #fff;
  445. border-radius: 16upx;
  446. box-sizing: border-box;
  447. }
  448. .pay-amount-card__head {
  449. display: flex;
  450. flex-direction: row;
  451. align-items: center;
  452. justify-content: space-between;
  453. }
  454. .pay-amount-card__title {
  455. font-size: 28upx;
  456. color: #666;
  457. line-height: 40upx;
  458. }
  459. .pay-amount-card__clear {
  460. font-size: 26upx;
  461. color: #1677ff;
  462. line-height: 40upx;
  463. padding: 0 8upx;
  464. }
  465. .pay-amount-row {
  466. display: flex;
  467. flex-direction: row;
  468. align-items: flex-end;
  469. margin-top: 28upx;
  470. min-height: 96upx;
  471. }
  472. .pay-amount-row__currency {
  473. font-size: 48upx;
  474. font-weight: 600;
  475. color: #222;
  476. line-height: 1;
  477. margin-right: 12upx;
  478. padding-bottom: 10upx;
  479. }
  480. .pay-amount-row__value {
  481. font-size: 80upx;
  482. font-weight: 600;
  483. color: #222;
  484. line-height: 1;
  485. font-family: 'DIN Alternate', 'Helvetica Neue', Arial, sans-serif;
  486. word-break: break-all;
  487. }
  488. .pay-amount-row__value--placeholder {
  489. color: #ccc;
  490. }
  491. /* 仿输入光标闪烁 */
  492. .pay-amount-row__cursor {
  493. width: 4upx;
  494. height: 64upx;
  495. margin-left: 8upx;
  496. margin-bottom: 8upx;
  497. background: #1677ff;
  498. animation: pay-cursor-blink 1s steps(1) infinite;
  499. }
  500. @keyframes pay-cursor-blink {
  501. 0%,
  502. 50% {
  503. opacity: 1;
  504. }
  505. 51%,
  506. 100% {
  507. opacity: 0;
  508. }
  509. }
  510. .pay-debt-tip {
  511. display: flex;
  512. flex-direction: row;
  513. align-items: center;
  514. justify-content: space-between;
  515. margin-top: 28upx;
  516. padding: 20upx 22upx;
  517. background: #fff7f0;
  518. border-radius: 12upx;
  519. box-sizing: border-box;
  520. }
  521. .pay-debt-tip__left {
  522. display: flex;
  523. flex-direction: row;
  524. align-items: baseline;
  525. flex: 1;
  526. min-width: 0;
  527. }
  528. .pay-debt-tip__label {
  529. font-size: 26upx;
  530. color: #999;
  531. line-height: 36upx;
  532. flex-shrink: 0;
  533. }
  534. .pay-debt-tip__value {
  535. margin-left: 12upx;
  536. font-size: 32upx;
  537. font-weight: 600;
  538. color: #ff6a00;
  539. line-height: 36upx;
  540. }
  541. .pay-debt-tip__btn {
  542. flex-shrink: 0;
  543. padding: 8upx 20upx;
  544. background: #1677ff;
  545. border-radius: 28upx;
  546. }
  547. .pay-debt-tip__action {
  548. font-size: 24upx;
  549. color: #fff;
  550. line-height: 32upx;
  551. }
  552. /* 正余额提示条:与待结条对称,蓝色系 */
  553. .pay-balance-tip {
  554. display: flex;
  555. flex-direction: row;
  556. align-items: center;
  557. justify-content: center;
  558. margin-top: 28upx;
  559. padding: 20upx 22upx;
  560. background: #f0f7ff;
  561. border-radius: 12upx;
  562. box-sizing: border-box;
  563. }
  564. .pay-balance-tip__label {
  565. font-size: 30upx;
  566. color: #333;
  567. line-height: 36upx;
  568. }
  569. .pay-balance-tip__value {
  570. margin-left: 12upx;
  571. font-size: 34upx;
  572. font-weight: 600;
  573. color: #1677ff;
  574. line-height: 36upx;
  575. }
  576. /* 账户 + 明细入口:白卡居中 */
  577. .pay-extra-card {
  578. margin: 20upx 24upx 0;
  579. padding: 28upx 24upx 30upx;
  580. background: #fff;
  581. border-radius: 16upx;
  582. box-sizing: border-box;
  583. }
  584. .pay-account {
  585. display: flex;
  586. flex-direction: row;
  587. align-items: center;
  588. justify-content: center;
  589. }
  590. .pay-account__badge {
  591. width: 56upx;
  592. height: 56upx;
  593. border-radius: 50%;
  594. background: #e8f3ff;
  595. display: flex;
  596. align-items: center;
  597. justify-content: center;
  598. flex-shrink: 0;
  599. }
  600. .pay-account__badge-text {
  601. font-size: 24upx;
  602. color: #1677ff;
  603. font-weight: 600;
  604. line-height: 1;
  605. }
  606. .pay-account__meta {
  607. display: flex;
  608. flex-direction: column;
  609. align-items: center;
  610. min-width: 0;
  611. }
  612. .pay-account__name {
  613. font-size: 32upx;
  614. font-weight: 600;
  615. color: #222;
  616. line-height: 40upx;
  617. }
  618. .pay-action-row {
  619. display: flex;
  620. flex-direction: row;
  621. align-items: stretch;
  622. justify-content: center;
  623. }
  624. .pay-action-row--with-account {
  625. margin-top: 28upx;
  626. padding-top: 28upx;
  627. border-top: 1upx solid #f0f0f0;
  628. }
  629. .pay-action-row--single .pay-action-chip {
  630. width: 300upx;
  631. flex: none;
  632. }
  633. .pay-action-chip {
  634. flex: 1;
  635. max-width: 300upx;
  636. height: 72upx;
  637. display: flex;
  638. align-items: center;
  639. justify-content: center;
  640. box-sizing: border-box;
  641. background: #f5f9ff;
  642. border: 1upx solid #d6e4ff;
  643. border-radius: 36upx;
  644. margin-left: 20upx;
  645. &:first-child {
  646. margin-left: 0;
  647. }
  648. }
  649. .pay-action-chip--debt {
  650. background: #fff7f0;
  651. border-color: #ffd8b8;
  652. }
  653. .pay-action-chip--debt .pay-action-chip__text {
  654. color: #ff6a00;
  655. }
  656. .pay-action-chip--disabled {
  657. opacity: 0.45;
  658. }
  659. .pay-action-chip:active {
  660. opacity: 0.85;
  661. }
  662. .pay-action-chip__text {
  663. font-size: 26upx;
  664. color: #1677ff;
  665. line-height: 36upx;
  666. font-weight: 500;
  667. }
  668. /* 底部键盘:左 3×4 数字区 + 右通栏付款 */
  669. .pay-keyboard-wrap {
  670. position: fixed;
  671. left: 0;
  672. right: 0;
  673. bottom: 0;
  674. background: #d1d3d9;
  675. z-index: 20;
  676. box-sizing: border-box;
  677. }
  678. .pay-keyboard {
  679. display: flex;
  680. flex-direction: row;
  681. align-items: stretch;
  682. padding: 12upx;
  683. box-sizing: border-box;
  684. }
  685. .pay-keyboard__keys {
  686. flex: 3;
  687. display: flex;
  688. flex-direction: row;
  689. flex-wrap: wrap;
  690. }
  691. .pay-key {
  692. width: 33.333%;
  693. height: 108upx;
  694. display: flex;
  695. align-items: center;
  696. justify-content: center;
  697. box-sizing: border-box;
  698. padding: 6upx;
  699. }
  700. .pay-key__inner {
  701. width: 100%;
  702. height: 100%;
  703. display: flex;
  704. align-items: center;
  705. justify-content: center;
  706. background: #fff;
  707. border-radius: 12upx;
  708. box-shadow: 0 2upx 0 #b8bbc3;
  709. }
  710. .pay-key:active .pay-key__inner {
  711. background: #e8e8e8;
  712. }
  713. .pay-key__num {
  714. font-size: 44upx;
  715. font-weight: 500;
  716. color: #222;
  717. line-height: 1;
  718. }
  719. .pay-key__del {
  720. font-size: 40upx;
  721. color: #333;
  722. line-height: 1;
  723. }
  724. .pay-key-pay {
  725. flex: 1;
  726. margin: 6upx;
  727. margin-left: 4upx;
  728. border-radius: 12upx;
  729. background: #1677ff;
  730. display: flex;
  731. align-items: center;
  732. justify-content: center;
  733. box-sizing: border-box;
  734. }
  735. .pay-key-pay--disabled {
  736. background: #a0c4ff;
  737. }
  738. .pay-key-pay:not(.pay-key-pay--disabled):active {
  739. background: #0958d9;
  740. }
  741. .pay-key-pay__text {
  742. color: #fff;
  743. font-size: 36upx;
  744. font-weight: 600;
  745. letter-spacing: 4upx;
  746. }
  747. .pay-safe-area {
  748. height: env(safe-area-inset-bottom);
  749. background: #d1d3d9;
  750. }
  751. </style>