pay.vue 9.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380
  1. <template>
  2. <view>
  3. <Loading :type="3" :loadStatus="loadStatus" :showText="errorText" />
  4. <zj-page-layout :hasFooter="true" v-if="detail">
  5. <view style="padding: 1rpx 30rpx">
  6. <view class="materials-container card mt30">
  7. <view class="title">
  8. <view class="t1">支付金额</view>
  9. <view class="t2"
  10. >¥<text>{{ detail.totalAmount | priceFilter }}</text></view
  11. >
  12. </view>
  13. <view class="id"><text>订单号:</text>{{ detail.orderId }}</view>
  14. <view class="product">
  15. <view
  16. class="it"
  17. v-for="(item, index) in wbId ? detail.rpMaterialOrderItems : detail.workerOrderItems"
  18. :key="index"
  19. >
  20. <view class="name"
  21. >{{ item.goodsName }}<text>×{{ item.num }}{{ item.unit }}</text></view
  22. >
  23. <view class="price">¥{{ item.totalAmount | priceFilter }}</view>
  24. </view>
  25. <view class="total">
  26. <view class="text">合计:</view>
  27. <view class="price">¥{{ detail.totalAmount | priceFilter }}</view>
  28. </view>
  29. </view>
  30. <view class="row"><text>备注:</text>{{ detail.remark }}</view>
  31. <view class="row"><text>操作人:</text>{{ detail.workerName }}</view>
  32. </view>
  33. <!-- <view class="pay-container card mt30">
  34. <view class="top">请选择客户支付方式</view>
  35. <view class="item" @tap="payType = 1">
  36. <view class="left">
  37. <text class="iconfont icon-weixinzhifu" style="color: #43c93e"></text>
  38. <text class="text">微信支付</text>
  39. </view>
  40. <view class="right">
  41. <text class="iconfont" :class="payType === 1 ? 'icon-danxuan2 active' : 'icon-danxuan'"></text>
  42. </view>
  43. </view>
  44. <view class="item" @tap="payType = 2">
  45. <view class="left">
  46. <text class="iconfont icon-xianxiazhifu" style="color: #0379ff"></text>
  47. <text class="text">线下支付</text>
  48. </view>
  49. <view class="right">
  50. <text class="iconfont" :class="payType === 2 ? 'icon-danxuan2 active' : 'icon-danxuan'"></text>
  51. </view>
  52. </view>
  53. </view> -->
  54. </view>
  55. <template slot="footer">
  56. <view class="footer-btn-group">
  57. <u-button text="取消订单" @click="cancelOrder"></u-button>
  58. <u-button text="扫码支付" type="primary" @click="scanCode"></u-button>
  59. <!-- <u-button text="扫码支付" type="primary" @click="scanCode" v-if="payType === 1"></u-button> -->
  60. <!-- <u-button text="确定支付" type="primary" @click="confirmPay" v-else></u-button> -->
  61. </view>
  62. </template>
  63. </zj-page-layout>
  64. </view>
  65. </template>
  66. <script>
  67. import { wxScanCode } from '@/common/utils/util.js'
  68. export default {
  69. data() {
  70. return {
  71. orderId: null,
  72. wbId: null,
  73. refresherTriggered: false,
  74. loadStatus: 0,
  75. errorText: '',
  76. detail: null,
  77. canScanCode: 0,
  78. timeout: null,
  79. timeoutNum: 0,
  80. payType: 1
  81. }
  82. },
  83. onLoad({ handleOrderId, wbId }) {
  84. this.orderId = handleOrderId
  85. this.wbId = wbId
  86. this.getDetail()
  87. this.crossPage.$on('reScanCode', () => {
  88. this.scanCode()
  89. })
  90. },
  91. onUnload() {
  92. clearTimeout(this.timeout)
  93. },
  94. methods: {
  95. getDetail() {
  96. let url = '',
  97. params = {}
  98. if (this.wbId) {
  99. url = '/engin/material/detail'
  100. params.id = this.orderId
  101. } else {
  102. url = '/pay/getOrder'
  103. params.orderId = this.orderId
  104. }
  105. this.$api
  106. .post(url, params)
  107. .then(res => {
  108. this.detail = res.data
  109. this.loadStatus = 0
  110. })
  111. .catch(res => {
  112. this.errorText = res.message
  113. this.loadStatus = 2
  114. })
  115. .finally(res => {
  116. this.refresherTriggered = false
  117. })
  118. },
  119. // 取消订单
  120. cancelOrder() {
  121. this.$modal({
  122. content: '确认取消订单吗?'
  123. })
  124. .then(() => {
  125. this.$api
  126. .post('/pay/cancel', {
  127. orderId: this.orderId
  128. })
  129. .then(res => {
  130. this.$successToast()
  131. this.$navToPage(
  132. {
  133. delta: 1
  134. },
  135. 'navigateBack'
  136. )
  137. })
  138. })
  139. .catch(() => {})
  140. },
  141. // 扫码
  142. async scanCode() {
  143. if (this.canScanCode > 0) return this.$toast(`请等待${this.canScanCode}秒后重试`)
  144. var codeVal = await wxScanCode()
  145. this.submitData(codeVal)
  146. },
  147. // 下单
  148. submitData(code) {
  149. let url = ''
  150. if (this.wbId) {
  151. url = '/engin/material/paid'
  152. } else {
  153. url = '/pay/paid'
  154. }
  155. this.$api
  156. .post(url, {
  157. authCode: code,
  158. orderId: this.orderId,
  159. payType: 'WECHAT'
  160. })
  161. .then(res => {
  162. // 返回true,则支付成功
  163. if (res.data) {
  164. this.timeoutNum = 0
  165. clearTimeout(this.timeout)
  166. this.$navToPage({
  167. url: `/packageMaterial/pages/sale/result?handleOrderId=${this.orderId}&result=1&wbId=${this.wbId || ''}`
  168. })
  169. }
  170. // 返回false,轮询3次
  171. else {
  172. if (this.timeoutNum < 4) {
  173. this.timeoutNum = this.timeoutNum + 1
  174. this.timeout = setTimeout(() => {
  175. this.submitData(code)
  176. }, 1000)
  177. } else {
  178. this.timeoutNum = 0
  179. clearTimeout(this.timeout)
  180. this.$navToPage({
  181. url: `/packageMaterial/pages/sale/result?handleOrderId=${this.orderId}&result=0&wbId=${this.wbId || ''}`
  182. })
  183. }
  184. }
  185. })
  186. .catch(res => {
  187. this.timeoutNum = 0
  188. clearTimeout(this.timeout)
  189. this.$tips(res.message)
  190. })
  191. .finally(() => {
  192. this.canScanCode = 15
  193. let time = setInterval(() => {
  194. if (this.canScanCode > 0) {
  195. this.canScanCode = this.canScanCode - 1
  196. } else {
  197. clearInterval(time)
  198. }
  199. }, 1000)
  200. })
  201. },
  202. confirmPay() {
  203. let url = ''
  204. if (this.wbId) {
  205. url = '/engin/material/paid'
  206. } else {
  207. url = '/pay/paid'
  208. }
  209. this.$api
  210. .post(url, {
  211. authCode: '',
  212. orderId: this.orderId,
  213. payType: 'LINE'
  214. })
  215. .then(res => {
  216. if (res.data) {
  217. this.$navToPage({
  218. url: `/packageMaterial/pages/sale/result?handleOrderId=${this.orderId}&result=1&wbId=${this.wbId || ''}`
  219. })
  220. } else {
  221. this.$navToPage({
  222. url: `/packageMaterial/pages/sale/result?handleOrderId=${this.orderId}&result=0&wbId=${this.wbId || ''}`
  223. })
  224. }
  225. })
  226. }
  227. }
  228. }
  229. </script>
  230. <style lang="scss" scoped>
  231. .card {
  232. @include zj-card;
  233. }
  234. .materials-container {
  235. padding: 30rpx;
  236. .title {
  237. text-align: center;
  238. margin-top: 30rpx;
  239. .t1 {
  240. font-size: 32rpx;
  241. font-weight: 500;
  242. }
  243. .t2 {
  244. font-size: 40rpx;
  245. color: $minor-color;
  246. margin-top: 20rpx;
  247. text {
  248. font-size: 56rpx;
  249. font-weight: 500;
  250. }
  251. }
  252. }
  253. .id {
  254. margin-top: 50rpx;
  255. text {
  256. color: $sec-font;
  257. }
  258. }
  259. .product {
  260. background: #f5f5f5;
  261. border-radius: 12rpx;
  262. padding: 20rpx;
  263. margin-top: 20rpx;
  264. .it {
  265. display: flex;
  266. align-items: flex-end;
  267. margin-bottom: 20rpx;
  268. .name {
  269. flex: 1;
  270. font-size: 28rpx;
  271. font-weight: 500;
  272. text {
  273. color: $sec-font;
  274. margin-left: 12rpx;
  275. font-weight: normal;
  276. }
  277. }
  278. .price {
  279. margin-left: 30rpx;
  280. font-size: 28rpx;
  281. font-weight: 500;
  282. }
  283. }
  284. .total {
  285. display: flex;
  286. align-items: center;
  287. justify-content: flex-end;
  288. margin-top: 30rpx;
  289. .text {
  290. font-size: 28rpx;
  291. color: $sec-font;
  292. }
  293. .price {
  294. font-size: 28rpx;
  295. color: $minor-color;
  296. font-weight: 500;
  297. }
  298. }
  299. }
  300. .row {
  301. margin-top: 20rpx;
  302. line-height: 40rpx;
  303. display: flex;
  304. font-size: 28rpx;
  305. text {
  306. color: $sec-font;
  307. flex-shrink: 0;
  308. line-height: 40rpx;
  309. }
  310. }
  311. }
  312. .pay-container {
  313. padding: 30rpx;
  314. .top {
  315. margin-bottom: 40rpx;
  316. }
  317. .item {
  318. display: flex;
  319. align-items: center;
  320. justify-content: space-between;
  321. margin: 30rpx 0;
  322. .left {
  323. display: flex;
  324. align-items: center;
  325. .iconfont {
  326. font-size: 44rpx;
  327. color: #43c93e;
  328. }
  329. .text {
  330. margin-left: 18rpx;
  331. font-size: 32rpx;
  332. }
  333. }
  334. .right {
  335. .iconfont {
  336. font-size: 40rpx;
  337. color: $sec-font;
  338. &.active {
  339. color: $theme-color;
  340. }
  341. }
  342. }
  343. }
  344. }
  345. </style>