Procházet zdrojové kódy

Signed-off-by: liuboyan <632697560@qq.com>
基本跑通大体流程

liuboyan před 4 roky
rodič
revize
8074d579a3

+ 35 - 1
config/api.js

@@ -1,6 +1,14 @@
-const API_BASE = 'http://jihengcc.cn:17080/ypdApi'
+const API_BASE = 'http://39.100.230.190:8019/ypdApi'
 
 module.exports = {
+	//  微信授权登录
+	wxLogin: API_BASE + '/v2/student/login/wxLogin',
+	//  账号密码登录
+	loginByPassword: API_BASE + '/v2/student/login/login',
+	//  根据经纬度获取位置
+	getAddressInfo: API_BASE + '/v2/location/pointToAddress',
+	
+	
 	//  获取首页轮播图列表
 	getIndexSwiperList: API_BASE + '/v2/home/getRollAdvertisingHomeList',
 	//  获取首页场馆列表
@@ -13,6 +21,16 @@ module.exports = {
 	getVideoList: API_BASE + '/v2/home/getCourseShowNearbyList',
 	
 	
+	//  获取可报名学员列表
+	getEnlistAbleStudent: API_BASE + '/v2/class/selectApplyList',
+	//  获取会员服务班级详情
+	getMemberClassDetail: API_BASE + '/v2/class/getDetail',
+	//  学员报名
+	enlistStudent: API_BASE + '/v2/class/apply',
+	//  获取可预约学员列表
+	getSubscribeAbleList: API_BASE + '/v2/class/selectStudent',
+	//  学员预约
+	subscribeStudent: API_BASE + '/v2/class/appointment',
 	//  提交新增学员表单
 	submitStudentForm: API_BASE + '/v2/student/info/add',
 	//  提交学员预约表单
@@ -21,8 +39,12 @@ module.exports = {
 	submitLevelForm: API_BASE + '/v2/class/leaveSubmit',
 	//  提交评价表单
 	submitEvaluateForm: API_BASE + '/v2/class/estimateSubmit',
+	//  提交成长历程
+	submitGrowForm: API_BASE + '/v2/class/addGrow',
 	
 	
+	//  获取我的账户
+	getMemberInfo: API_BASE + '/v2/student/myCenter/getMemberInfo',
 	//  获取我的课程列表
 	getMyClassList: API_BASE + '/v2/class/getList',
 	//  获取我的请假列表
@@ -33,8 +55,12 @@ module.exports = {
 	getStudentList: API_BASE + '/v2/student/myCenter/selectStudent',
 	//  获取我的优惠券列表
 	getCouponList: API_BASE + '/v2/student/myCenter/getCouponList',
+	//  获取分享有礼二维码
+	getShareUrl: API_BASE + '/v2/student/myCenter/share',
 	//  获取我的评价列表
 	getEvaluateList: API_BASE + '/v2/student/myCenter/getClassEvaluateList',
+	//  获取我的预约体验列表
+	getSubscribeList: API_BASE + '/v2/student/myCenter/getSubscribeClassEvaluateList',
 	
 	
 	//  获取可购买会员卡列表
@@ -45,8 +71,16 @@ module.exports = {
 	getUsableCouponList: API_BASE + '/v2/student/myCenter/getOwnCouponList',
 	//  获取可购买会员卡选择优惠券后信息
 	getMemberCardInfoAfterCoupon: API_BASE + '/v2/student/myCenter/getMemberDetailAfterCoupon',
+	//  获取可购买会员卡学员列表
+	getAllStudentList: API_BASE + '/v2/student/myCenter/selectAllStudent',
 	//  获取支付回调数据
 	getPayParams: API_BASE + '/v2/student/myCenter/getWxPayParams',
 	//  获取支付结果
 	getPayResult: API_BASE + '/v2/student/myCenter/getPayResult',
+	
+	
+	//  获取服务器端图片
+	getServerImg: API_BASE + '/download/icon/',
+	//  上传地址
+	uploadFile: API_BASE + '/v2/common/file/uploadOne',
 }

+ 24 - 23
manifest.json

@@ -10,8 +10,8 @@
         "compilerVersion" : 3,
         /* 5+App特有相关 */
         "modules" : {
-            "OAuth" : {},
-            "Payment" : {}
+            "Payment" : {},
+            "OAuth" : {}
         },
         /* 模块配置 */
         "distribute" : {
@@ -19,27 +19,27 @@
             "android" : {
                 /* android打包配置 */
                 "permissions" : [
-                    "<uses-permission android:name=\"android.permission.CHANGE_NETWORK_STATE\"/>",
-                    "<uses-permission android:name=\"android.permission.MOUNT_UNMOUNT_FILESYSTEMS\"/>",
-                    "<uses-permission android:name=\"android.permission.READ_CONTACTS\"/>",
-                    "<uses-permission android:name=\"android.permission.VIBRATE\"/>",
-                    "<uses-permission android:name=\"android.permission.READ_LOGS\"/>",
-                    "<uses-permission android:name=\"android.permission.ACCESS_WIFI_STATE\"/>",
+                    "<uses-feature android:name=\"android.hardware.camera\"/>",
                     "<uses-feature android:name=\"android.hardware.camera.autofocus\"/>",
-                    "<uses-permission android:name=\"android.permission.WRITE_CONTACTS\"/>",
+                    "<uses-permission android:name=\"android.permission.ACCESS_COARSE_LOCATION\"/>",
+                    "<uses-permission android:name=\"android.permission.ACCESS_FINE_LOCATION\"/>",
                     "<uses-permission android:name=\"android.permission.ACCESS_NETWORK_STATE\"/>",
+                    "<uses-permission android:name=\"android.permission.ACCESS_WIFI_STATE\"/>",
+                    "<uses-permission android:name=\"android.permission.CALL_PHONE\"/>",
                     "<uses-permission android:name=\"android.permission.CAMERA\"/>",
-                    "<uses-permission android:name=\"android.permission.RECORD_AUDIO\"/>",
+                    "<uses-permission android:name=\"android.permission.CHANGE_NETWORK_STATE\"/>",
+                    "<uses-permission android:name=\"android.permission.CHANGE_WIFI_STATE\"/>",
+                    "<uses-permission android:name=\"android.permission.FLASHLIGHT\"/>",
                     "<uses-permission android:name=\"android.permission.GET_ACCOUNTS\"/>",
                     "<uses-permission android:name=\"android.permission.MODIFY_AUDIO_SETTINGS\"/>",
+                    "<uses-permission android:name=\"android.permission.MOUNT_UNMOUNT_FILESYSTEMS\"/>",
+                    "<uses-permission android:name=\"android.permission.READ_CONTACTS\"/>",
+                    "<uses-permission android:name=\"android.permission.READ_LOGS\"/>",
                     "<uses-permission android:name=\"android.permission.READ_PHONE_STATE\"/>",
-                    "<uses-permission android:name=\"android.permission.CHANGE_WIFI_STATE\"/>",
+                    "<uses-permission android:name=\"android.permission.RECORD_AUDIO\"/>",
+                    "<uses-permission android:name=\"android.permission.VIBRATE\"/>",
                     "<uses-permission android:name=\"android.permission.WAKE_LOCK\"/>",
-                    "<uses-permission android:name=\"android.permission.CALL_PHONE\"/>",
-                    "<uses-permission android:name=\"android.permission.FLASHLIGHT\"/>",
-                    "<uses-permission android:name=\"android.permission.ACCESS_COARSE_LOCATION\"/>",
-                    "<uses-feature android:name=\"android.hardware.camera\"/>",
-                    "<uses-permission android:name=\"android.permission.ACCESS_FINE_LOCATION\"/>",
+                    "<uses-permission android:name=\"android.permission.WRITE_CONTACTS\"/>",
                     "<uses-permission android:name=\"android.permission.WRITE_SETTINGS\"/>"
                 ]
             },
@@ -49,15 +49,15 @@
                 "ad" : {},
                 "oauth" : {
                     "weixin" : {
-                        "appid" : "wxc6ab95e70160a2ee",
-                        "appsecret" : "a1eee335af123ba2f7621e6687ddb33b",
+                        "appid" : "wx066a613dd9d313e7",
+                        "appsecret" : "cbc8988b59fd9174251ce03dccc8a760",
                         "UniversalLinks" : ""
                     }
                 },
                 "payment" : {
                     "weixin" : {
-                        "__platform__" : [ "android" ],
-                        "appid" : "wxc6ab95e70160a2ee",
+                        "__platform__" : [ "ios", "android" ],
+                        "appid" : "wx066a613dd9d313e7",
                         "UniversalLinks" : ""
                     }
                 }
@@ -105,9 +105,10 @@
     /* 快应用特有相关 */
     "mp-weixin" : {
         /* 小程序特有相关 */
-        "appid" : "wx0c8f390063292c1f",
+        "appid" : "wx066a613dd9d313e7",
         "setting" : {
-            "urlCheck" : true
+            "urlCheck" : false,
+            "minified" : true
         },
         "optimization" : {
             "subPackages" : true
@@ -125,7 +126,7 @@
             "mode" : "history",
             "base" : "./"
         },
-        "title" : "cereshop",
+        "title" : "星火纵横学员端",
         "domain" : "39.100.102.234",
         "devServer" : {
             "port" : 8080

+ 20 - 0
pages.json

@@ -19,6 +19,11 @@
 		"style": {
 			"navigationBarTitleText": "个人"
 		}
+	}, {
+		"path": "pages/login/index",
+		"style": {
+			"navigationStyle": "custom"
+		}
 	}],
 	"subPackages": [{
 		"root": "pagesMember",
@@ -39,6 +44,11 @@
 			"style": {
 				"navigationBarTitleText": "添加信息"
 			}
+		},  {
+			"path": "subscribelSuccess",
+			"style": {
+				"navigationBarTitleText": "新增成功"
+			}
 		}, {
 			"path": "leaveForm",
 			"style": {
@@ -78,10 +88,20 @@
 				"navigationBarTitleText": "我的优惠券"
 			}
 		}, {
+			"path": "shareInfo",
+			"style": {
+				"navigationBarTitleText": "分享有礼"
+			}
+		},  {
 			"path": "evaluateList",
 			"style": {
 				"navigationBarTitleText": "我的评价"
 			}
+		}, {
+			"path": "subscribeList",
+			"style": {
+				"navigationBarTitleText": "我的预约"
+			}
 		}, {
 			"path": "memberCardList",
 			"style": {

+ 107 - 65
pages/index/index.vue

@@ -2,26 +2,38 @@
 	<view class="content">
 		<u-navbar back-icon-size="0" :back-text="locationText" title="星火纵横" :title-color="mainColor" title-bold></u-navbar>
 		<u-swiper :list="swiperList" mode="rect" effect3d border-radius="30" name="url" style="margin-bottom: 10px;"></u-swiper>
-		<u-section title="附近场馆" :right="false" font-size="32" :line-color="mainColor" class="title-box"></u-section>
+		<view class="section-title">
+			<u-image width="20px" height="10px" :src="sectionIcon"></u-image>
+			<u-section title="附近场馆" font-size="32" :right="false" :show-line="false"></u-section>
+		</view>
 		<view class="venue-box">
-			<u-card :head-border-bottom="false" :foot-border-top="false" padding="0" margin="10px" v-for="(item, index) in venueList"
+			<u-card :head-border-bottom="false" :show-foot="false" title-size="32" padding="0" margin="10px" v-for="(item, index) in venueList"
 			 :key="index" class="venue-card" @click="goToVenueDetail(item)">
 				<view class="venue-content" slot="head" style="padding-top: 10px;">
-					<view class="venue-type">体验馆</view>
-					<text class="venue-name">{{item.name}}</text>
+					<view class="venue-name">{{item.name}}</view>
 				</view>
 				<view class="venue-content" slot="body">
-					<text class="venue-distance">{{item.name}}</text>
-				</view>
-				<view class="venue-content" slot="foot" style="padding-bottom: 10px;">
-					<text class="venue-address">{{item.address}}</text>
+					<view class="info-text">
+						<u-icon name="car"></u-icon>
+						距您{{item.distance}}km
+					</view>
+					<view class="info-text">
+						<u-icon name="map"></u-icon>
+						{{item.address}}
+					</view>
 				</view>
 			</u-card>
 		</view>
-		<u-section title="附近场馆" :right="false" font-size="32" :line-color="mainColor" class="title-box"></u-section>
+		<view class="section-title">
+			<u-image width="20px" height="10px" :src="sectionIcon"></u-image>
+			<u-section title="精彩瞬间" font-size="32" :right="false" :show-line="false"></u-section>
+		</view>
 		<view class="video-box">
 			<view v-for="(item, index) in videoList" :key="index" class="video-card">
-				<u-image :src="item.url" mode="aspectFill" height="30vw" border-radius="10px"></u-image>
+				<view class="video-col">
+					<video :src="item.url" object-fit="cover" controls></video>
+				</view>
+				<!-- <u-image :src="item.url" mode="aspectFill" height="30vw" border-radius="10px"></u-image> -->
 				<view class="video-name">{{item.title}}</view>
 			</view>
 		</view>
@@ -43,26 +55,43 @@
 		},
 		data() {
 			return {
+				sectionIcon: API.getServerImg + 'biaoti.png',
 				longitude: '',
 				latitude: '',
-				locationText: '沈阳>浑南',
+				locationText: '',
 				swiperList: [],
 				venueList: [],
 				videoList: []
 			}
 		},
-		onLoad() {
+		onLoad(options) {
+			if (options.shareParams) {
+				uni.setStorageSync({
+					key: 'shareParams',
+					data: options.shareParams
+				})
+			}
 			uni.getLocation({
 				type: 'wgs84',
 				geocode: true,
 				success: (res) => {
-					this.longitude = res.longitude
-					this.latitude = res.latitude
+					uni.setStorage({
+						key: 'locationData',
+						data: {
+							longitude: res.longitude,
+							latitude: res.latitude,
+						}
+					})
 					this.initialize()
 				}
 			});
 		},
-		onReady() {
+		onShow() {
+			if (!uni.getStorageSync('token')) {
+				uni.navigateTo({
+					url: '/pages/login/index'
+				});
+			}
 		},
 		onPullDownRefresh() {
 			this.initialize()
@@ -77,29 +106,31 @@
 					this.swiperList = res.data
 				}).catch(error => {
 					this.$refs.uTips.show({
-						title: '获取首页轮播图失败',
+						title: error.message,
 						type: 'warning',
 					})
 				})
-				NET.request(API.getVenueList, {
-					longitude: this.longitude,
-					latitude: this.latitude,
-				}, 'POST').then(res => {
+				NET.request(API.getAddressInfo, uni.getStorageSync('locationData'), 'POST').then(res => {
+					this.locationText = res.data.province + '-' + res.data.city + '-' + res.data.district
+				}).catch(error => {
+					this.$refs.uTips.show({
+						title: error.message,
+						type: 'warning',
+					})
+				})
+				NET.request(API.getVenueList, uni.getStorageSync('locationData'), 'POST').then(res => {
 					this.venueList = res.data
 				}).catch(error => {
 					this.$refs.uTips.show({
-						title: '获取首页场馆列表失败',
+						title: error.message,
 						type: 'warning',
 					})
 				})
-				NET.request(API.getVideoList, {
-					longitude: this.longitude,
-					latitude: this.latitude,
-				}, 'POST').then(res => {
+				NET.request(API.getVideoList, uni.getStorageSync('locationData'), 'POST').then(res => {
 					this.videoList = res.data
 				}).catch(error => {
 					this.$refs.uTips.show({
-						title: '获取首页精彩瞬间列表失败',
+						title: error.message,
 						type: 'warning',
 					})
 				})
@@ -127,11 +158,18 @@
 			}
 		}
 
-		.title-box {
-			width: 100vw;
-			padding: 10px 15px 5px 15px;
-			float: left;
-			box-sizing: border-box;
+		.section-title {
+			width: 100%;
+			height: 28px;
+			display: flex;
+			align-items: center;
+			margin-top: 20px;
+			padding: 0 15px;
+
+			u-section {
+				margin-left: 10px;
+				flex: 1;
+			}
 		}
 
 		.venue-box {
@@ -141,44 +179,34 @@
 			overflow-x: auto;
 			white-space: nowrap;
 
+			/deep/.u-card--border:after {
+				border-color: #cccccc;
+				border-radius: 15px;
+			}
+
 			.venue-card {
+				min-width: 70vw;
 				display: inline-block;
 
-				/deep/.u-border:after {
-					border-radius: 20px !important;
-					border-color: #999999;
-				}
-
 				.venue-content {
-					padding: 5px 15px;
-				}
-
-				.venue-type {
-					height: 20px;
-					display: inline-block;
-					padding: 0 10px;
-					margin-right: 5px;
-					background-color: $mainColor;
-					border-radius: 10px;
-					line-height: 20px;
-					color: #FFFFFF;
-					font-weight: bold;
-				}
-
-				.venue-name {
-					height: 20px;
-					display: inline-block;
-					font-weight: bold;
-					font-size: 14px;
-					line-height: 20px;
-				}
-
-				.venue-distance {
-					color: #999999;
-				}
-
-				.venue-address {
-					color: #999999;
+					padding: 0px 25px 10px 15px;
+
+					.venue-name {
+						height: 20px;
+						font-weight: bold;
+						font-size: 15px;
+						line-height: 20px;
+					}
+
+					.info-text {
+						color: #999999;
+						line-height: 18px;
+
+						/deep/.u-icon {
+							margin-right: 5px;
+							font-size: 14px;
+						}
+					}
 				}
 			}
 		}
@@ -194,8 +222,22 @@
 				margin: 0 8px 16px 8px;
 				float: left;
 
+				.video-col {
+					width: 100%;
+					height: 30vw;
+					float: left;
+						border-radius: 10px;
+						overflow: hidden;
+
+					video {
+						width: 100%;
+						height: 30vw;
+					}
+				}
+
 				.video-name {
 					width: 100%;
+					float: left;
 					text-align: center;
 					line-height: 20px;
 					font-size: 14px;

+ 169 - 10
pages/login/index.vue

@@ -1,30 +1,189 @@
 <template>
 	<view class="content">
-		login
+		<u-image :src="logo" mode="aspectFit" width="208rpx" height="272rpx" class="logo"></u-image>
+		<u-card :show-head="false" :show-foot="false" padding="40" margin="40rpx 40rpx" borderRadius="40" box-shadow="0 0 8px rgba(0, 0, 0, 0.2)"
+		 class="card-box">
+			<view slot="body">
+				<u-cell-group :border="false">
+					<u-cell-item icon="account" icon-size="46" :icon-style="iconStyle" :arrow="false">
+						<u-input v-model="account" />
+					</u-cell-item>
+					<u-cell-item icon="lock" icon-size="46" :icon-style="iconStyle" :arrow="false">
+						<u-input v-model="password" type="password" :password-icon="true" />
+					</u-cell-item>
+				</u-cell-group>
+				<u-button type="warning" :ripple="true" :custom-style="{...customStyle, margin: '10px 0'}" @click="login()">登录</u-button>
+				<u-button type="warning" :ripple="true" :custom-style="{...customStyle, margin: '10px 0'}" @click="login1()">app微信授权登录</u-button>
+				<u-button type="warning" :ripple="true" :custom-style="{...customStyle, backgroundColor: '#07c160'}" open-type="getUserInfo"
+				 @getuserinfo="getUserinfoWechat" withCredentials="true">微信一键登录</u-button>
+			</view>
+		</u-card>
 		<u-top-tips ref="uTips"></u-top-tips>
 	</view>
 </template>
 
 <script>
+	import {
+		mapGetters
+	} from 'vuex'
 	const NET = require('@/utils/request')
 	const API = require('@/config/api')
 	export default {
+		computed: {
+			...mapGetters([
+				'customStyle',
+			])
+		},
 		data() {
-			return {}
+			return {
+				logo: API.getServerImg + 'logo.png',
+				account: '',
+				password: '',
+				iconStyle: {
+					color: '#999999',
+					marginRight: '10px'
+				}
+			}
 		},
 		onLoad() {},
-		methods: {}
+		methods: {
+			login() {
+				if (!this.account || !this.password) {
+					this.$refs.uTips.show({
+						title: '请输入账号密码',
+						type: 'warning',
+					})
+					return
+				}
+				NET.request(API.loginByPassword, {
+					phone: this.account,
+					pwd: this.password,
+				}, 'POST').then(res => {
+					uni.setStorage({
+						key: 'token',
+						data: res.data.token
+					})
+					uni.setStorage({
+						key: 'userData',
+						data: {
+							headImage: res.data.url,
+							userId: res.data.id,
+							nickName: res.data.nickName,
+							userName: res.data.username,
+							phone: res.data.phone,
+						}
+					})
+					uni.reLaunch({
+						url: '/pages/index/index'
+					})
+				}).catch(error => {
+					this.$refs.uTips.show({
+						title: '登录失败',
+						type: 'warning',
+					})
+				})
+			},
+			login1() {
+				let that = this
+				uni.login({
+					provider: 'weixin',
+					success: function(loginRes) {
+						uni.getUserInfo({
+							provider: 'weixin',
+							success: function(infoRes) {
+							}
+						});
+					}
+				});
+			},
+			getUserinfoWechat(data) {
+				uni.getProvider({
+					service: 'oauth',
+					success: (res) => {
+						if (~res.provider.indexOf('weixin')) {
+							uni.login({
+								provider: 'weixin',
+								success: (res2) => {
+									let wxLoginData = {
+										code: res2.code,
+										encryptedData: data.detail.encryptedData,
+										iv: data.detail.iv,
+										shareParams: uni.getStorageSync('shareParams')
+									}
+									uni.setStorage({
+										key: 'wxLoginData',
+										data: wxLoginData
+									})
+									this.getUserInfo(wxLoginData)
+								},
+								fail: () => {
+									this.$refs.uTips.show({
+										title: '微信登录授权失败',
+										type: 'warning',
+									})
+								}
+							})
+						} else {
+							this.$refs.uTips.show({
+								title: '请先安装微信或升级版本',
+								type: 'warning',
+							})
+						}
+					}
+				});
+			},
+			// 发请求获取个人数据
+			getUserInfo(wxLoginData) {
+				NET.request(API.wxLogin, wxLoginData, 'POST').then(res => {
+					uni.setStorage({
+						key: 'token',
+						data: res.data.token
+					})
+					uni.setStorage({
+						key: 'userData',
+						data: {
+							headImage: res.data.url,
+							userId: res.data.id,
+							nickName: res.data.nickName,
+							userName: res.data.username,
+							phone: res.data.phone,
+						}
+					})
+					uni.reLaunch({
+						url: '/pages/index/index'
+					})
+				}).catch(error => {
+					this.$refs.uTips.show({
+						title: error.message,
+						type: 'warning',
+					})
+				})
+			},
+		}
 	}
 </script>
 
-<style lang='scss'>
-	page {
-		width: 100%;
-		height: 100%;
-	}
-
+<style lang="scss" scoped>
 	.content {
 		width: 100%;
-		height: 100%;
+		height: 100vh;
+		padding: 480rpx 0 60px 0;
+		float: left;
+
+		.logo {
+			top: 140rpx;
+			left: 50%;
+			transform: translateX(-50%);
+			position: absolute;
+		}
+
+		.card-box {
+			/deep/.u-cell {
+				border: 1px solid #eeeeee;
+				border-radius: 8px;
+				padding: 8px 10px;
+				margin-bottom: 16px;
+			}
+		}
 	}
 </style>

+ 14 - 9
pages/member/index.vue

@@ -8,7 +8,7 @@
 				 :refresher-triggered="triggered" :refresher-threshold="100" refresher-background="white" @refresherrefresh="onRefresh"
 				 @refresherrestore="onRestore">
 					<u-card :head-border-bottom="false" :foot-border-top="false" padding="0px" margin="10px" borderRadius="40" v-for="(site, index2) in item.tableList"
-					 :key="index" class="class-card" @click="goToMyClass(site)">
+					 :key="index2" class="class-card" @click="goToMyClass(site)">
 						<view class="class-content" slot="head" style="padding-top: 10px;">
 							<view class="student-name">{{site.studentName}}</view>
 							<view class="class-name">{{site.name}}</view>
@@ -25,8 +25,9 @@
 						</view>
 						<view class="class-content" slot="foot" style="padding-bottom: 10px;text-align: right;">
 							<u-button type="default" shape="circle" :ripple="true" :custom-style="handleDefaultCustomStyle" size="mini"
-							 :hair-line="false" plain @click.stop="goToLeave(site)">请假</u-button>
-							<u-button type="warning" shape="circle" :ripple="true" :custom-style="handleCustomStyle" size="mini" @click.stop="goToEvaluate(site)">评价</u-button>
+							 :hair-line="false" plain @click.stop="goToLeave(site)" v-if="index1 != 2">请假</u-button>
+							<u-button type="warning" shape="circle" :ripple="true" :custom-style="handleCustomStyle" size="mini" @click.stop="goToEvaluate(site)"
+							 v-if="site.isEvaluate == 0 && index1 == 2">评价</u-button>
 						</view>
 					</u-card>
 					<u-divider v-if="item.isOver" bg-color="transparent">没有更多了</u-divider>
@@ -75,11 +76,15 @@
 			}
 		},
 		onLoad() {
-			this.getTableList(0)
 			this.getTableList(1)
 			this.getTableList(2)
 		},
-		onReady() {},
+		onShow() {
+			this.tabList[this.current].isOver = false
+			this.tabList[this.current].pageIndex = 1
+			this.tabList[this.current].tableList = []
+			this.getTableList(this.current)
+		},
 		methods: {
 			//  tab页面切换
 			tabsChange(index) {
@@ -125,12 +130,12 @@
 					size: 10,
 				}, 'POST').then(res => {
 					this.triggered = false
-					this.tabList[index].tableList = this.tabList[index].tableList.concat(res.data.list)
-					this.tabList[index].isOver = res.data.list.length != 10
+					this.tabList[index].tableList = this.tabList[index].tableList.concat(res.data.row)
+					this.tabList[index].isOver = res.data.row.length != 10
 				}).catch(error => {
 					this.triggered = false
 					this.$refs.uTips.show({
-						title: error.data.msg,
+						title: error.message,
 						type: 'warning',
 					})
 				})
@@ -138,7 +143,7 @@
 			//  跳转请假界面
 			goToLeave(site) {
 				uni.navigateTo({
-					url: '/pagesMember/leaveForm?id=' + site.id
+					url: '/pagesMember/leaveForm?id=' + site.id + '&studentId=' +site.studentId
 				});
 			},
 			//  跳转评价表单

+ 153 - 84
pages/user/index.vue

@@ -2,28 +2,43 @@
 	<view class="content">
 		<view class="user-info">
 			<view class="user-data">
-				<view class="user-name">自行车</view>
-				<view class="user-phone">234567865</view>
+				<view class="user-name">{{userData.nickName}}</view>
+				<view class="user-phone">{{userData.phone}}</view>
 			</view>
 			<view class="user-img">
-				<u-avatar :src="src" size="160"></u-avatar>
+				<u-avatar :src="userData.headImage" size="160"></u-avatar>
 			</view>
 		</view>
-		<view class="member-card" @click="goToMemberCard()">
-			<view class="member-info">
-				<view class="member-title">我的账号</view>
-				<view class="member-text">您目前尚未开通会员</view>
+		<scroll-view scroll-x class="member-box">
+			<view class="member-card" @click="goToMemberCard()" v-if="memberInfo.status == 0">
+				<view class="member-info">
+					<view class="member-title">我的账号</view>
+					<view class="member-text">您目前尚未开通会员</view>
+				</view>>
+				<view class="member-handle">立即开通&nbsp;<u-icon name="arrow-right"></u-icon>
+				</view>
 			</view>
-			<view class="member-handle">
-				立即开通&nbsp;
-				<u-icon name="arrow-right"></u-icon>
-			</view>
-		</view>
+			<template v-else>
+				<view class="member-card" @click="goToMemberCard()" v-for="(item, index) in studentList" :key="index">
+					<view class="member-info">
+						<view class="member-title">我的账号</view>
+						<view class="member-text">
+							<view>{{item.studentName}}&nbsp;剩余&nbsp;{{item.days}}&nbsp;天</view>
+						</view>
+					</view>
+					<view class="member-handle">立即续费&nbsp;<u-icon name="arrow-right"></u-icon>
+					</view>
+				</view>
+			</template>
+		</scroll-view>
 		<view class="user-handle" v-for="(item, index) in handleList" :key="index" @click="goToHandle(item)">
 			<view class="handle-icon">
-				<view class="iconfont" :class="item.icon"></view>
+				<u-image :src="item.icon" mode="aspectFit" width="28px" height="28px"></u-image>
+			</view>
+			<view class="handle-label">
+				<!-- <button type="primary" open-type="share" @click="share" v-if="item.path == 'share'" class="share-text">{{item.label}}</button> -->
+				<text>{{item.label}}</text>
 			</view>
-			<view class="handle-label">{{item.label}}</view>
 			<view class="handle-arrow">
 				<u-icon name="arrow-right" color="#cccccc" size="32"></u-icon>
 			</view>
@@ -38,41 +53,74 @@
 	export default {
 		data() {
 			return {
-				src: '',
+				userData: {
+					headImage: '',
+					userId: '',
+					nickName: '',
+					userName: '',
+					phone: '',
+				},
+				memberInfo: {
+					lastDays: 0,
+					status: 0,
+				},
 				handleList: [{
 						label: '订单管理',
 						path: 'orderList',
-						icon: 'icondingdan'
+						icon: API.getServerImg + 'dingdanguanli.png'
 					},
 					{
 						label: '学员信息',
 						path: 'studentList',
-						icon: 'iconxueyuanxinxi'
+						icon: API.getServerImg + 'xueyuanxinxi.png'
 					},
 					{
 						label: '我的优惠券',
 						path: 'couponList',
-						icon: 'iconyouhuiquan'
+						icon: API.getServerImg + 'youhiquan.png'
 					},
 					{
 						label: '分享有礼',
-						path: 'share',
-						icon: 'iconliwu'
+						path: 'shareInfo',
+						icon: API.getServerImg + 'liwu.png'
 					},
 					{
 						label: '我的评价',
 						path: 'evaluateList',
-						icon: 'iconpingjia'
+						icon: API.getServerImg + 'pingjia.png'
 					},
 					{
 						label: '预约体验',
-						path: '',
-						icon: 'iconyuyueshijian'
+						path: 'subscribeList',
+						icon: API.getServerImg + 'yuyue.png'
 					},
-				]
+				],
+				studentList: []
+			}
+		},
+		onLoad() {
+			if (uni.getStorageSync('userData')) {
+				this.userData = uni.getStorageSync('userData')
 			}
+			NET.request(API.getMemberInfo, {}, 'POST').then(res => {
+				this.memberInfo = res.data
+			}).catch(error => {
+				this.$refs.uTips.show({
+					title: error.message,
+					type: 'warning',
+				})
+			})
+		},
+		onShow() {
+			NET.request(API.getAllStudentList, {}, 'POST').then(res => {
+				this.studentList = res.data
+			}).catch(error => {
+				this.$refs.uTips.show({
+					title: error.message,
+					type: 'warning',
+				})
+			})
 		},
-		onLoad() {},
 		methods: {
 			//  跳转开通会员
 			goToMemberCard() {
@@ -82,25 +130,25 @@
 			},
 			//  跳转我的各列表界面
 			goToHandle(site) {
-				if (site.path == 'share') {
-					uni.share({
-						provider: "weixin",
-						scene: "WXSceneSession",
-						type: 1,
-						summary: "我正在使用HBuilderX开发uni-app,赶紧跟我一起来体验!",
-						success: function(res) {
-							console.log("success:" + JSON.stringify(res));
-						},
-						fail: function(err) {
-							console.log("fail:" + JSON.stringify(err));
-						}
-					});
-				} else {
-					uni.navigateTo({
-						url: '/pagesMain/' + site.path
-					});
-				}
+				uni.navigateTo({
+					url: '/pagesMain/' + site.path
+				});
 			},
+			//  分享
+			share() {
+				uni.share({
+					provider: "weixin",
+					scene: "WXSceneSession",
+					type: 1,
+					summary: "我正在使用HBuilderX开发uni-app,赶紧跟我一起来体验!",
+					success: function(res) {
+						console.log("success:" + JSON.stringify(res));
+					},
+					fail: function(err) {
+						console.log("fail:" + JSON.stringify(err));
+					}
+				});
+			}
 		}
 	}
 </script>
@@ -157,45 +205,52 @@
 			}
 		}
 
-		.member-card {
-			width: calc(100vw - 30px);
+		.member-box {
+			white-space: nowrap;
 			float: left;
-			border-radius: 10px;
-			background-color: $mainColor;
-			padding: 15px;
-			margin: 0 15px 20px 15px;
-			position: relative;
-
-			.member-info {
-				width: calc(100% - 100px);
-				float: left;
+			width: 100vw;
+			height: 92px;
 
-				.member-title {
-					font-size: 18px;
-					line-height: 20px;
-					color: #FFFFFF;
-					font-weight: bold;
-				}
+			.member-card {
+				width: calc(100vw - 30px);
+				display: inline-block;
+				border-radius: 10px;
+				background-color: $mainColor;
+				padding: 15px;
+				margin: 0 15px 20px 15px;
+				position: relative;
 
-				.member-text {
-					margin-top: 5px;
-					line-height: 16px;
-					color: #FFFFFF;
+				.member-info {
+					width: calc(100% - 100px);
+					float: left;
+
+					.member-title {
+						font-size: 18px;
+						line-height: 20px;
+						color: #FFFFFF;
+						font-weight: bold;
+					}
+
+					.member-text {
+						margin-top: 5px;
+						line-height: 16px;
+						color: #FFFFFF;
+					}
 				}
-			}
 
-			.member-handle {
-				width: 90px;
-				height: 30px;
-				margin-top: 6px;
-				float: right;
-				background-color: #FFFFFF;
-				border-radius: 20px;
-				font-size: 13px;
-				color: $mainColor;
-				text-align: center;
-				font-weight: bold;
-				line-height: 30px;
+				.member-handle {
+					width: 90px;
+					height: 30px;
+					margin-top: 6px;
+					float: right;
+					background-color: #FFFFFF;
+					border-radius: 20px;
+					font-size: 13px;
+					color: $mainColor;
+					text-align: center;
+					font-weight: bold;
+					line-height: 30px;
+				}
 			}
 		}
 
@@ -205,31 +260,45 @@
 			float: left;
 			padding: 0 15px;
 			margin-bottom: 10px;
+			display: flex;
+			align-items: center;
 
 			.handle-icon {
 				width: 40px;
 				height: 40px;
-				float: left;
 				text-align: center;
 				line-height: 40px;
-
-				.iconfont {
-					font-size: 28px;
-				}
+				display: flex;
+				align-items: center;
 			}
 
 			.handle-label {
-				width: calc(100% - 70px);
 				height: 40px;
+				flex: 1;
 				margin-left: 10px;
-				float: left;
 				line-height: 40px;
 				font-size: 15px;
+				position: relative;
 			}
 
 			.handle-arrow {
 				line-height: 40px;
 			}
+
+			.share-text {
+				width: 100vw;
+				padding: 0 65px;
+				font-size: 16px;
+				text-align: left;
+				color: #303133;
+				background-color: transparent;
+				position: absolute;
+				left: -65px;
+			}
+
+			.share-text:after {
+				border: none;
+			}
 		}
 	}
 </style>

+ 6 - 3
pagesMain/couponList.vue

@@ -118,12 +118,12 @@
 					size: 10,
 				}, 'POST').then(res => {
 					this.triggered = false
-					this.tabList[index].tableList = this.tabList[index].tableList.concat(res.data.list)
-					this.tabList[index].isOver = res.data.list.length != 10
+					this.tabList[index].tableList = this.tabList[index].tableList.concat(res.data.row)
+					this.tabList[index].isOver = res.data.row.length != 10
 				}).catch(error => {
 					this.triggered = false
 					this.$refs.uTips.show({
-						title: error.data.msg,
+						title: error.message,
 						type: 'warning',
 					})
 				})
@@ -155,6 +155,8 @@
 				.scroll-box {
 					width: 100%;
 					height: calc(100vh - 34px);
+					padding-bottom: 10px;
+					box-sizing: border-box;
 
 					.class-card {
 						.class-content {
@@ -178,6 +180,7 @@
 							font-size: 16px;
 							color: #000000;
 							word-break: break-all;
+							margin-bottom: 5px;
 						}
 
 						.class-info-text {

+ 6 - 5
pagesMain/evaluateList.vue

@@ -3,7 +3,7 @@
 		<scroll-view scroll-y class="scroll-box" @scrolltolower="handleLoadMore" :refresher-enabled="true"
 		 :refresher-triggered="triggered" :refresher-threshold="100" refresher-background="white" @refresherrefresh="onRefresh"
 		 @refresherrestore="onRestore">
-			<u-card :head-border-bottom="false" :foot-border-top="false" padding="0px" margin="10px" borderRadius="40" v-for="(item, index) in tableList"
+			<u-card :head-border-bottom="false" padding="0px" margin="10px" borderRadius="40" v-for="(item, index) in tableList"
 			 :key="index" class="class-card">
 				<view class="class-content" slot="head" style="padding-top: 10px;">
 					<view class="student-name">{{item.studentName}}</view>
@@ -85,12 +85,12 @@
 					size: 10,
 				}, 'POST').then(res => {
 					this.triggered = false
-					this.tableList = this.tableList.concat(res.data.list)
-					this.isOver = res.data.list.length != 10
+					this.tableList = this.tableList.concat(res.data.row)
+					this.isOver = res.data.row.length != 10
 				}).catch(error => {
 					this.triggered = false
 					this.$refs.uTips.show({
-						title: error.data.msg,
+						title: error.message,
 						type: 'warning',
 					})
 				})
@@ -116,9 +116,10 @@
 		.scroll-box {
 			width: 100%;
 			height: 100vh;
+			padding-bottom: 10px;
+			box-sizing: border-box;
 
 			.class-card {
-
 				.class-content {
 					padding: 5px 15px;
 				}

+ 1 - 1
pagesMain/memberCardList.vue

@@ -35,7 +35,7 @@
 					this.tableList = res.data
 				}).catch(error => {
 					this.$refs.uTips.show({
-						title: error.data.msg,
+						title: error.message,
 						type: 'warning',
 					})
 				})

+ 66 - 11
pagesMain/openMember.vue

@@ -8,6 +8,7 @@
 		<u-cell-group style="width: 100%; float: left;">
 			<u-cell-item title="使用时间" :value="memberInfo.startDate + '~' + memberInfo.endDate" :arrow="false"></u-cell-item>
 			<u-cell-item title="优惠金额" :value="couponId ? '-¥' + memberInfo.discountsAmount : ''" @click="couponShow = true"></u-cell-item>
+			<u-cell-item title="学员姓名" :value="studentName" @click="studentShow = true"></u-cell-item>
 			<u-cell-item title="实际金额" :value="'¥' + memberInfo.realPayAmount" :arrow="false"></u-cell-item>
 		</u-cell-group>
 		<u-popup v-model="couponShow" mode="bottom" border-radius="30" closeable>
@@ -30,6 +31,17 @@
 		<view class="handle-fix-box">
 			<u-button type="warning" shape="circle" :ripple="true" :custom-style="customStyle" @click="toPay()">确定支付¥{{memberInfo.realPayAmount}}</u-button>
 		</view>
+		<u-popup v-model="studentShow" mode="bottom" border-radius="30">
+			<scroll-view scroll-y class="student-box">
+				<u-card :title="item.studentName" title-size="32" :head-style="cardStyle" :head-border-bottom="false" :show-foot="false"
+				 margin="10px" borderRadius="20" v-for="(item, index) in studentList" :key="index" @click="selectStudent(item)">
+					<view class="student-card" slot="body">
+						<view class="class-info-text">性别:{{item.sex}}&nbsp;&nbsp;年龄:{{item.age}}</view>
+					</view>
+				</u-card>
+			</scroll-view>
+			<u-button type="warning" shape="circle" :ripple="true" :custom-style="{...customStyle,margin:'15px'}" @click="goToSubscribelForm()">新增学员</u-button>
+		</u-popup>
 		<u-top-tips ref="uTips"></u-top-tips>
 	</view>
 </template>
@@ -61,13 +73,29 @@
 				couponId: '',
 				couponShow: false,
 				couponList: [],
+				cardStyle: {
+					fontWeight: 'bold'
+				},
+				studentId: '',
+				studentName: '',
+				studentShow: false,
+				studentList: [],
 			}
 		},
 		onLoad(options) {
 			this.memberCardId = options.id
 			this.getMemberInfo()
 		},
-		onReady() {},
+		onShow() {
+			NET.request(API.getAllStudentList, {}, 'POST').then(res => {
+				this.studentList = res.data
+			}).catch(error => {
+				this.$refs.uTips.show({
+					title: error.message,
+					type: 'warning',
+				})
+			})
+		},
 		methods: {
 			//  获取数据
 			getMemberInfo() {
@@ -77,17 +105,17 @@
 					this.memberInfo = res.data
 				}).catch(error => {
 					this.$refs.uTips.show({
-						title: error.data.msg,
+						title: error.message,
 						type: 'warning',
 					})
 				})
 				NET.request(API.getUsableCouponList, {
 					id: this.memberCardId
 				}, 'POST').then(res => {
-					this.couponList = res.data
+					this.couponList = res.data.row
 				}).catch(error => {
 					this.$refs.uTips.show({
-						title: error.data.msg,
+						title: error.message,
 						type: 'warning',
 					})
 				})
@@ -96,24 +124,35 @@
 			selectCoupon(item) {
 				this.couponId = item.id
 				NET.request(API.getMemberCardInfoAfterCoupon, {
-					id: this.memberCardId,
+					memberId: this.memberCardId,
 					couponId: this.couponId
 				}, 'POST').then(res => {
 					this.memberInfo = res.data
 					this.couponShow = false
 				}).catch(error => {
 					this.$refs.uTips.show({
-						title: error.data.msg,
+						title: error.message,
 						type: 'warning',
 					})
 				})
 			},
+			//  选择学员
+			selectStudent(item) {
+				this.studentId = item.studentId
+				this.studentName = item.studentName
+				this.studentShow = false
+			},
 			//  支付
 			toPay() {
 				NET.request(API.getPayParams, {
 					id: this.memberCardId,
-					couponId: this.couponId
+					couponId: this.couponId,
+					studentId: this.studentId,
 				}, 'POST').then(res => {
+					if (this.memberInfo.realPayAmount <= 0) {
+						this.goToPayResult(res.data.oderNo)
+						return false
+					}
 					uni.requestPayment({
 						provider: 'wxpay',
 						timeStamp: res.data.timeStamp,
@@ -122,9 +161,7 @@
 						signType: res.data.signType,
 						paySign: res.data.paySign,
 						success: (payRes) => {
-							uni.redirectTo({
-								url: '/pagesMain/payResult?id=' + res.data.oderNo
-							});
+							this.goToPayResult(res.data.oderNo)
 						},
 						fail: (error) => {
 							this.$refs.uTips.show({
@@ -135,11 +172,17 @@
 					})
 				}).catch(error => {
 					this.$refs.uTips.show({
-						title: error.data.msg,
+						title: error.message,
 						type: 'warning',
 					})
 				})
 			},
+			//  跳转支付结果
+			goToPayResult(oderNo) {
+				uni.redirectTo({
+					url: '/pagesMain/payResult?id=' + oderNo
+				});
+			}
 		},
 	}
 </script>
@@ -226,5 +269,17 @@
 				margin-bottom: 5px;
 			}
 		}
+
+		.student-box {
+			max-height: 200px;
+			padding: 0 15px;
+			margin: 25px 0 0 0;
+			box-sizing: border-box;
+			overflow: auto;
+
+			/deep/.u-card__head {
+				padding-bottom: 0px !important;
+			}
+		}
 	}
 </style>

+ 5 - 4
pagesMain/orderList.vue

@@ -79,12 +79,12 @@
 					size: 10,
 				}, 'POST').then(res => {
 					this.triggered = false
-					this.tableList = this.tableList.concat(res.data.list)
-					this.isOver = res.data.list.length != 10
+					this.tableList = this.tableList.concat(res.data.row)
+					this.isOver = res.data.row.length != 10
 				}).catch(error => {
 					this.triggered = false
 					this.$refs.uTips.show({
-						title: error.data.msg,
+						title: error.message,
 						type: 'warning',
 					})
 				})
@@ -110,9 +110,10 @@
 		.scroll-box {
 			width: 100%;
 			height: 100vh;
+			padding-bottom: 10px;
+			box-sizing: border-box;
 
 			.class-card {
-
 				.class-content {
 					padding: 5px 15px;
 				}

+ 1 - 1
pagesMain/payResult.vue

@@ -42,7 +42,7 @@
 				this.payResult = res.data.status
 			}).catch(error => {
 				this.$refs.uTips.show({
-					title: error.data.msg,
+						title: error.message,
 					type: 'warning',
 				})
 			})

+ 60 - 0
pagesMain/shareInfo.vue

@@ -0,0 +1,60 @@
+<template>
+	<view class="content">
+		<u-image width="60vw" height="60vw" :src="shareUrl" class="share-img"></u-image>
+		<u-top-tips ref="uTips"></u-top-tips>
+	</view>
+</template>
+
+<script>
+	import {
+		mapGetters
+	} from 'vuex'
+	const NET = require('@/utils/request')
+	const API = require('@/config/api')
+	export default {
+		computed: {
+			...mapGetters([
+				'mainColor'
+			])
+		},
+		data() {
+			return {
+				shareUrl: ''
+			}
+		},
+		onLoad() {
+			this.getData()
+		},
+		onReady() {},
+		methods: {
+			//  获取数据
+			getData() {
+				NET.request(API.getShareUrl, {}, 'POST').then(res => {
+					this.shareUrl = res.data
+				}).catch(error => {
+					this.$refs.uTips.show({
+						title: error.message,
+						type: 'warning',
+					})
+				})
+			}
+		},
+	}
+</script>
+<style lang="scss" scoped>
+	@import "@/static/css/themes.scss";
+
+	.content {
+		width: 100%;
+		height: 100vh;
+		float: left;
+		position: relative;
+
+		.share-img {
+			top: 40%;
+			left: 50%;
+			transform: translate(-50%, -50%);
+			position: absolute;
+		}
+	}
+</style>

+ 5 - 3
pagesMain/studentList.vue

@@ -77,12 +77,12 @@
 					size: 10,
 				}, 'POST').then(res => {
 					this.triggered = false
-					this.tableList = this.tableList.concat(res.data.list)
-					this.isOver = res.data.list.length != 10
+					this.tableList = this.tableList.concat(res.data.row)
+					this.isOver = res.data.row.length != 10
 				}).catch(error => {
 					this.triggered = false
 					this.$refs.uTips.show({
-						title: error.data.msg,
+						title: error.message,
 						type: 'warning',
 					})
 				})
