kporder.vue 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422
  1. <template>
  2. <view class="safeArea">
  3. <view class="appointment">
  4. <view class="appointmentItem">
  5. <view class="title">考前培训地点:</view>
  6. <view class="place" @click="showAddress">
  7. <view class="name">{{ addressName }}</view>
  8. <view><u-icon name="arrow-right" color="#999999" size="28"></u-icon></view>
  9. </view>
  10. </view>
  11. <view class="appointmentItem" v-if="activeList.length">
  12. <view class="title">考前培训时间:</view>
  13. <view class="main">
  14. <view v-for="(item, index) in activeList" class="item" :key="index" @click="choItem(index, item.examTime)">
  15. <view class="checkbox">
  16. <u-checkbox
  17. :disabled="item.examTime >= applyDs.applySiteExamTime ? true : false"
  18. v-if="item.status === 0"
  19. v-model="item.checked"
  20. shape="circle"
  21. ></u-checkbox>
  22. </view>
  23. <view class="box">
  24. <view :class="['time', { active: item.checked }, { no: item.status !== 0 }]">{{ item.dataTime + ' ' + item.startTime + ' ~ ' + item.endTime }}</view>
  25. <view class="statusInfo" v-if="item.status !== 0">
  26. <template v-if="item.status === 2">
  27. 预约名额已满
  28. </template>
  29. <template v-if="item.status === 1">
  30. 此时段您已经有其他考前培训预约
  31. </template>
  32. </view>
  33. </view>
  34. <view class="num">已报:{{ item.registration }}/{{ item.num }}</view>
  35. </view>
  36. </view>
  37. </view>
  38. <view v-else class="appointmentItem">
  39. <view class="title">
  40. <text v-if="addressName">
  41. 该考试地点暂无考试时间,建议重新选择考试地点
  42. </text>
  43. <text v-else>
  44. 当前考培地点无考前培训时间点
  45. </text>
  46. </view>
  47. </view>
  48. <view class="btnMain">
  49. <view class="return" @click="backPage">上一步</view>
  50. <view class="sure" @click="sureOppoint">确定预约</view>
  51. </view>
  52. </view>
  53. <!-- 弹框-->
  54. <u-popup v-model="address_show" mode="bottom" class="addModel">
  55. <view class="tipBox safeArea">
  56. <view class="line"></view>
  57. <view class="title">温馨提示</view>
  58. <u-line color="#EEEEEE" />
  59. <scroll-view class="addressList" :scroll-y="true">
  60. <view class="item" v-for="(item, index) in listData" :key="index" @click="choAddress(index)">
  61. <u-checkbox class="checkbox" v-model="item.checked" shape="circle"></u-checkbox>
  62. <view :class="['address', { active: item.checked }]">{{ item.siteAddress }}</view>
  63. </view>
  64. </scroll-view>
  65. <u-line color="#EEEEEE" />
  66. <view class="btn" @click="sureAddress">确认</view>
  67. </view>
  68. </u-popup>
  69. </view>
  70. </template>
  71. <script>
  72. import { mapGetters } from 'vuex';
  73. export default {
  74. data() {
  75. return {
  76. address_show: false,
  77. addressName: '请选择',
  78. addressId: null, //当前选中考试点ID
  79. listData: [], //考试地点数据
  80. activeList: [], //选中考试地点列表
  81. applyId: null, //考试计划ID
  82. goodsId: null, //商品ID
  83. applyStatus: null, //学员状态ID
  84. applyDs: {}
  85. };
  86. },
  87. onLoad(option) {
  88. this.applyId = Number(option.applyId);
  89. this.goodsId = Number(option.goodsId);
  90. this.applyStatus = Number(option.applyStatus);
  91. this.getInfo();
  92. this.getVuexData();
  93. uni.showModal({
  94. content: '线下考前培训,自由填选如您有需要,建议先进行预约具体安排,后续会有相关工作人员与您沟通',
  95. showCancel: false
  96. });
  97. },
  98. methods: {
  99. getVuexData() {
  100. this.applyDs = this.$store.getters.getApplyData;
  101. console.log(this.applyDs.applySiteExamTime)
  102. },
  103. //获取考培地点
  104. getInfo() {
  105. this.$api.getApplysubscribeApplySiteTrain({ applyId: this.applyId }).then(res => {
  106. if (res.data.code === 200) {
  107. res.data.data.forEach((item, index) => {
  108. item.checked = false;
  109. });
  110. this.listData = res.data.data;
  111. }
  112. });
  113. },
  114. showAddress() {
  115. this.address_show = true;
  116. },
  117. choAddress(index) {
  118. this.listData.forEach((item, idx) => {
  119. this.$set(item, 'checked', false);
  120. if (idx === index) {
  121. this.$set(item, 'checked', true);
  122. }
  123. });
  124. },
  125. sureAddress() {
  126. var self = this;
  127. const index = this.listData.findIndex(item => item.checked);
  128. if (index === -1) {
  129. // uni.showToast({
  130. // title: '请选择考前培训地点',
  131. // icon: 'none'
  132. // });
  133. // return;
  134. }
  135. if (this.addressId === this.listData[index].id) {
  136. this.address_show = false;
  137. return;
  138. }
  139. this.addressName = this.listData[index].siteAddress;
  140. this.addressId = this.listData[index].id;
  141. var arrays = [];
  142. this.listData[index].examUserApplySiteTime.forEach(item => {
  143. if(item.examTime < self.applyDs.applySiteExamTime){
  144. item.examApplySiteTimeTwoVo.forEach(items => {
  145. arrays.push({
  146. examTime: item.examTime,
  147. startTimeC: items.startTime,
  148. endTimeC: items.endTime,
  149. dataTime: self.$method.timestampToTime(item.examTime),
  150. startTime: items.startTime,
  151. endTime: items.endTime,
  152. num: items.num,
  153. registration: items.registration,
  154. checked: false,
  155. status: items.status === 1 ? items.status : items.registration >= items.num ? 2 : items.status
  156. });
  157. });
  158. }
  159. });
  160. this.activeList = arrays.filter((item,index) => {
  161. const newTime = parseInt(new Date().getTime() / 1000)
  162. const liTime = parseInt(new Date(item.dataTime + '' + item.startTime + ':00').getTime() / 1000)
  163. if(liTime > newTime){
  164. return item
  165. }
  166. });
  167. this.address_show = false;
  168. },
  169. choItem(index,time) {
  170. if(time >= this.applyDs.applySiteExamTime){
  171. return
  172. }
  173. const item = this.activeList[index];
  174. if (item.status !== 0) {
  175. return;
  176. }
  177. this.activeList.forEach((item, idx) => {
  178. item.checked = false;
  179. if (idx === index) {
  180. item.checked = true;
  181. }
  182. });
  183. },
  184. sureOppoint() {
  185. var self = this;
  186. if (self.addressId) {
  187. var ast = self.activeList.some(item => {
  188. return item.checked === true;
  189. });
  190. if (ast) {
  191. var copyData = JSON.parse(JSON.stringify(self.activeList));
  192. const index = copyData.findIndex(item => item.checked);
  193. var data = {
  194. applySiteAddressTrain: self.addressName,
  195. applySiteExamTrainTime: copyData[index].examTime,
  196. applySiteStartTrainTime: copyData[index].startTimeC,
  197. applySiteEndTrainTime: copyData[index].endTimeC
  198. };
  199. let newObj = {};
  200. Object.assign(newObj, data, self.applyDs);
  201. self.$api.addApply(newObj).then(res => {
  202. if (res.data.code === 200) {
  203. uni.reLaunch({
  204. url: `/pages2/appointment/appointment_success?subscribeId=${res.data.data}`
  205. });
  206. }
  207. });
  208. } else {
  209. var data = JSON.parse(JSON.stringify(self.applyDs));
  210. self.$api.addApply(data).then(res => {
  211. if (res.data.code === 200) {
  212. uni.reLaunch({
  213. url: `/pages2/appointment/appointment_success?subscribeId=${res.data.data}`
  214. });
  215. }
  216. });
  217. }
  218. } else {
  219. var data = JSON.parse(JSON.stringify(self.applyDs));
  220. self.$api.addApply(data).then(res => {
  221. if (res.data.code === 200) {
  222. uni.reLaunch({
  223. url: `/pages2/appointment/appointment_success?subscribeId=${res.data.data}`
  224. });
  225. }
  226. });
  227. }
  228. },
  229. backPage() {
  230. uni.navigateBack({
  231. delta: 1
  232. });
  233. }
  234. }
  235. };
  236. </script>
  237. <style>
  238. page {
  239. background-color: #eaeef1;
  240. }
  241. .addModel .u-drawer-bottom {
  242. box-shadow: 0px 0px 16px 4px rgba(145, 156, 178, 0.1);
  243. border-radius: 32rpx 32rpx 0px 0px;
  244. }
  245. </style>
  246. <style scoped lang="scss">
  247. .appointment {
  248. padding: 0 8rpx;
  249. .appointmentItem {
  250. margin: 24rpx 0 40rpx;
  251. .title {
  252. font-size: 30rpx;
  253. font-family: PingFang SC;
  254. font-weight: 500;
  255. color: #333333;
  256. line-height: 1;
  257. margin-bottom: 16rpx;
  258. padding-left: 24rpx;
  259. }
  260. .place {
  261. height: 80rpx;
  262. background: #ffffff;
  263. border-radius: 16rpx;
  264. display: flex;
  265. justify-content: space-between;
  266. align-items: center;
  267. padding: 0 24rpx;
  268. }
  269. }
  270. .main {
  271. background: #ffffff;
  272. border-radius: 16rpx;
  273. padding: 32rpx 16rpx;
  274. .item {
  275. display: flex;
  276. align-items: center;
  277. margin-bottom: 16rpx;
  278. font-size: 28rpx;
  279. font-family: PingFang SC;
  280. font-weight: 500;
  281. color: #333333;
  282. .statusInfo {
  283. font-size: 24rpx;
  284. font-family: PingFang SC;
  285. font-weight: 500;
  286. color: #ff3b30;
  287. padding-left: 24rpx;
  288. }
  289. .checkbox {
  290. width: 32rpx;
  291. height: 32rpx;
  292. display: flex;
  293. align-items: center;
  294. }
  295. .time {
  296. width: 430rpx;
  297. height: 80rpx;
  298. line-height: 80rpx;
  299. background: #f5f5f5;
  300. border: 2rpx solid #f5f5f5;
  301. border-radius: 16rpx;
  302. font-size: 30rpx;
  303. font-family: PingFang SC;
  304. font-weight: bold;
  305. text-align: center;
  306. color: #333333;
  307. margin: 0 18rpx 0 8rpx;
  308. &.active {
  309. background: #ebf5ff;
  310. border: 2rpx solid #007aff;
  311. }
  312. &.no {
  313. background: #ffdddb;
  314. border: 2rpx solid #ffdddb;
  315. }
  316. }
  317. }
  318. }
  319. .btnMain {
  320. display: flex;
  321. justify-content: center;
  322. text-align: center;
  323. .return {
  324. width: 200rpx;
  325. height: 80rpx;
  326. line-height: 80rpx;
  327. background: #f5f5f5;
  328. border-radius: 40rpx;
  329. font-size: 30rpx;
  330. font-family: PingFang SC;
  331. font-weight: bold;
  332. color: #007aff;
  333. }
  334. .sure {
  335. width: 438rpx;
  336. height: 80rpx;
  337. line-height: 80rpx;
  338. background: #007aff;
  339. border-radius: 40rpx;
  340. font-size: 30rpx;
  341. font-family: PingFang SC;
  342. font-weight: bold;
  343. color: #ffffff;
  344. margin-left: 24rpx;
  345. }
  346. }
  347. }
  348. .tipBox {
  349. width: 100%;
  350. font-family: PingFang SC;
  351. .line {
  352. width: 80rpx;
  353. height: 8rpx;
  354. background: #999999;
  355. border-radius: 4rpx;
  356. margin: 8rpx auto;
  357. }
  358. .title {
  359. text-align: center;
  360. font-size: 24rpx;
  361. font-family: PingFang SC;
  362. font-weight: 500;
  363. color: #999999;
  364. margin: 15rpx 0;
  365. }
  366. .main {
  367. font-size: 30rpx;
  368. font-weight: 500;
  369. color: #666666;
  370. line-height: 48rpx;
  371. margin-bottom: 40rpx;
  372. }
  373. .addressList {
  374. height: 500rpx;
  375. padding-top: 24rpx;
  376. .item {
  377. display: flex;
  378. align-items: center;
  379. padding: 0 24rpx;
  380. margin-bottom: 24rpx;
  381. .checkbox {
  382. width: 32rpx;
  383. height: 32rpx;
  384. display: flex;
  385. align-items: center;
  386. margin-right: 8rpx;
  387. }
  388. .address {
  389. width: 654rpx;
  390. height: 80rpx;
  391. line-height: 80rpx;
  392. background: #f5f5f5;
  393. border-radius: 16rpx;
  394. font-size: 30rpx;
  395. font-family: PingFang SC;
  396. font-weight: bold;
  397. color: #333333;
  398. padding: 0 24rpx;
  399. &.active {
  400. background: #ebf5ff;
  401. border: 2rpx solid #007aff;
  402. }
  403. }
  404. }
  405. }
  406. .btn {
  407. width: 200rpx;
  408. height: 64rpx;
  409. line-height: 64rpx;
  410. background: linear-gradient(0deg, #015eea, #00c0fa);
  411. border-radius: 32rpx;
  412. margin: 17rpx auto;
  413. font-size: 30rpx;
  414. font-family: PingFang SC;
  415. font-weight: 500;
  416. text-align: center;
  417. color: #ffffff;
  418. }
  419. }
  420. </style>