21.前台系统-医院详情页
# 页面效果
# 预约挂号功能后端实现
需要获取医院信息(医院基本信息、预约信息)和科室信息
# 修改controller
在 service-hosp
的 HospitalApiController
中添加如下接口
package com.stt.yygh.hosp.controller;
...
@Api(tags = "医院管理接口")
@RestController
@RequestMapping("/api/hosp/hospital")
public class HospitalApiController {
@Autowired
private HospitalService service;
@Autowired
private DepartmentService departmentService;
...
@ApiOperation(value = "获取科室列表")
@GetMapping("department/{hoscode}")
public Result department(@ApiParam(name = "hoscode", value = "医院code", required = true)
@PathVariable String hoscode) {
return Result.ok(departmentService.findDeptTree(hoscode));
}
@ApiOperation(value = "医院预约挂号详情")
@GetMapping("{hoscode}")
public Result detail(@ApiParam(name = "hoscode", value = "医院code", required = true)
@PathVariable String hoscode) {
return Result.ok(service.detail(hoscode));
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
# 修改service
在 service-hosp
的HospitalService
中添加方法
package com.stt.yygh.hosp.service;
...
public interface HospitalService {
...
Map<String, Object> detail(String hoscode);
}
1
2
3
4
5
6
7
2
3
4
5
6
7
在 service-hosp
的HospitalServiceImpl
中添加实现
package com.stt.yygh.hosp.service.impl;
...
@Slf4j
@Service
public class HospitalServiceImpl implements HospitalService {
...
@Override
public Map<String, Object> detail(String hoscode) {
Map<String, Object> re = new HashMap<>();
//医院详情
Hospital hospital = this.packHospital(this.getByHoscode(hoscode));
re.put("hospital", hospital);
//预约规则
re.put("bookingRule", hospital.getBookingRule());
//不需要重复返回
hospital.setBookingRule(null);
// 虽然返回map扩展性很强,但实际工作中还是建议返回相应的VO,易于维护,字段信息清晰
return re;
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
# 预约挂号功能前端实现
# 封装api
在yygh-site
项目中,修改api/hosp/hosp.js文件,添加如下方法
export function detail(hoscode) {
return request({
url: `${api_name}/${hoscode}`,
method: 'get'
})
}
export function findDepartment(hoscode) {
return request({
url: `${api_name}/department/${hoscode}`,
method: 'get'
})
}
1
2
3
4
5
6
7
8
9
10
11
12
13
2
3
4
5
6
7
8
9
10
11
12
13
# 关于Nuxt路由
# 固定路由
每次跳转路由一样,没有传递参数,可以使用如下方式跳转
window.location.href = '/demo'
1
然后在pages文件夹下创建demo/index.vue文件,Nuxt框架会自动寻找pages/demo/index.vue路径作为路由
# 动态路由
在跳转的同时传递参数,如
window.location.href = '/demo/'+id
1
id是一个变量名称,那么需要在pages中创建pages/demo/_id.vue文件,Nuxt会找到路径作为路由
- Nuxt中动态路由的vue文件命名规范:_参数名称.vue
在vue页面中,通过如下方式获取参数
const id = this.$route.params.id
1
# 创建hospital/_hoscode.vue页面组件
创建/pages/hospital/_hoscode.vue组件
<template>
<!-- header -->
<div class="nav-container page-component">
<!--左侧导航 #start -->
<div class="nav left-nav">
<div class="nav-item selected">
<span class="v-link selected dark" :onclick="'javascript:window.location=\'/hospital/'+hospital.hoscode+'\''">预约挂号 </span>
</div>
<div class="nav-item ">
<span class="v-link clickable dark"
:onclick="'javascript:window.location=\'/hospital/detail/'+hospital.hoscode+'\''"> 医院详情 </span>
</div>
<div class="nav-item">
<span class="v-link clickable dark"
:onclick="'javascript:window.location=\'/hospital/notice/'+hospital.hoscode+'\''"> 预约须知 </span>
</div>
<div class="nav-item "><span class="v-link clickable dark"> 停诊信息 </span></div>
<div class="nav-item "><span class="v-link clickable dark"> 查询/取消 </span></div>
</div>
<!-- 左侧导航 #end -->
<!-- 右侧内容 #start -->
<div class="page-container">
<div class="hospital-home">
<div class="common-header">
<div class="title-wrapper">
<span class="hospital-title">{{ hospital.hosname }}</span>
<div class="icon-wrapper"><span class="iconfont"></span>{{ hospital.param.hostypeString }}</div>
</div>
</div>
<div class="info-wrapper">
<img class="hospital-img" :src="'data:image/jpeg;base64,'+hospital.logoData" :alt="hospital.hosname">
<div class="content-wrapper">
<div> 挂号规则</div>
<div class="line">
<div><span class="label">预约周期:</span><span>{{ bookingRule.cycle }}天</span></div>
<div class="space"><span class="label">放号时间:</span><span>{{ bookingRule.releaseTime }}</span></div>
<div class="space"><span class="label">停挂时间:</span><span>{{ bookingRule.stopTime }}</span></div>
</div>
<div class="line">
<span class="label">退号时间:</span>
<span v-if="bookingRule.quitDay == -1">就诊前一工作日{{ bookingRule.quitTime }}前取消</span>
<span v-if="bookingRule.quitDay == 0">就诊前当天{{ bookingRule.quitTime }}前取消</span>
</div>
<div style="margin-top:20px"> 医院预约规则</div>
<div class="rule-wrapper">
<ol>
<li v-for="item in bookingRule.rule" :key="item">{{ item }}</li>
</ol>
</div>
</div>
</div>
<div class="title select-title"> 选择科室</div>
<div class="select-dept-wrapper">
<div class="department-wrapper">
<div class="hospital-department">
<div class="dept-list-wrapper el-scrollbar" style="height: 100%;">
<div class="dept-list el-scrollbar__wrap" style="margin-bottom: -17px; margin-right: -17px;">
<div class="el-scrollbar__view">
<div class="sub-item" v-for="(item,index) in departmentVoList" :key="item.id"
:class="index == activeIndex ? 'selected' : ''" @click="move(index,item.depcode)">
{{ item.depname }}
</div>
</div>
</div>
<div class="el-scrollbar__bar is-horizontal">
<div class="el-scrollbar__thumb" style="transform: translateX(0%);"></div>
</div>
<div class="el-scrollbar__bar is-vertical">
<div class="el-scrollbar__thumb" style="transform: translateY(0%); height: 91.4761%;"></div>
</div>
</div>
</div>
</div>
<div class="sub-dept-container">
<div v-for="(item,index) in departmentVoList" :key="item.id" :class="index == 0 ? 'selected' : ''"
class="sub-dept-wrapper" :id="item.depcode">
<div class="sub-title">
<div class="block selected"></div>
{{ item.depname }}
</div>
<div class="sub-item-wrapper">
<div v-for="it in item.children" :key="it.id" class="sub-item" @click="schedule(it.depcode)">
<span class="v-link clickable">{{ it.depname }} </span>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- 右侧内容 #end -->
</div>
<!-- footer -->
</template>
<script>
import '~/assets/css/hospital_personal.css'
import '~/assets/css/hospital.css'
import { detail, findDepartment } from '~/api/hosp/hosp'
export default {
data() {
return {
hoscode: null,
activeIndex: 0,
hospital: {
param: {}
},
bookingRule: {},
departmentVoList: []
}
},
created() {
this.hoscode = this.$route.params.hoscode
this.init()
},
methods: {
init() {
detail(this.hoscode).then(res => {
this.hospital = res.data.hospital
this.bookingRule = res.data.bookingRule
})
findDepartment(this.hoscode).then(res => {
this.departmentVoList = res.data
})
},
move(index, depcode) {
this.activeIndex = index
document.getElementById(depcode).scrollIntoView()
},
schedule(depcode) {
window.location.href = '/hospital/schedule?hoscode=' + this.hoscode + '&depcode=' + depcode
}
}
}
</script>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
# 医院详情功能前端实现
创建/pages/hospital/detail/_hoscode.vue组件
<template>
<!-- header -->
<div class="nav-container page-component">
<!--左侧导航 #start -->
<div class="nav left-nav">
<div class="nav-item ">
<span class="v-link clickable dark"
:onclick="'javascript:window.location=\'/hospital/'+hospital.hoscode+'\''">预约挂号 </span>
</div>
<div class="nav-item selected">
<span class="v-link selected dark"
:onclick="'javascript:window.location=\'/hospital/detail/'+hospital.hoscode+'\''"> 医院详情 </span>
</div>
<div class="nav-item">
<span class="v-link clickable dark"
:onclick="'javascript:window.location=\'/hospital/notice/'+hospital.hoscode+'\''"> 预约须知 </span>
</div>
<div class="nav-item "><span class="v-link clickable dark"> 停诊信息 </span></div>
<div class="nav-item "><span class="v-link clickable dark"> 查询/取消 </span></div>
</div>
<!-- 左侧导航 #end -->
<!-- 右侧内容 #start -->
<div class="page-container">
<div class="hospital-detail">
<div class="common-header">
<div class="title-wrapper"><span class="hospital-title">{{ hospital.hosname }}</span>
<div class="icon-wrapper"><span class="iconfont"></span> {{ hospital.param.hostypeString }}</div>
</div>
</div>
<div class="info-wrapper">
<img :src="'data:image/jpeg;base64,'+hospital.logoData" :alt="hospital.hosname"
style="width: 80px; height: 80px;">
<div class="content-wrapper">
<div class="icon-text-wrapper">
<span class="iconfont prefix-icon"></span>
<span class="text"><p>{{ hospital.route }}</p></span>
<span class="iconfont right-icon"></span>
</div>
</div>
</div>
<div class="title mt40">医院介绍</div>
<div class="detail-content mt40"><p>{{ hospital.intro }}</p></div>
</div>
</div>
<!-- 右侧内容 #end -->
</div>
<!-- footer -->
</template>
<script>
import '~/assets/css/hospital_personal.css'
import '~/assets/css/hospital.css'
import { detail } from '~/api/hosp/hosp'
export default {
data() {
return {
hoscode: null,
hospital: {
param: {}
}
}
},
created() {
this.hoscode = this.$route.params.hoscode
this.init()
},
methods: {
init() {
detail(this.hoscode).then(res => {
this.hospital = res.data.hospital
})
}
}
}
</script>
<style scoped>
.hospital-detail .info-wrapper {
width: 100%;
padding-left: 0;
padding-top: 0;
margin-top: 0;
flex-direction: inherit;
}
.hospital-detail .info-wrapper .text {
font-size: 14px;
}
.hospital-detail .content-wrapper p {
text-indent: 0;
}
</style>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
# 预约须知功能前端实现
创建/pages/hospital/notice/_hoscode.vue组件
<template>
<!-- header -->
<div class="nav-container page-component">
<!--左侧导航 #start -->
<div class="nav left-nav">
<div class="nav-item ">
<span class="v-link clickable dark"
:onclick="'javascript:window.location=\'/hospital/'+hospital.hoscode+'\''">预约挂号 </span>
</div>
<div class="nav-item ">
<span class="v-link clickable dark"
:onclick="'javascript:window.location=\'/hospital/detail/'+hospital.hoscode+'\''"> 医院详情 </span>
</div>
<div class="nav-item selected">
<span class="v-link selected dark"
:onclick="'javascript:window.location=\'/hospital/notice/'+hospital.hoscode+'\''"> 预约须知 </span>
</div>
<div class="nav-item "><span class="v-link clickable dark"> 停诊信息 </span></div>
<div class="nav-item "><span class="v-link clickable dark"> 查询/取消 </span></div>
</div>
<!-- 左侧导航 #end -->
<!-- 右侧内容 #start -->
<div class="page-container">
<div class="hospital-notice">
<div class="content">
<h2>{{ hospital.hosname }}预约挂号须知</h2>
<p>为方便您早日就医康复,请您认真阅读预约挂号须知:</p>
<h4 id="一、预约实名制:">一、预约实名制:</h4>
<p>统一平台电话预约和网上预约挂号均采取实名制注册预约,请您如实提供就诊人员的真实姓名、有效证件号(身份证、护照)、性别、手机号码、社保卡号等基本信息。</p>
<h4 id="二、预约挂号:">二、预约挂号:</h4>
<p>按照北京市卫健委统一平台要求,预约挂号规则如下:</p>
<ul>
<li>在同一自然日,同一医院,同一科室,同一就诊单元,同一就诊人,可以预约最多1个号源;</li>
<li>在同一自然周,同一就诊人,可以预约最多8个号源;</li>
<li>在同一自然月,同一就诊人,可以预约最多12个号源;</li>
<li>在同一自然季度,同一就诊人,可以预约最多24个号源。</li>
</ul>
<h4 id="三、取消预约:">三、取消预约:</h4>
<p>已完成预约的号源,如需办理退号,至少在就诊前一工作日14:00前通过网站、微信公众号、114电话等平台预约渠道进行取消预约。</p>
<h4 id="四、爽约处理:">四、爽约处理:</h4>
<p>如预约成功后患者未能按时就诊且不办理取消预约号视为爽约,同一患者在自然年内爽约规则如下:</p>
<ul>
<li>累计爽约3次,自3次爽约日起,90天内不允许通过114平台进行预约挂号;</li>
<li>累计爽约6次,自6次爽约日起,180天内不允许通过114平台进行预约挂号。</li>
</ul>
</div>
</div>
</div>
<!-- 右侧内容 #end -->
</div>
<!-- footer -->
</template>
<script>
import '~/assets/css/hospital_personal.css'
import '~/assets/css/hospital.css'
import { detail } from '~/api/hosp/hosp'
export default {
data() {
return {
hoscode: null,
hospital: {
param: {}
}
}
},
created() {
this.hoscode = this.$route.params.hoscode
this.init()
},
methods: {
init() {
detail(this.hoscode).then(response => {
this.hospital = response.data.hospital
})
}
}
}
</script>
<style scoped>
.hospital-detail .info-wrapper {
width: 100%;
padding-left: 0;
padding-top: 0;
margin-top: 0;
flex-direction: inherit;
}
.hospital-detail .info-wrapper .text {
font-size: 14px;
}
.hospital-detail .content-wrapper p {
text-indent: 0;
}
</style>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
Last Updated: 2022/01/16, 11:29:51