@@ -114,6 +114,8 @@
 		.scroll-box {
 			width: 100%;
 			height: calc(100vh - 60px);
+			padding-bottom: 10px;
+			box-sizing: border-box;
 
 			.class-card {
 

+ 161 - 0
pagesMain/subscribeList.vue

@@ -0,0 +1,161 @@
+<template>
+	<view class="content">
+		<scroll-view scroll-y class="scroll-box" @scrolltolower="handleLoadMore" :refresher-enabled="true"
+		 :refresher-triggered="triggered" :refresher-threshold="100" refresher-background="white" @refresherrefresh="onRefresh"
+		 @refresherrestore="onRestore">
+			<u-card :head-border-bottom="false" padding="0px" margin="10px" borderRadius="40" v-for="(item, index) in tableList"
+			 :key="index" class="class-card">
+				<view class="class-content" slot="head" style="padding-top: 10px;">
+					<view class="student-name">{{item.studentName}}</view>
+					<view class="class-name">{{item.name}}</view>
+				</view>
+				<view class="class-content" slot="body">
+					<view class="class-info-text">
+						<u-icon name="clock"></u-icon>
+						{{item.classStartDate}}&nbsp;&nbsp;{{item.classStartHours}}&nbsp;&nbsp;{{item.residue}}课时
+					</view>
+					<view class="class-info-text">
+						<u-icon name="map"></u-icon>
+						{{item.address}}
+					</view>
+				</view>
+				<view class="class-foot" slot="foot">
+					<u-button type="default" shape="circle" :ripple="true" :custom-style="handleDefaultCustomStyle" size="mini"
+					 :hair-line="false" plain>已预约</u-button>
+				</view>
+			</u-card>
+			<u-divider v-if="isOver" bg-color="transparent">没有更多了</u-divider>
+		</scroll-view>
+		<u-top-tips ref="uTips"></u-top-tips>
+	</view>
+</template>
+
+<script>
+	import {
+		mapGetters
+	} from 'vuex'
+	const NET = require('@/utils/request')
+	const API = require('@/config/api')
+	export default {
+		computed: {
+			...mapGetters([
+				'handleDefaultCustomStyle',
+			])
+		},
+		data() {
+			return {
+				triggered: false,
+				isOver: false,
+				pageIndex: 1,
+				tableList: [],
+			}
+		},
+		onLoad() {
+			this.getTableList()
+		},
+		onReady() {},
+		methods: {
+			//  下拉刷新
+			onRefresh() {
+				this.triggered = true
+				this.isOver = false
+				this.pageIndex = 1
+				this.tableList = []
+				this.getTableList()
+			},
+			//  重置下拉刷新状态
+			onRestore() {
+				this.triggered = 'restore'
+				this.triggered = false
+			},
+			//  懒加载
+			handleLoadMore() {
+				if (!this.isOver) {
+					this.pageIndex++
+					this.getTableList()
+				}
+			},
+			//  获取列表数据
+			getTableList() {
+				NET.request(API.getSubscribeList, {
+					page: this.pageIndex,
+					size: 10,
+				}, 'POST').then(res => {
+					this.triggered = false
+					this.tableList = this.tableList.concat(res.data.row)
+					this.isOver = res.data.row.length != 10
+				}).catch(error => {
+					this.triggered = false
+					this.$refs.uTips.show({
+						title: error.message,
+						type: 'warning',
+					})
+				})
+			}
+		},
+	}
+</script>
+
+<style>
+	page {
+		width: 100%;
+		height: 100%;
+		background-color: #f7f7f7;
+	}
+</style>
+<style lang="scss" scoped>
+	@import "@/static/css/themes.scss";
+
+	.content {
+		width: 100%;
+		float: left;
+
+		.scroll-box {
+			width: 100%;
+			height: 100vh;
+			padding-bottom: 10px;
+			box-sizing: border-box;
+
+			.class-card {
+				.class-content {
+					padding: 5px 15px;
+				}
+
+				.student-name {
+					height: 20px;
+					display: inline-block;
+					padding: 0 10px;
+					margin-right: 5px;
+					background-color: $mainColor;
+					border-radius: 10px;
+					line-height: 20px;
+					color: #FFFFFF;
+				}
+
+				.class-name {
+					height: 20px;
+					display: inline-block;
+					font-weight: bold;
+					font-size: 14px;
+					line-height: 20px;
+				}
+
+				.class-info-text {
+					color: #999999;
+					margin-bottom: 5px;
+
+					/deep/.u-icon {
+						margin-right: 5px;
+						font-size: 14px;
+						color: #000000;
+					}
+				}
+			}
+
+			.class-foot {
+				padding: 10px 15px;
+				text-align: right;
+			}
+		}
+	}
+</style>

+ 0 - 79
pagesMain/subscribelSuccess.vue

@@ -1,79 +0,0 @@
-<template>
-	<view class="content">
-		<view class="success-title">预约成功</view>
-		<view class="success-icon">
-			<u-icon name="checkmark-circle-fill" color="#19be6b" size="156"></u-icon>
-		</view>
-		<view class="success-text">课程预约成功,稍后我们会联系您</view>
-		<view class="handle-fix-box">
-			<u-button type="warning" shape="circle" :ripple="true" :custom-style="customStyle" @click="goBack()">返回</u-button>
-		</view>
-		<u-top-tips ref="uTips"></u-top-tips>
-	</view>
-</template>
-
-<script>
-	import {
-		mapGetters
-	} from 'vuex'
-	export default {
-		computed: {
-			...mapGetters([
-				'customStyle',
-			])
-		},
-		data() {
-			return {}
-		},
-		onLoad() {},
-		onReady() {},
-		methods: {
-			//  返回
-			goBack() {
-				uni.navigateBack()
-			},
-		},
-	}
-</script>
-
-<style>
-	page {
-		width: 100%;
-		height: 100%;
-		position: relative;
-	}
-</style>
-<style lang="scss" scoped>
-	@import "@/static/css/themes.scss";
-	.content {
-		width: 100%;
-		float: left;
-		padding: 0 15px 60px 15px;
-		box-sizing: border-box;
-
-		.success-title {
-			width: 100%;
-			height: 64px;
-			float: left;
-			line-height: 48px;
-			font-size: 28px;
-			text-align: center;
-		}
-
-		.success-icon {
-			width: 100%;
-			float: left;
-			text-align: center;
-		}
-
-		.success-text {
-			width: 100%;
-			height: 20px;
-			float: left;
-			line-height: 20px;
-			font-size: 12px;
-			text-align: center;
-			margin-top: 20px;
-		}
-	}
-</style>

+ 128 - 12
pagesMember/classDetail.vue

@@ -21,12 +21,11 @@
 				</view>
 			</view>
 		</u-card>
-		<u-card title="班级简介" title-size="32" margin="0px 0px 10px 0px" :head-style="cardStyle">
+		<u-card title="班级简介" title-size="32" :show-foot="true" margin="0px 0px 10px 0px" :head-style="cardStyle">
 			<view slot="body">
-				<view class="class-info-text">{{classInfo.desc}}</view>
-			</view>
-			<view slot="foot" style="text-align: center;">
-				<u-icon name="arrow-down" size="34" color="" label="查看更多" label-pos="left"></u-icon>
+				<u-read-more :toggle="true" show-height="100" color="#333333" :shadow-style="shadowStyle">
+					<view class="class-info-text">{{classInfo.desc}}</view>
+				</u-read-more>
 			</view>
 		</u-card>
 		<u-card title="班级展示" sub-title="查看更多" :show-foot="false" title-size="32" margin="0px" :head-style="cardStyle">
@@ -37,10 +36,33 @@
 				</view>
 			</view>
 		</u-card>
+		<u-popup v-model="enlistShow" mode="bottom" border-radius="30" :closeable="true">
+			<scroll-view scroll-y class="student-box">
+				<u-card :title="item.studentName" title-size="32" :head-style="cardStyle" :head-border-bottom="false" :show-foot="false"
+				 margin="10px" borderRadius="20" v-for="(item, index) in studentList1" :key="index" @click="enlistStudent(item)">
+					<view class="student-card" slot="body">
+						<view class="class-info-text">性别:{{item.sex}}&nbsp;&nbsp;年龄:{{item.age}}</view>
+					</view>
+				</u-card>
+			</scroll-view>
+			<u-button type="warning" shape="circle" :ripple="true" :custom-style="{...customStyle,margin:'15px'}" @click="goToSubscribelForm()">新增学员</u-button>
+		</u-popup>
+		<u-popup v-model="subscribeShow" mode="bottom" border-radius="30">
+			<scroll-view scroll-y class="student-box">
+				<u-card :title="item.studentName" title-size="32" :head-style="cardStyle" :head-border-bottom="false" :show-foot="false"
+				 margin="10px" borderRadius="20" v-for="(item, index) in studentList2" :key="index" @click="subscribeStudent(item)">
+					<view class="student-card" slot="body">
+						<view class="class-info-text">性别:{{item.sex}}&nbsp;&nbsp;年龄:{{item.age}}</view>
+					</view>
+				</u-card>
+			</scroll-view>
+			<u-button type="warning" shape="circle" :ripple="true" :custom-style="{...customStyle,margin:'15px'}" @click="goToSubscribelForm()">新增学员</u-button>
+		</u-popup>
 		<view class="handle-fix-box">
-			<u-button type="warning" shape="circle" :ripple="true" :custom-style="customStyle" @click="goToSubscribelForm()">立即预约</u-button>
+			<u-button type="warning" shape="circle" :ripple="true" :custom-style="{...customStyle,...handleStyleLeft}" @click="subscribeShow = true">预约体验</u-button>
+			<u-button type="warning" shape="circle" :ripple="true" :custom-style="{...customStyle,...handleStyleRight}" @click="enlistShow = true">立即报名</u-button>
 		</view>
-		<u-top-tips ref="uTips"></u-top-tips>
+		<u-top-tips ref="uTips" zIndex="100000"></u-top-tips>
 	</view>
 </template>
 
@@ -71,16 +93,50 @@
 					desc: '',
 					showList: [],
 				},
+				handleStyleLeft: {
+					borderRadius: '40px 0 0 40px',
+					borderRight: '1px solid #ffffff'
+				},
+				handleStyleRight: {
+					borderRadius: '0 40px 40px 0',
+					borderLeft: '1px solid #ffffff'
+				},
 				cardStyle: {
 					fontWeight: 'bold'
-				}
+				},
+				shadowStyle: {
+					backgroundImage: 'linear-gradient(to bottom, transparent 80rpx, #ffffff 80rpx, #ffffff 100rpx)',
+					paddingTop: "100rpx",
+					marginTop: "-100rpx"
+				},
+				enlistShow: false,
+				studentList1: [],
+				subscribeShow: false,
+				studentList2: [],
 			}
 		},
 		onLoad(options) {
 			this.classId = options.id
 			this.initialize()
 		},
