placeAnOrder.vue 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681
  1. <template>
  2. <!-- 订单页面容器 -->
  3. <view class="order-box">
  4. <view class="hospital-box">
  5. <image :src="hospitalInfo.logoUrl" mode="aspectFill"></image>
  6. <view class="hospital-info">
  7. <view class="hospital-name">{{hospitalInfo.name || '-'}}</view>
  8. <view class="hospital-address">
  9. <u-icon name="map-fill" color="#999999" size="14"></u-icon>
  10. <span class="address">{{hospitalInfo.address || '-'}}</span>
  11. </span>
  12. </view>
  13. <!-- <view class="hospital-area">所在区:{{hospitalInfo.areaName || '-'}}</view> -->
  14. </view>
  15. </view>
  16. <view class="hospital-form">
  17. <!-- 用u-form写一个表单,包括所在科室(为一个选择器,内容为1,2,3),房床号,订单备注,就诊人,服务产品,期望时间,下单数量 -->
  18. <u--form labelWidth="150rpx" :model="form" :rules="rules" ref="uForm" :error-type="errorType">
  19. <view class="form-item">
  20. <u-form-item label="所在科室" prop="department" @click="showDepartment = true;" required borderBottom>
  21. <u--input :border="none" disabled v-model="form.department" disabledColor="#ffffff"
  22. placeholder="请选择" inputAlign="right" />
  23. <u-icon slot="right" name="arrow-right"></u-icon>
  24. </u-form-item>
  25. <u-form-item label="房床号" prop="roomNumber" required borderBottom>
  26. <u--input v-model="form.roomNumber" placeholder="请输入房号与床号" :border="none" inputAlign="right" />
  27. </u-form-item>
  28. <u-form-item label="订单备注" prop="remarks" style="margin: 20rpx 0;" labelPosition="top">
  29. <u-textarea ref="textarea" count maxlength="50" v-model="form.remarks"
  30. placeholder="请输入客户或订单特殊情况,可留空"></u-textarea>
  31. </u-form-item>
  32. </view>
  33. <view class="form-item">
  34. <u-form-item label="就诊人" prop="patient" @click="toPage" required>
  35. <u--input :border="none" disabled v-model="form.patient" disabledColor="#ffffff"
  36. placeholder="请选择" inputAlign="right" />
  37. <u-icon slot="right" name="arrow-right"></u-icon>
  38. </u-form-item>
  39. </view>
  40. <view class="form-item">
  41. <u-form-item label="服务产品" prop="serviceName" @click="toServicePage" required borderBottom>
  42. <u--input :border="none" disabled v-model="form.serviceName" disabledColor="#ffffff"
  43. placeholder="请选择" inputAlign="right" />
  44. <u-icon slot="right" name="arrow-right"></u-icon>
  45. </u-form-item>
  46. <u-form-item label="期望时间" prop="expectedTimeFormat" @click="showTimePicker = true;" borderBottom
  47. required>
  48. <u--input :border="none" disabled v-model="form.expectedTimeFormat" disabledColor="#ffffff"
  49. placeholder="请选择服务开始时间" inputAlign="right" />
  50. <u-icon slot="right" name="arrow-right"></u-icon>
  51. <u-datetime-picker :show="showTimePicker" v-model="form.expectedTime" mode="datetime"
  52. @confirm=selectTime @cancel="showTimePicker = false"
  53. :filter="timeFilter"></u-datetime-picker>
  54. </u-form-item>
  55. <u-form-item label="下单数量" prop="orderNum" required>
  56. <view class="flex-box-r">
  57. <u-number-box v-model="form.orderNum" @change="valChange" :max="999"></u-number-box>
  58. <span style="margin-left: 20rpx;">{{getUnitTxt(unitName) || ''}}</span>
  59. </view>
  60. </u-form-item>
  61. </view>
  62. </u--form>
  63. <u-action-sheet :show="showDepartment" :actions="actions" title="请选择科室" @close="showDepartment = false"
  64. @select="departmentSelect">
  65. <!-- <view class="search-box">
  66. <u-search
  67. v-model="searchText"
  68. placeholder="请输入搜索关键词"
  69. :show-action="false"
  70. @change="onSearch"
  71. ></u-search>
  72. </view> -->
  73. </u-action-sheet>
  74. </view>
  75. <!-- 多选框的服务协议 -->
  76. <view class="agreement-box">
  77. <u-checkbox-group v-model="checked" @change="checkboxChange">
  78. <u-checkbox size="16" shape="square" labelSize="12" active-color="#4B91D1" label="我已阅读并同意" la
  79. labelColor="#999999" name="true" :value="true"></u-checkbox>
  80. </u-checkbox-group>
  81. <view class="agreement" @click="toPrivacy('service_protocol')">《服务协议》</view>
  82. </view>
  83. <view class="tips flex-box-cloum">
  84. <span>润康优护服务公司为您提供服务</span>
  85. </view>
  86. <view class="submit-box flex-box-c-b">
  87. <view class="price-box">
  88. <span class="txt">金额:</span>
  89. <span class="price">¥{{(price * form.orderNum).toFixed(2)}}</span>
  90. </view>
  91. <view class="submit-btn" @click="submit">确认下单</view>
  92. </view>
  93. <u-popup :overlayStyle="{'touch-action':'none'}" closeable mode="bottom" :show="popShow" @close="popClose"
  94. @open="open" :round="20">
  95. <view class="pop-box">
  96. <view class="title-box">
  97. 用户服务协议
  98. </view>
  99. <scroll-view class="scroll-content" scroll-y @scroll="handleScroll">
  100. <view v-html="agreementContent"></view>
  101. </scroll-view>
  102. <view class="line-progress">
  103. <u-line-progress height="12" :percentage="percentage" activeColor="#4B91D1"></u-line-progress>
  104. </view>
  105. <view class="btn-box">
  106. <span class="btn" :class="readed?'active':''" @click="confirm">我已确认</span>
  107. </view>
  108. </view>
  109. </u-popup>
  110. </view>
  111. </template>
  112. <script>
  113. import {
  114. addOrder,
  115. getDepartmentList,
  116. getPrivacy,
  117. getServiceUnit,
  118. getDefaultPatient
  119. } from '@/api/order.js'
  120. import {
  121. getHospitalInfo
  122. } from '@/api/home.js'
  123. export default {
  124. data() {
  125. return {
  126. percentage: 0,
  127. agreement: '',
  128. popShow: false,
  129. checked: false,
  130. // 表单数据
  131. form: {
  132. hospitalId: '',
  133. department: '',
  134. hospitalDepartmentId: '',
  135. roomNumber: '',
  136. remarks: '',
  137. patient: '',
  138. patientId: '',
  139. serviceName: '',
  140. serviceId: '',
  141. expectedTime: null,
  142. orderNum: 1
  143. },
  144. price: 0,
  145. // 表单验证规则
  146. rules: {
  147. department: [{
  148. required: true,
  149. message: '请选择所在科室',
  150. trigger: ['change', 'blur']
  151. }],
  152. roomNumber: [{
  153. required: true,
  154. message: '请输入房床号',
  155. trigger: ['change', 'blur']
  156. }],
  157. // remarks: [{
  158. // required: true,
  159. // message: '请输入订单备注',
  160. // trigger: ['change', 'blur']
  161. // }],
  162. patient: [{
  163. required: true,
  164. message: '请选择就诊人',
  165. trigger: ['change', 'blur']
  166. }],
  167. serviceName: [{
  168. required: true,
  169. message: '请选择服务产品',
  170. trigger: ['change', 'blur']
  171. }],
  172. expectedTimeFormat: [{
  173. required: true,
  174. message: '请选择期望时间',
  175. trigger: ['change', 'blur']
  176. }],
  177. // orderNum: [{
  178. // required: true,
  179. // message: '请输入下单数量',
  180. // trigger: ['change']
  181. // }]
  182. },
  183. errorType: ['toast'],
  184. showDepartment: false,
  185. showTimePicker: false,
  186. actions: [],
  187. hospitalInfo: {},
  188. readed: false,
  189. agreementContent: '',
  190. unitName: null,
  191. unitList: [],
  192. isLogin: false,
  193. };
  194. },
  195. computed: {
  196. // price() {
  197. // let that = this;
  198. // let price = 0;
  199. // if (that.form.orderNum && that.unitName) {
  200. // let unit = that.unitList.find(item => item.name == that.unitName);
  201. // if (unit) {
  202. // price = that.form.orderNum * unit.price;
  203. // }
  204. // }
  205. // return price.toFixed(2);
  206. // }
  207. },
  208. onLoad(option) {
  209. let that = this;
  210. let user = uni.getStorageSync('apiToken');
  211. if (option.id) {
  212. that.form.hospitalId = option.id;
  213. that.getHospitalInfo(option.id)
  214. }
  215. if (option.scene) {
  216. let data = decodeURIComponent(option.scene);
  217. //截取t=i&id=13 中id= 后面的值
  218. let id = data.split('&')[1].split('=')[1];
  219. console.log("id", id);
  220. that.form.hospitalId = id;
  221. this.getHospitalInfo(id)
  222. }
  223. this.getServiceUnit();
  224. if (user) {
  225. this.getDefaultInfo();
  226. }
  227. uni.$on('returnService', function(data) {
  228. that.form.serviceName = data.name;
  229. that.form.serviceId = data.id;
  230. that.price = data.sellingPrice;
  231. that.unitName = data.serviceUnit;
  232. });
  233. uni.$on('returnPatient', function(data) {
  234. that.form.patient = data.name;
  235. that.form.patientId = data.id;
  236. });
  237. //处理期待时间,获取当前时间,判断分钟是否小于30,小于30设置我30,大于30设置为00没并且转换成时间戳格式
  238. let d = new Date();
  239. let hour = d.getHours();
  240. let minute = d.getMinutes();
  241. if (minute < 30) {
  242. minute = '30';
  243. } else {
  244. minute = '00';
  245. hour = hour + 1;
  246. if (hour > 23) {
  247. hour = 0;
  248. d.setDate(d.getDate() + 1);
  249. }
  250. }
  251. let time = d.getFullYear() + '-' + (d.getMonth() + 1) + '-' + d.getDate() + ' ' + hour + ':' + minute;
  252. that.form.expectedTime = time;
  253. console.log(time);
  254. },
  255. onReady() {
  256. let that = this;
  257. that.$refs.uForm.setRules(this.rules);
  258. // 如果需要兼容微信小程序的话,需要用此写法
  259. that.$refs.textarea.setFormatter((value) => {
  260. if (value.length >= 50) {
  261. return value.substr(0, 50)
  262. } else {
  263. return value
  264. }
  265. })
  266. },
  267. methods: {
  268. timeFilter(mode, options) {
  269. // console.log(mode);
  270. let d = new Date()
  271. // console.log(d.getFullYear());
  272. if (mode === 'year') {
  273. return options.filter((option) => option >= d.getFullYear())
  274. }
  275. if (mode === 'month') {
  276. return options.filter((option) => option >= d.getMonth() + 1)
  277. }
  278. if (mode === 'minute') {
  279. return options.filter((option) => option === '00' || option === '30');
  280. }
  281. return options;
  282. },
  283. //获取医院详情
  284. getHospitalInfo(id) {
  285. let that = this;
  286. getHospitalInfo(id).then(res => {
  287. if (res.code == 200) {
  288. that.hospitalInfo = res.data;
  289. that.form.hospitalId = that.hospitalInfo.id
  290. that.getDepartmentList()
  291. }
  292. })
  293. },
  294. //获取默认就诊人
  295. getDefaultInfo() {
  296. let that = this;
  297. getDefaultPatient().then(res => {
  298. if (res.code == 200) {
  299. let data = res.data;
  300. if (data) {
  301. that.form.patient = data.name + '(' + data.mobile + ')';
  302. that.form.patientId = data.id;
  303. }
  304. }
  305. })
  306. },
  307. //滚动协议
  308. handleScroll(e) {
  309. //根据。agreement-content 的滚动条的进度,设置百分比
  310. if (this.percentage < 100) {
  311. let scrollHeight = e.detail.scrollHeight;
  312. let scrollTop = e.detail.scrollTop;
  313. this.percentage = ((scrollTop / (scrollHeight - 400)) * 100).toFixed(0);
  314. if (this.percentage >= 100) {
  315. this.readed = true
  316. } else {
  317. this.readed = false
  318. }
  319. }
  320. },
  321. getUnitTxt(value) {
  322. let obj = this.unitList.find(item => item.code == value);;
  323. return obj ? obj.value : ''
  324. },
  325. //查询订单状态
  326. getServiceUnit() {
  327. let that = this;
  328. getServiceUnit().then(res => {
  329. if (res.code == 200) {
  330. this.unitList = res.data.serviceUnit;
  331. }
  332. })
  333. .catch((err) => {
  334. console.log(err);
  335. })
  336. },
  337. //获取科室列表
  338. getDepartmentList() {
  339. let that = this;
  340. let param = {
  341. hospitalId: that.form.hospitalId
  342. };
  343. getDepartmentList(param).then(res => {
  344. if (res.code == 200) {
  345. this.actions = res.data
  346. }
  347. })
  348. },
  349. // 提交表单
  350. submit() {
  351. let that = this;
  352. if (that.checked != 'true') {
  353. uni.showToast({
  354. title: '请先阅读并同意服务协议',
  355. icon: 'none'
  356. })
  357. return
  358. }
  359. this.$refs.uForm.validate().then((res) => {
  360. if (res) {
  361. // 提交表单
  362. that.open();
  363. } else {
  364. console.log('表单验证失败');
  365. }
  366. }).catch((errors) => {
  367. console.log('表单验证失败', errors);
  368. })
  369. },
  370. confirm() {
  371. if (!this.readed) {
  372. uni.showToast({
  373. title: '请先滑动阅读服务协议',
  374. icon: 'none'
  375. })
  376. return
  377. }
  378. addOrder(this.form).then(res => {
  379. if (res.code == 200) {
  380. uni.showToast({
  381. title: '下单成功',
  382. icon: 'success'
  383. })
  384. setTimeout(() => {
  385. this.popShow = false;
  386. //跳转订单页面传递参数
  387. getApp().globalData.switchTabParams = {
  388. reload: 'reload'
  389. };
  390. uni.switchTab({
  391. url: '/pages/tabBar/order',
  392. })
  393. }, 1000)
  394. }
  395. })
  396. },
  397. //选择时间
  398. selectTime(e) {
  399. this.form.expectedTime = e.value
  400. console.log("this.form.expectedTime", this.form.expectedTime);
  401. this.form.expectedTimeFormat = this.$utils.mFormatDate(e.value, 'yyyy-MM-dd HH:mm')
  402. console.log("this.form.expectedTimeFormat", this.form.expectedTimeFormat);
  403. this.showTimePicker = false
  404. },
  405. //选择科室
  406. departmentSelect(e) {
  407. this.form.department = e.name;
  408. this.form.hospitalDepartmentId = e.id;
  409. this.showDepartment = false;
  410. this.$refs.uForm.validateField('hospitalDepartmentId')
  411. },
  412. //数量
  413. valChange(e) {
  414. this.form.orderNum = e.value
  415. },
  416. //选择同意协议
  417. checkboxChange(e) {
  418. console.log('当前值为: ' + e)
  419. if (e == 'true') {
  420. this.checked = true
  421. } else {
  422. this.checked = false
  423. }
  424. console.log('this.checked: ' + this.checked)
  425. },
  426. //去选择服务
  427. toServicePage() {
  428. uni.navigateTo({
  429. url: '/pages/order/chooseService'
  430. })
  431. },
  432. //去就诊人页面
  433. toPage() {
  434. uni.setStorageSync('patientType', 'order')
  435. uni.navigateTo({
  436. url: '/pages/mine/patient/patient'
  437. })
  438. },
  439. // 打开协议弹窗
  440. open() {
  441. let that = this;
  442. that.popShow = true;
  443. getPrivacy({
  444. code: 'service_protocol'
  445. }).then(res => {
  446. if (res.code == 200) {
  447. that.agreementContent = res.data.protocolContent.replace(/\<img/gi,
  448. '<img style="max-width:100%;height:auto" ');
  449. }
  450. })
  451. },
  452. toPrivacy(type) {
  453. uni.navigateTo({
  454. url: '/pages/mine/agreement?type=service_protocol'
  455. })
  456. },
  457. popClose() {
  458. this.readed = false;
  459. this.percentage = 0;
  460. this.popShow = false;
  461. },
  462. },
  463. onUnload() {
  464. uni.$off('returnService');
  465. uni.$off('returnPatient');
  466. },
  467. }
  468. </script>
  469. <style lang="scss" scoped>
  470. .order-box {
  471. background-color: #f6f6f6;
  472. padding: 20rpx 20rpx 200rpx;
  473. .hospital-box {
  474. display: flex;
  475. align-items: center;
  476. padding: 20rpx;
  477. background-color: #fff;
  478. border-radius: 10rpx;
  479. image {
  480. width: 180rpx;
  481. height: 172rpx;
  482. border-radius: 10rpx;
  483. margin-right: 20rpx;
  484. }
  485. .hospital-info {
  486. flex: 1;
  487. .hospital-name {
  488. word-break: break-all;
  489. font-size: 28rpx;
  490. font-weight: bold;
  491. }
  492. .hospital-address {
  493. display: flex;
  494. justify-content: flex-start;
  495. align-items: flex-start;
  496. width: 100%;
  497. font-size: 26rpx;
  498. color: #666;
  499. margin-top: 20rpx;
  500. font-weight: 500;
  501. line-height: 35rpx;
  502. overflow: hidden; //超出的文本隐藏
  503. text-overflow: ellipsis; //溢出用省略号显示
  504. white-space: normal; //处理元素中的 空白
  505. display: -webkit-box;
  506. -webkit-line-clamp: 2;
  507. -webkit-box-orient: vertical;
  508. display: -moz-box;
  509. -moz-line-clamp: 2;
  510. -moz-box-orient: vertical;
  511. overflow-wrap: break-word;
  512. word-break: break-all;
  513. ::v-deep .u-icon {
  514. display: inline-block;
  515. }
  516. .address {
  517. font-size: 28rpx;
  518. margin-left: 5rpx;
  519. color: #999999;
  520. }
  521. }
  522. .hospital-area {
  523. font-size: 24rpx;
  524. color: #999;
  525. }
  526. }
  527. }
  528. .hospital-form {
  529. margin-top: 20rpx;
  530. border-radius: 10rpx;
  531. .form-item {
  532. padding: 20rpx 30rpx;
  533. margin-bottom: 20rpx;
  534. background-color: #fff;
  535. border-radius: 10rpx;
  536. }
  537. }
  538. .agreement-box {
  539. display: flex;
  540. align-items: center;
  541. justify-content: center;
  542. margin-top: 20rpx;
  543. .agreement {
  544. font-size: 22rpx;
  545. margin-left: 10rpx;
  546. color: #2979ff;
  547. }
  548. }
  549. .tips {
  550. margin-top: 20rpx;
  551. color: #666666;
  552. font-size: 22rpx;
  553. }
  554. .pop-box {
  555. padding: 0 40rpx;
  556. .title-box {
  557. padding: 30rpx 0;
  558. width: 100%;
  559. text-align: center;
  560. }
  561. .scroll-content {
  562. padding: 20rpx;
  563. width: 100%;
  564. box-sizing: border-box;
  565. height: 400px;
  566. border: 1rpx solid #f6f6f6;
  567. }
  568. .line-progress {
  569. padding: 20rpx 0;
  570. }
  571. .btn-box {
  572. margin-bottom: 40rpx;
  573. .btn {
  574. display: block;
  575. width: 100%;
  576. height: 72rpx;
  577. text-align: center;
  578. line-height: 72rpx;
  579. background-color: #999;
  580. color: #fff;
  581. border-radius: 40rpx;
  582. }
  583. .active {
  584. background-color: #4B91D1;
  585. }
  586. }
  587. }
  588. .submit-box {
  589. position: fixed;
  590. bottom: 0;
  591. left: 0;
  592. right: 0;
  593. background-color: #fff;
  594. padding: 40rpx 20rpx;
  595. box-shadow: 0 -2rpx 10rpx rgba(0, 0, 0, 0.1);
  596. .price-box {
  597. font-size: 32rpx;
  598. .txt {
  599. color: #666;
  600. }
  601. .price {
  602. color: #ff0000;
  603. }
  604. }
  605. .submit-btn {
  606. padding: 20rpx 40rpx;
  607. background-color: #2979ff;
  608. color: #fff;
  609. width: 200rpx;
  610. border-radius: 40rpx;
  611. text-align: center;
  612. font-size: 24rpx;
  613. }
  614. }
  615. ::v-deep .u-textarea {
  616. margin-top: 20rpx;
  617. }
  618. }
  619. </style>