-		onReady() {},
+		onShow() {
+			NET.request(API.getEnlistAbleStudent, {}, 'POST').then(res => {
+				this.studentList1 = res.data.row
+			}).catch(error => {
+				this.$refs.uTips.show({
+					title: error.message,
+					type: 'warning',
+				})
+			})
+			NET.request(API.getSubscribeAbleList, {}, 'POST').then(res => {
+				this.studentList2 = res.data.row
+			}).catch(error => {
+				this.$refs.uTips.show({
+					title: error.message,
+					type: 'warning',
+				})
+			})
+		},
 		onPullDownRefresh() {
 			this.initialize()
 			setTimeout(() => {
@@ -96,15 +152,51 @@
 					this.classInfo = res.data
 				}).catch(error => {
 					this.$refs.uTips.show({
-						title: '获取班级详情失败',
+						title: error.message,
 						type: 'warning',
 					})
 				})
 			},
-			//  跳转预定表单
+			//  学员报名
+			enlistStudent(item) {
+				NET.request(API.enlistStudent, {
+					classId: this.classId,
+					studentId: item.studentId,
+				}, 'POST').then(res => {
+					this.enlistShow = false
+					this.$refs.uTips.show({
+						title: res.message,
+						type: 'success',
+					})
+				}).catch(error => {
+					this.$refs.uTips.show({
+						title: error.message,
+						type: 'warning',
+					})
+				})
+			},
+			//  学员预约
+			subscribeStudent(item) {
+				NET.request(API.subscribeStudent, {
+					classId: this.classId,
+					studentId: item.studentId,
+				}, 'POST').then(res => {
+					this.subscribeShow = false
+					this.$refs.uTips.show({
+						title: res.message,
+						type: 'success',
+					})
+				}).catch(error => {
+					this.$refs.uTips.show({
+						title: error.message,
+						type: 'warning',
+					})
+				})
+			},
+			//  跳转新增学员表单
 			goToSubscribelForm() {
 				uni.navigateTo({
-					url: '/pagesMember/subscribelForm?id=' + this.classId
+					url: '/pagesMember/subscribelForm'
 				});
 			},
 		},
@@ -121,6 +213,7 @@
 </style>
 <style lang="scss" scoped>
 	@import "@/static/css/themes.scss";
+
 	.content {
 		width: 100%;
 		float: left;
@@ -129,6 +222,22 @@
 		.class-info-text {
 			color: #999999;
 			line-height: 18px;
+
+			u-icon {
+				margin-right: 2px;
+			}
+		}
+
+		.student-box {
+			max-height: 200px;
+			padding: 0 15px;
+			margin: 25px 0 0 0;
+			box-sizing: border-box;
+			overflow: auto;
+
+			/deep/.u-card__head {
+				padding-bottom: 0px !important;
+			}
 		}
 
 		.techaer-info-box {
@@ -165,5 +274,12 @@
 				}
 			}
 		}
+
+		.handle-fix-box {
+			u-button {
+				width: 50%;
+				display: inline-block;
+			}
+		}
 	}
 </style>

+ 37 - 19
pagesMember/courseForm.vue

@@ -1,11 +1,12 @@
 <template>
 	<view class="content">
 		<u-form :model="form" ref="form" label-width="140">
-			<u-form-item label="评价内容" prop="estimateContent" required>
-				<u-input v-model="form.estimateContent" placeholder="请输入评价内容" type="textarea" auto-height :height="100" />
+			<u-form-item label="评价内容" prop="content" required>
+				<u-input v-model="form.content" placeholder="请输入评价内容" type="textarea" auto-height :height="100" />
 			</u-form-item>
-			<u-form-item label="上传附件" prop="estimateContent" required>
-				<u-upload :action="uploadAaction" :head="uploadHeader" max-count="5" :multiple="false" :file-list="fileList"></u-upload>
+			<u-form-item label="上传附件" label-position="top">
+				<u-upload max-count="5" :multiple="false" :action="uploadUrl" :header="uploadHeader" @on-success="uploadSuccess"
+				 @on-error="uploadError" @on-remove="uploadRemove"></u-upload>
 			</u-form-item>
 		</u-form>
 		<view class="handle-fix-box">
@@ -31,19 +32,15 @@
 			return {
 				classId: '',
 				form: {
-					level: 0,
-					estimateContent: '',
+					content: '',
+					fileId: [],
+				},
+				uploadUrl: API.uploadFile,
+				uploadHeader: {
+					Authorization: uni.getStorageSync('token')
 				},
-				uploadAaction: '',
-				uploadHeader: {},
-				fileList: [],
 				rules: {
-					level: [{
-						required: true,
-						message: '请选择评价星级',
-						trigger: 'change'
-					}],
-					estimateContent: [{
+					content: [{
 						required: true,
 						message: '请输入评价内容',
 						trigger: 'change'
@@ -58,16 +55,36 @@
 			this.$refs.form.setRules(this.rules);
 		},
 		methods: {
+			//  文件上传成功回调
+			uploadSuccess(res, index, lists, name) {
+				this.form.fileId.push(res.data.id)
+				this.$refs.uTips.show({
+					title: '文件上传成功',
+					type: 'success',
+				})
+				return true
+			},
+			//  文件上传失败回调
+			uploadError(res, index, lists, name) {
+				this.$refs.uTips.show({
+					title: '文件上传失败',
+					type: 'warning',
+				})
+			},
+			//  移除文件回调
+			uploadRemove(index, lists, name) {
+				this.form.fileId.splice(index, 1)
+			},
 			//  提交表单
 			submitForm() {
 				this.$refs.form.validate(valid => {
 					if (valid) {
-						NET.request(API.submitLevelForm, {
-							classId: this.classId,
+						NET.request(API.submitGrowForm, {
+							id: this.classId,
 							...this.form
 						}, 'POST').then(res => {
 							this.$refs.uTips.show({
-								title: '评价成功',
+								title: '填写成功',
 								type: 'success',
 							})
 							setTimeout(() => {
@@ -75,7 +92,7 @@
 							}, 1000)
 						}).catch(error => {
 							this.$refs.uTips.show({
-								title: '评价失败',
+								title: error.message,
 								type: 'warning',
 							})
 						})
@@ -95,6 +112,7 @@
 </style>
 <style lang="scss" scoped>
 	@import "@/static/css/themes.scss";
+
 	.content {
 		width: 100%;
 		float: left;

+ 3 - 1
pagesMember/evaluateForm.vue

@@ -38,6 +38,7 @@
 				rules: {
 					level: [{
 						required: true,
+						type: 'number',
 						message: '请选择评价星级',
 						trigger: 'change'
 					}],
@@ -73,7 +74,7 @@
 							}, 1000)
 						}).catch(error => {
 							this.$refs.uTips.show({
-								title: '评价失败',
+								title: error.message,
 								type: 'warning',
 							})
 						})
@@ -93,6 +94,7 @@
 </style>
 <style lang="scss" scoped>
 	@import "@/static/css/themes.scss";
+
 	.content {
 		width: 100%;
 		float: left;

+ 23 - 3
pagesMember/leaveForm.vue

@@ -9,7 +9,7 @@
 			</u-form-item>
 		</u-form>
 		<u-calendar v-model="leaveTimeShow" mode="date" :active-bg-color="mainColor" btn-type="error" availableText="有课"
-		 :available="availableList" @change="setLeaveTime" max-date="2300-12-31"></u-calendar>
+		 :available="availableList" activeText="已请假" :activeList="activeList" @change="setLeaveTime" max-date="2300-12-31"></u-calendar>
 		<view class="handle-fix-box">
 			<u-button type="warning" shape="circle" :ripple="true" :custom-style="customStyle" @click="submitForm()">提交</u-button>
 		</view>
@@ -33,6 +33,7 @@
 		data() {
 			return {
 				classId: '',
+				studentId: '',
 				form: {
 					leaveTime: '',
 					leaveReason: '',
@@ -50,11 +51,28 @@
 					}],
 				},
 				leaveTimeShow: false,
-				availableList: []
+				availableList: [],
+				activeList: [],
 			}
 		},
 		onLoad(options) {
 			this.classId = options.id
+			this.studentId = options.studentId
+			NET.request(API.getLeaveList, {
+				id: this.classId
+			}, 'POST').then(res => {
+				this.availableList = res.data.filter(site => site.type == 0).map(site => {
+					return site.lastDate
+				})
+				this.activeList = res.data.filter(site => site.type == 1).map(site => {
+					return site.lastDate
+				})
+			}).catch(error => {
+				this.$refs.uTips.show({
+					title: error.message,
+					type: 'warning',
+				})
+			})
 		},
 		onReady() {
 			this.$refs.form.setRules(this.rules);
@@ -79,6 +97,7 @@
 					if (valid) {
 						NET.request(API.submitLevelForm, {
 							classId: this.classId,
+							studentId: this.studentId,
 							...this.form
 						}, 'POST').then(res => {
 							this.$refs.uTips.show({
@@ -90,7 +109,7 @@
 							}, 1000)
 						}).catch(error => {
 							this.$refs.uTips.show({
-								title: '请假失败',
+								title: error.message,
 								type: 'warning',
 							})
 						})
@@ -110,6 +129,7 @@
 </style>
 <style lang="scss" scoped>
 	@import "@/static/css/themes.scss";
+
 	.content {
 		width: 100%;
 		float: left;

+ 4 - 4
pagesMember/myClassDetail.vue

@@ -72,13 +72,13 @@
 		methods: {
 			//  获取初始化数据
 			initialize() {
-				NET.request(API.getClassDetail, {
+				NET.request(API.getMemberClassDetail, {
 					id: this.classId
 				}, 'POST').then(res => {
-					this.swiperList = res.data
+					this.classInfo = res.data
 				}).catch(error => {
 					this.$refs.uTips.show({
-						title: '获取班级详情失败',
+						title: error.message,
 						type: 'warning',
 					})
 				})
@@ -93,7 +93,7 @@
 					})
 				}).catch(error => {
 					this.$refs.uTips.show({
-						title: '获取班级详情失败',
+						title: error.message,
 						type: 'warning',
 					})
 				})

+ 6 - 11
pagesMember/subscribelForm.vue

@@ -17,7 +17,7 @@
 				<u-input v-model="subscribelForm.birthday" placeholder="请选择学生生日" :select-open="birthdayShow" type="select" @click="birthdayShow = true" />
 			</u-form-item>
 			<u-form-item label="手机号码" prop="phone" required>
-				<u-input v-model="subscribelForm.phone" placeholder="请输入手机号码" />
+				<u-input v-model="subscribelForm.phone" type="number" placeholder="请输入手机号码" />
 			</u-form-item>
 			<!-- <u-form-item label="体验日期" placeholder="请选择体验日期" prop="experience">
 				<u-input v-model="subscribelForm.experience" :select-open="experienceShow" type="select" @click="experienceShow = true" />
@@ -49,7 +49,6 @@
 		},
 		data() {
 			return {
-				classId: '',
 				subscribelForm: {
 					studentName: '',
 					fatherName: '',
@@ -121,9 +120,7 @@
 				availableList: []
 			}
 		},
-		onLoad(options) {
-			this.classId = options.id
-		},
+		onLoad(options) {},
 		onReady() {
 			this.$refs.subscribelForm.setRules(this.rules);
 		},
@@ -153,22 +150,19 @@
 			submitForm() {
 				this.$refs.subscribelForm.validate(valid => {
 					if (valid) {
-						NET.request(API.submitStudentForm, {
-							classId: this.classId,
-							...this.subscribelForm
-						}, 'POST').then(res => {
+						NET.request(API.submitStudentForm, this.subscribelForm, 'POST').then(res => {
 							this.$refs.uTips.show({
 								title: '新增成功',
 								type: 'success',
 							})
 							setTimeout(() => {
 								uni.redirectTo({
-									url: '/pagesMain/subscribelSuccess'
+									url: '/pagesMember/subscribelSuccess'
 								});
 							}, 1000)
 						}).catch(error => {
 							this.$refs.uTips.show({
-								title: '新增失败',
+								title: error.message,
 								type: 'warning',
 							})
 						})
@@ -188,6 +182,7 @@
 </style>
 <style lang="scss" scoped>
 	@import "@/static/css/themes.scss";
+
 	.content {
 		width: 100%;
 		float: left;

+ 2 - 2
pagesMember/subscribelSuccess.vue

@@ -1,10 +1,10 @@
 <template>
 	<view class="content">
-		<view class="success-title">预约成功</view>
+		<view class="success-title">新增成功</view>
 		<view class="success-icon">
 			<u-icon name="checkmark-circle-fill" color="#19be6b" size="156"></u-icon>
 		</view>
-		<view class="success-text">课程预约成功,稍后我们会联系您</view>
+		<view class="success-text">新增学员成功,稍后我们会联系您</view>
 		<view class="handle-fix-box">
 			<u-button type="warning" shape="circle" :ripple="true" :custom-style="customStyle" @click="goBack()">返回</u-button>
 		</view>

+ 124 - 27
pagesMember/venueDetail.vue

@@ -2,12 +2,15 @@
 	<view class="content">
 		<u-image :src="venueInfo.url" mode="aspectFill" height="45vw" border-radius="10px" width="calc(100vw - 30px)" style="margin: 10px 15px;float: left;"></u-image>
 		<u-section :title="venueInfo.name" :right="false" :show-line="false" font-size="32" class="title-box"></u-section>
-		<view class="venue-text">{{venueInfo.address}}</view>
+		<view class="venue-text">
+			<u-icon name="map" style="font-size: 14px;margin-right: 2px;"></u-icon>
+			{{venueInfo.address}}
+		</view>
 		<u-section title="场馆简介" :right="false" :show-line="false" font-size="32" class="title-box"></u-section>
 		<view class="venue-text">{{venueInfo.desc}}</view>
 		<u-section title="班级信息" :right="false" :show-line="false" font-size="32" class="title-box"></u-section>
 		<view class="class-box">
-			<u-card :head-border-bottom="false" :show-foot="false" padding="0" margin="10px" v-for="(item, index) in venueInfo.classListResList"
+			<u-card :head-border-bottom="false" :foot-border-top="false" padding="0" margin="10px" v-for="(item, index) in venueInfo.classListResList"
 			 :key="index" class="class-card" @click="goToClassDetail(item)">
 				<view class="class-content" slot="head" style="padding-top: 10px;">
 					<text class="class-name">{{item.name}}</text>
@@ -17,11 +20,37 @@
 						<view class="class-info-row">{{item.classStartDate}}&nbsp;&nbsp;{{item.classStartHours}}&nbsp;&nbsp;{{item.residue}}课时</view>
 						<view class="class-info-row">{{item.address}}</view>
 					</view>
-					<view class="class-handle" @click.stop="goToSubscribelForm(item)">预约</view>
+				</view>
+				<view class="class-content" slot="foot" style="padding-bottom: 10px;text-align: right;">
+					<u-button type="default" shape="circle" :ripple="true" :custom-style="handleDefaultCustomStyle" size="mini"
+					 :hair-line="false" plain @click.stop="cardHandle(item, 1)">体验</u-button>
+					<u-button type="warning" shape="circle" :ripple="true" :custom-style="handleCustomStyle" size="mini" @click.stop="cardHandle(item, 2)">报名</u-button>
 				</view>
 			</u-card>
 		</view>
-		<u-top-tips ref="uTips"></u-top-tips>
+		<u-popup v-model="enlistShow" mode="bottom" border-radius="30" :closeable="true">
+			<scroll-view scroll-y class="student-box">
+				<u-card :title="item.studentName" title-size="32" :head-style="cardStyle" :head-border-bottom="false" :show-foot="false"
+				 margin="10px" borderRadius="20" v-for="(item, index) in studentList1" :key="index" @click="enlistStudent(item)">
+					<view class="student-card" slot="body">
+						<view class="class-info-text">性别:{{item.sex}}&nbsp;&nbsp;年龄:{{item.age}}</view>
+					</view>
+				</u-card>
+			</scroll-view>
+			<u-button type="warning" shape="circle" :ripple="true" :custom-style="{...customStyle,margin:'15px'}" @click="goToSubscribelForm()">新增学员</u-button>
+		</u-popup>
+		<u-popup v-model="subscribeShow" mode="bottom" border-radius="30">
+			<scroll-view scroll-y class="student-box">
+				<u-card :title="item.studentName" title-size="32" :head-style="cardStyle" :head-border-bottom="false" :show-foot="false"
+				 margin="10px" borderRadius="20" v-for="(item, index) in studentList2" :key="index" @click="subscribeStudent(item)">
+					<view class="student-card" slot="body">
+						<view class="class-info-text">性别:{{item.sex}}&nbsp;&nbsp;年龄:{{item.age}}</view>
+					</view>
+				</u-card>
+			</scroll-view>
+			<u-button type="warning" shape="circle" :ripple="true" :custom-style="{...customStyle,margin:'15px'}" @click="goToSubscribelForm()">新增学员</u-button>
+		</u-popup>
+		<u-top-tips ref="uTips" zIndex="100000"></u-top-tips>
 	</view>
 </template>
 
@@ -35,6 +64,9 @@
 		computed: {
 			...mapGetters([
 				'mainColor',
+				'customStyle',
+				'handleCustomStyle',
+				'handleDefaultCustomStyle',
 			])
 		},
 		data() {
@@ -47,13 +79,38 @@
 					desc: '',
 					classListResList: [],
 				},
+				classId: '',
+				cardStyle: {
+					fontWeight: 'bold'
+				},
+				enlistShow: false,
+				studentList1: [],
+				subscribeShow: false,
+				studentList2: [],
 			}
 		},
 		onLoad(options) {
 			this.venueId = options.id
 			this.initialize()
 		},
-		onReady() {},
+		onShow() {
+			NET.request(API.getEnlistAbleStudent, {}, 'POST').then(res => {
+				this.studentList1 = res.data.row
+			}).catch(error => {
+				this.$refs.uTips.show({
+					title: error.message,
+					type: 'warning',
+				})
+			})
+			NET.request(API.getSubscribeAbleList, {}, 'POST').then(res => {
+				this.studentList2 = res.data.row
+			}).catch(error => {
+				this.$refs.uTips.show({
+					title: error.message,
+					type: 'warning',
+				})
+			})
+		},
 		onPullDownRefresh() {
 			this.initialize()
 			setTimeout(() => {
@@ -63,13 +120,13 @@
 		methods: {
 			//  获取初始化数据
 			initialize() {
-				NET.request(API.getVenueList, {
+				NET.request(API.getVenueDetail, {
 					id: this.venueId
 				}, 'POST').then(res => {
-					this.swiperList = res.data
+					this.venueInfo = res.data
 				}).catch(error => {
 					this.$refs.uTips.show({
-						title: '获取场馆详情失败',
+						title: error.message,
 						type: 'warning',
 					})
 				})
@@ -80,10 +137,55 @@
 					url: '/pagesMember/classDetail?id=' + item.id
 				});
 			},
-			//  跳转预定表单
-			goToSubscribelForm(item) {
+			//  弹出
+			cardHandle(item, type) {
+				this.classId = item.id
+				if (type == 1) {
+					this.subscribeShow = true
+				} else {
+					this.enlistShow = true
+				}
+			},
+			//  学员报名
+			enlistStudent(item) {
+				NET.request(API.enlistStudent, {
+					classId: this.classId,
+					studentId: item.studentId,
+				}, 'POST').then(res => {
+					this.enlistShow = false
+					this.$refs.uTips.show({
+						title: res.message,
+						type: 'success',
+					})
+				}).catch(error => {
+					this.$refs.uTips.show({
+						title: error.message,
+						type: 'warning',
+					})
+				})
+			},
+			//  学员预约
+			subscribeStudent(item) {
+				NET.request(API.subscribeStudent, {
+					classId: this.classId,
+					studentId: item.studentId,
+				}, 'POST').then(res => {
+					this.subscribeShow = false
+					this.$refs.uTips.show({
+						title: res.message,
+						type: 'success',
+					})
+				}).catch(error => {
+					this.$refs.uTips.show({
+						title: error.message,
+						type: 'warning',
+					})
+				})
+			},
+			//  跳转新增学员表单
+			goToSubscribelForm() {
 				uni.navigateTo({
-					url: '/pagesMember/subscribelForm?id=' + item.id
+					url: '/pagesMember/subscribelForm'
 				});
 			},
 		},
@@ -141,28 +243,23 @@
 				}
 
 				.class-info {
-					width: calc(100% - 56px);
-					float: left;
-
 					.class-info-row {
 						color: #999999;
 						line-height: 18px;
 					}
 				}
+			}
+		}
 
-				.class-handle {
-					width: 52px;
-					height: 22px;
-					border-radius: 10px;
-					background-color: $mainColor;
-					line-height: 22px;
-					color: #FFFFFF;
-					text-align: center;
-					right: 15px;
-					top: 50%;
-					position: absolute;
-					transform: translateY(-55%);
-				}
+		.student-box {
+			max-height: 200px;
+			padding: 0 15px;
+			margin: 25px 0 0 0;
+			box-sizing: border-box;
+			overflow: auto;
+
+			/deep/.u-card__head {
+				padding-bottom: 0px !important;
 			}
 		}
 	}

+ 8 - 20
store/index.js

@@ -1,4 +1,3 @@
-//引入vue和vuex
 import Vue from 'vue'
 import Vuex from 'vuex'
 Vue.use(Vuex)
@@ -8,39 +7,28 @@ const store = new Vuex.Store({ //  全局变量定义
 		mainColor: '#ff6e3e', //  主色
 		customStyle: { //  底部悬浮按钮样式
 			height: '40px',
+			fontSize: '14px',
 			backgroundColor: '#ff6e3e'
 		},
 		handleCustomStyle: { //  卡片主要操作按钮样式
 			backgroundColor: '#ff6e3e',
 			fontSize: '11px',
-			padding: '0 15px'
+			padding: '0 15px',
+			marginLeft: '10px'
 		},
 		handleDefaultCustomStyle: { //  卡片普通操作按钮样式
 			color: '#ff6e3e',
 			fontSize: '11px',
 			padding: '0 15px',
 			borderColor: '#ff6e3e',
+			marginLeft: '10px'
 		},
 	},
 	mutations: {
-		// 登录
-		login(state, provider) {
-			state.userLoginFlag = true;
-			state.userInfo = provider
-			uni.setStorage({ // 异步缓存用户信息
-				key: "userinfo",
-				data: provider
-			})
-			console.log(state.userInfo)
-		},
-		// 退出
-		logout(state) {
-			state.userLoginFlag = false;
-			state.userInfo = {};
-			uni.removeStorage({ // 清除用户信息
-				key: "userinfo"
-			})
-		}
+		//  例子
+		test(state, provider) {
+			//  state.mainColor = '';
+		},
 	},
 	getters: {
 		mainColor: state => {

+ 21 - 8
utils/request.js

@@ -1,3 +1,4 @@
+let requestTimes = 0;
 const request = (url, data, method = 'GET') => {
 	return new Promise((resolve, reject) => {
 		let header = {
@@ -6,6 +7,13 @@ const request = (url, data, method = 'GET') => {
 		if (uni.getStorageSync('token')) {
 			header.Authorization = uni.getStorageSync('token')
 		}
+		if (requestTimes === 0) {
+			uni.showLoading({
+				title: '加载中',
+				mask: true,
+			});
+		}
+		requestTimes++;
 		uni.request({
 			url: url,
 			data: data,
@@ -14,29 +22,34 @@ const request = (url, data, method = 'GET') => {
 			success: res => {
 				if (res.statusCode == 200) {
 					let data = res.data
-					if (data.code == 40001) {
+					if (data.status == 30001) {
+						uni.removeStorageSync('token')
 						uni.navigateTo({
-							url: '/pages/index/login'
+							url: '/pages/login/index'
 						});
 						return false
 					}
-					if (data.code == 0 || data.code == 200) {
+					if (data.status == 10000) {
 						resolve(res.data)
 					} else {
-						reject(res)
+						reject(res.data)
 					}
 				} else {
-					reject(res)
+					reject(res.data)
 				}
 			},
 			fail: res => {
-				reject(res)
+				reject(res.data)
+			},
+			complete: () => {
+				requestTimes--;
+				if (requestTimes === 0) {
+					uni.hideLoading();
+				}
 			}
 		})
 	});
 }
-
-
 module.exports = {
 	request: request
 }

+ 3 - 1
uview-ui/components/u-calendar/u-calendar.vue

@@ -612,10 +612,12 @@
 				@include vue-flex;
 				align-items: center;
 				justify-content: center;
-				padding: 6px 0;
+				padding: 5px 0;
 				overflow: hidden;
 				position: relative;
 				z-index: 2;
+				border: 1px solid #ffffff;
+				box-sizing: border-box;
 
 				&__inner {
 					height: 84rpx;