39f68355 by lttnew

道馆页面更改

1 parent a4aa5d24
...@@ -5,7 +5,9 @@ ...@@ -5,7 +5,9 @@
5 "WebFetch(domain:minimax-algeng-chat-tts.oss-cn-wulanchabu.aliyuncs.com)", 5 "WebFetch(domain:minimax-algeng-chat-tts.oss-cn-wulanchabu.aliyuncs.com)",
6 "Bash(node -c pages/index/perfect.vue)", 6 "Bash(node -c pages/index/perfect.vue)",
7 "Bash(git checkout:*)", 7 "Bash(git checkout:*)",
8 "Bash(git restore:*)" 8 "Bash(git restore:*)",
9 "Bash(git:*)",
10 "Bash(python3 -c \"import json,sys; d=json.load\\(sys.stdin\\); print\\('tabBar list:', [l['pagePath'] for l in d.get\\('tabBar',{}\\).get\\('list',[]\\)]\\)\")"
9 ] 11 ]
10 } 12 }
11 } 13 }
......
...@@ -11,22 +11,28 @@ ...@@ -11,22 +11,28 @@
11 baseUrl_api: '', 11 baseUrl_api: '',
12 user: null 12 user: null
13 }, 13 },
14 onLaunch: function(options) { 14 onLaunch: async function(options) {
15 console.log('App Launch', options); 15 console.log('App Launch', options);
16 this.globalData.baseUrl_api = config.baseUrl_api; 16 this.globalData.baseUrl_api = config.baseUrl_api;
17 17
18 let userName = uni.getStorageSync('userName') 18 let userName = uni.getStorageSync('userName')
19 if (userName) { 19 if (userName) {
20 getInfo().then(() => { 20 await getInfo(this)
21 this.globalData.isLogin = true 21 this.globalData.isLogin = true
22 // 道馆用户跳转到道馆首页
23 const deptType = this.globalData.deptType
24 const userType = this.globalData.userType
25
26 // 道馆判断:deptType=6 或者 userType='4'
27 if (deptType == 6 || deptType == '6' || userType == '4') {
22 uni.reLaunch({ 28 uni.reLaunch({
23 url: '/pages/index/home' 29 url: '/pages/index/daoGuanPerson'
24 }) 30 })
25 }).catch(() => { 31 } else {
26 uni.reLaunch({ 32 uni.reLaunch({
27 url: '/login/login' 33 url: '/pages/index/home'
28 }) 34 })
29 }) 35 }
30 return 36 return
31 } 37 }
32 38
...@@ -62,4 +68,4 @@ ...@@ -62,4 +68,4 @@
62 /*每个页面公共css */ 68 /*每个页面公共css */
63 @import '/common/uni.css'; 69 @import '/common/uni.css';
64 @import '/common/mystyle.scss'; 70 @import '/common/mystyle.scss';
65 </style>
...\ No newline at end of file ...\ No newline at end of file
71 </style>
......
...@@ -10,7 +10,13 @@ function pcLogin(data) { ...@@ -10,7 +10,13 @@ function pcLogin(data) {
10 params: data 10 params: data
11 }).then((res) => { 11 }).then((res) => {
12 uni.setStorageSync('token', 'Bearer ' + res.data.token) 12 uni.setStorageSync('token', 'Bearer ' + res.data.token)
13 pcLoginOpenId() 13 return new Promise((resolve) => {
14 pcLoginOpenId()
15 // 延迟一下确保 token 设置完成
16 setTimeout(() => {
17 resolve()
18 }, 100)
19 })
14 }).then(getInfo) 20 }).then(getInfo)
15 } 21 }
16 22
...@@ -98,14 +104,16 @@ function loginByPhone(phonenumber, code) { ...@@ -98,14 +104,16 @@ function loginByPhone(phonenumber, code) {
98 } 104 }
99 105
100 // 获取用户详细信息 106 // 获取用户详细信息
101 function getInfo() { 107 function getInfo(appInstance) {
102 return request({ 108 console.log('getInfo 开始调用')
103 url: '/getInfo', 109 return request({
104 method: 'get' 110 url: '/getInfo',
105 }).then(res => { 111 method: 'get'
106 const userStore = useUserStore() 112 }).then(res => {
107 const app = getApp() 113 console.log('getInfo 成功', res.data)
108 const user = res.data.user 114 const userStore = useUserStore()
115 const app = appInstance || getApp()
116 const user = res.data.user
109 117
110 uni.setStorageSync('userName', user.userName) 118 uni.setStorageSync('userName', user.userName)
111 uni.removeStorageSync('webUserName') 119 uni.removeStorageSync('webUserName')
...@@ -126,6 +134,12 @@ function getInfo() { ...@@ -126,6 +134,12 @@ function getInfo() {
126 } else { 134 } else {
127 app.globalData.userType = '3' 135 app.globalData.userType = '3'
128 } 136 }
137
138 console.log('getInfo跳转判断 - deptType:', deptType, 'userType:', app.globalData.userType)
139 // 道馆用户跳转道馆首页
140 return res
141 }).catch(err => {
142 console.error('getInfo 失败:', err)
129 }) 143 })
130 } 144 }
131 145
......
1 <template>
2 <view class="dao-guan-tab-bar">
3 <image
4 v-if="currentIndex >= 0"
5 :src="config.baseUrl_api + '/fs/static/img/toolbar.png'"
6 class="dg-tab-bar-bg"
7 mode="scaleToFill"
8 :style="{ left: tabBgLeft }"
9 ></image>
10 <view
11 v-for="(item, index) in tabs"
12 :key="index"
13 class="dg-tab-item"
14 :class="{ active: currentIndex === index }"
15 @click="handleClick(index, item.url)"
16 >
17 <image :src="currentIndex === index ? item.activeIcon : item.icon" class="dg-tab-icon"></image>
18 <text class="dg-tab-text">{{ item.text }}</text>
19 </view>
20 </view>
21 </template>
22
23 <script setup>
24 import config from '@/config.js'
25 import { computed, ref } from 'vue'
26
27 const props = defineProps({
28 currentIndex: {
29 type: Number,
30 default: 0
31 }
32 })
33
34 const emit = defineEmits(['switch'])
35 const switching = ref(false)
36
37 const tabs = [
38 { text: '人员', url: '/pages/index/daoGuanPerson', icon: '/static/img/tool01.png', activeIcon: '/static/img/tool01_dwn.png' },
39 { text: '订单', url: '/pages/index/daoGuanOrder', icon: '/static/img/tool02.png', activeIcon: '/static/img/tool02_dwn.png' },
40 { text: '通知', url: '/pages/index/daoGuanNotice', icon: '/static/img/tool03.png', activeIcon: '/static/img/tool03_dwn.png' },
41 { text: '级位', url: '/pages/index/daoGuanLevel', icon: '/static/img/tool04.png', activeIcon: '/static/img/tool04_dwn.png' },
42 { text: '我的', url: '/pages/index/daoGuanMy', icon: '/static/img/tool05.png', activeIcon: '/static/img/tool05_dwn.png' },
43 ]
44
45 const tabBgLeft = computed(() => {
46 if (props.currentIndex < 0) return '0'
47 return `${props.currentIndex * 20}%`
48 })
49
50 const handleClick = (index, url) => {
51 if (switching.value || index === props.currentIndex) return
52
53 switching.value = true
54 emit('switch', index, url)
55
56 uni.redirectTo({
57 url,
58 fail: () => {
59 switching.value = false
60 }
61 })
62 }
63 </script>
64
65 <style lang="scss" scoped>
66 .dao-guan-tab-bar {
67 position: fixed;
68 bottom: 0;
69 left: 0;
70 right: 0;
71 height: 120rpx;
72 display: flex;
73 justify-content: flex-start;
74 align-items: stretch;
75 padding-bottom: env(safe-area-inset-bottom);
76 z-index: 9999;
77 background-color: #d9d9d9;
78 overflow: hidden;
79 }
80
81 .dg-tab-bar-bg {
82 position: absolute;
83 top: 0rpx;
84 width: 20%;
85 height: calc(100% - 35rpx);
86 z-index: 0;
87 transition: left 0.3s ease;
88 pointer-events: none;
89 }
90
91 .dg-tab-item {
92 display: flex;
93 flex-direction: column;
94 align-items: center;
95 justify-content: center;
96 width: 20%;
97 height: 100%;
98 position: relative;
99 z-index: 1;
100 }
101
102 .dg-tab-icon {
103 width: 50rpx;
104 height: 50rpx;
105 margin-bottom: 4rpx;
106 }
107
108 .dg-tab-text {
109 font-size: 20rpx;
110 color: #666;
111 }
112
113 .dg-tab-item.active .dg-tab-text {
114 color: #C30D23;
115 font-weight: bold;
116 }
117 </style>
1 <template> 1 <template>
2 <view class="role-entry-page"> 2 <view class="role-entry-page">
3 <!-- 全屏背景图 --> 3 <!-- 全屏背景图 -->
4 <image :src="config.loginImage_api + '/fs/static/dg/bg@3x.png'" class="page-bg" mode="aspectFill"></image> 4 <image :src="config.baseUrl_api + '/fs/static/img/home_bg.png'" class="page-bg" mode="aspectFill"></image>
5 5
6 <!-- 顶部 Logo 区域 --> 6 <!-- 顶部 Logo 区域 -->
7 <view class="header-wrapper"> 7 <!-- <view class="header-wrapper">
8 <view class="logo-box"> 8 <view class="logo-box">
9 <image :src="config.loginImage_api + '/fs/static/dg/ztx_b.svg'" class="logo" mode="aspectFit"></image> 9 <image :src="config.loginImage_api + '/fs/static/dg/ztx_b.svg'" class="logo" mode="aspectFit"></image>
10 </view> 10 </view>
11 </view> 11 </view> -->
12 12
13 <!-- 功能按钮区域 --> 13 <!-- 功能按钮区域 -->
14 <view class="btn-container"> 14 <view class="btn-container">
15 <view @click="goToPage('/personal/addVip_per')"> 15 <view
16 <image :src="config.loginImage_api + '/fs/static/dg/btn01@3x.png'" class="btn-item"></image> 16 class="entry-btn"
17 </view> 17 :class="{ active: activeEntry === 'unit' }"
18 <view @click="goToPage('/personal/home')"> 18 @click="goUnitLogin"
19 <image :src="config.loginImage_api + '/fs/static/dg/btn02@3x.png'" class="btn-item"></image> 19 >
20 </view> 20 <image :src="activeEntry === 'unit' ? '/static/img/home_btn2.png' : '/static/img/home_btn.png'" class="btn-bg" mode="scaleToFill"></image>
21 <view @click="goToPage('/login/loginC')"> 21 <text>单位会员入口</text>
22 <image :src="config.loginImage_api + '/fs/static/dg/btn03@3x.png'" class="btn-item"></image> 22 </view>
23 </view> 23
24 </view> 24 <view
25 25 class="entry-btn"
26 26 :class="{ active: activeEntry === 'personal' }"
27 </view> 27 @click="showLoginPopup"
28 </template> 28 >
29 <script setup> 29 <image :src="activeEntry === 'personal' ? '/static/img/home_btn2.png' : '/static/img/home_btn.png'" class="btn-bg" mode="scaleToFill"></image>
30 import {ref} from 'vue' 30 <text>个人会员入口</text>
31 import {onShow} from '@dcloudio/uni-app' 31 </view>
32 import config from '@/config.js' 32 </view>
33 33
34 onShow(() => { 34 <!-- 个人会员登录注册弹框 -->
35 uni.hideLoading(); 35 <uni-popup ref="loginPopup" :mask-click="true" type="center" @change="handlePopupChange">
36 }) 36 <view class="login-popup-content">
37 37 <!-- <view class="popup-title">请选择办理方式</view> -->
38 const goToPage = (url) => { 38 <view class="popup-btn active-btn" @click="goToPage('/personal/addVip_per')">
39 uni.navigateTo({ 39 个人会员注册
40 url, 40 </view>
41 }) 41 <view class="popup-btn plain-btn" @click="goToPage('/personal/home')">
42 } 42 个人会员登录
43 </script> 43 </view>
44 <style lang="scss" scoped> 44 </view>
45 .role-entry-page { 45 </uni-popup>
46 width: 100%; 46
47 min-height: 100vh; 47 </view>
48 position: relative; 48 </template>
49 padding: 20rpx; 49 <script setup>
50 box-sizing: border-box; 50 import {ref} from 'vue'
51 } 51 import {onShow} from '@dcloudio/uni-app'
52 52 import config from '@/config.js'
53 .page-bg { 53
54 position: absolute; 54 const loginPopup = ref(null)
55 top: 0; 55 const activeEntry = ref('')
56 left: 0; 56
57 width: 100%; 57 onShow(() => {
58 height: 100%; 58 uni.hideLoading();
59 z-index: -1; 59 })
60 } 60
61 61 const showLoginPopup = () => {
62 .header-wrapper { 62 activeEntry.value = 'personal'
63 text-align: center; 63 loginPopup.value.open()
64 // padding: 40rpx 0; 64 }
65 border-radius: 16rpx; 65
66 margin-top: 100rpx; 66 const goUnitLogin = () => {
67 } 67 activeEntry.value = 'unit'
68 68 uni.navigateTo({
69 .btn-container { 69 url: '/login/loginC',
70 display: flex; 70 })
71 flex-direction: column; 71 }
72 align-items: center; 72
73 margin: 0 auto; 73 const goToPage = (url) => {
74 74 loginPopup.value?.close()
75 img, image { 75 uni.navigateTo({
76 width: 509rpx; 76 url,
77 height: 117rpx; 77 })
78 margin: 40rpx 0; 78 }
79 79
80 } 80 const handlePopupChange = (e) => {
81 } 81 if (!e.show && activeEntry.value === 'personal') {
82 82 activeEntry.value = ''
83 .loading-overlay { 83 }
84 position: fixed; 84 }
85 top: 0; 85 </script>
86 left: 0; 86 <style lang="scss" scoped>
87 right: 0; 87 .role-entry-page {
88 bottom: 0; 88 width: 100%;
89 background-color: rgba(0, 0, 0, 0.5); 89 min-height: 100vh;
90 display: flex; 90 position: relative;
91 justify-content: center; 91 padding: 20rpx 0;
92 align-items: center; 92 box-sizing: border-box;
93 z-index: 999; 93 overflow: hidden;
94 } 94 }
95 95
96 .loading-content { 96 .page-bg {
97 color: white; 97 position: absolute;
98 font-size: 28rpx; 98 top: 0;
99 } 99 left: 0;
100 </style> 100 width: 100%;
101 height: 100%;
102 z-index: -1;
103 }
104
105 .header-wrapper {
106 text-align: center;
107 // padding: 40rpx 0;
108 border-radius: 16rpx;
109 margin-top: 100rpx;
110 }
111
112 .btn-container {
113 display: flex;
114 flex-direction: column;
115 align-items: center;
116 margin: 0 auto;
117 padding-top: 1040rpx;
118 gap: 52rpx;
119 }
120
121 .entry-btn {
122 position: relative;
123 width: 424rpx;
124 height: 86rpx;
125 display: flex;
126 align-items: center;
127 justify-content: center;
128 color: #2f2f2f;
129 font-size: 34rpx;
130 font-weight: 700;
131 letter-spacing: 2rpx;
132 }
133
134 .entry-btn.active {
135 color: #fff;
136 }
137
138 .btn-bg {
139 position: absolute;
140 inset: 0;
141 width: 100%;
142 height: 100%;
143 }
144
145 .entry-btn text {
146 position: relative;
147 z-index: 1;
148 }
149
150 .loading-overlay {
151 position: fixed;
152 top: 0;
153 left: 0;
154 right: 0;
155 bottom: 0;
156 background-color: rgba(0, 0, 0, 0.5);
157 display: flex;
158 justify-content: center;
159 align-items: center;
160 z-index: 999;
161 }
162
163 .loading-content {
164 color: white;
165 font-size: 28rpx;
166 }
167
168 .login-popup-content {
169 width: 560rpx;
170 background: #fff;
171 border-radius: 28rpx;
172 padding: 42rpx 42rpx 50rpx;
173 display: flex;
174 flex-direction: column;
175 align-items: center;
176 box-shadow: 0 20rpx 60rpx rgba(50, 0, 0, 0.25);
177 }
178
179 .popup-title {
180 margin-bottom: 22rpx;
181 color: #222;
182 font-size: 34rpx;
183 font-weight: 700;
184 }
185
186 .popup-btn {
187 position: relative;
188 width: 424rpx;
189 height: 86rpx;
190 line-height: 86rpx;
191 text-align: center;
192 border-radius: 16rpx;
193 font-size: 34rpx;
194 font-weight: 700;
195 margin: 18rpx 0;
196 box-sizing: border-box;
197 }
198
199 .active-btn {
200 background: linear-gradient(90deg, #ff9a00 0%, #e50012 100%);
201 color: #fff;
202 }
203
204 .plain-btn {
205 background: #fff;
206 color: #2f2f2f;
207 border: 4rpx solid #0b94d2;
208 box-shadow: inset 4rpx 0 0 #f7a100;
209 }
210 </style>
......
...@@ -118,25 +118,29 @@ ...@@ -118,25 +118,29 @@
118 <view class="popup-title">系统提示</view> 118 <view class="popup-title">系统提示</view>
119 <view class="popup-content"> 119 <view class="popup-content">
120 <view class="popup-text">尊敬的用户,您好!</view> 120 <view class="popup-text">尊敬的用户,您好!</view>
121 <view class="popup-text">在开始注册团体会员前,请您提前准备好以下材料,以便顺利完成申请</view> 121 <view class="popup-text">开始注册单位会员前,请提前准备以下材料(建议拍照或扫描,确保文字清晰、无遮挡)</view>
122 <view class="popup-item"> 122 <view class="popup-item">
123 <text class="popup-num ml10">1.</text> 123 <text class="popup-num ml10">1.</text>
124 单位营业执照 124 单位营业执照
125 </view> 125 </view>
126 <view class="popup-desc">请提供清晰的营业执照原件照片或扫描件(加盖公章更佳)</view> 126 <view class="popup-desc">原件照片或扫描件(加盖公章更佳)</view>
127 <view class="popup-item"> 127 <view class="popup-item">
128 <text class="popup-tip">!</text> 128 <text class="popup-tip">!</text>
129 <text class="popup-num"> 2.</text> 129 <text class="popup-num"> 2.</text>
130 法人身份证正反面照片 130 法人身份证
131 </view> 131 </view>
132 <view class="popup-desc">请分别上传身份证正面及反面清晰照片</view> 132 <view class="popup-desc">正、反面清晰照片(信息完整、无模糊)</view>
133 <view class="popup-desc">确保信息完整、无遮挡、无模糊</view> 133 <!-- <view class="popup-desc">确保信息完整、无遮挡、无模糊</view> -->
134 <view class="popup-item"> 134 <view class="popup-item">
135 <text class="popup-num ml10">3.</text> 135 <text class="popup-num ml10">3.</text>
136 机构照片 136 机构照片
137 </view> 137 </view>
138 <view class="popup-desc">请提供体现单位实际经营或办公环境的照片1-2张</view> 138 <view class="popup-desc">1–2张能体现单位真实经营或办公环境的照片,例如:门头、办公场所、活动场地等</view>
139 <view class="popup-desc">如门头、办公场所、活动场地等(能展示机构真实存在即可)</view> 139 <!-- <view class="popup-desc">如门头、办公场所、活动场地等(能展示机构真实存在即可)</view> -->
140 <view class="popup-text">
141 <!-- <text class="popup-num ml10">3.</text> -->
142 感谢您的配合,祝您注册顺利!
143 </view>
140 </view> 144 </view>
141 <view class="popup-btns"> 145 <view class="popup-btns">
142 <view class="popup-btn cancel" @click="closeRegisterPopup">取消</view> 146 <view class="popup-btn cancel" @click="closeRegisterPopup">取消</view>
...@@ -151,7 +155,7 @@ ...@@ -151,7 +155,7 @@
151 import {onLoad, onReady} from '@dcloudio/uni-app'; 155 import {onLoad, onReady} from '@dcloudio/uni-app';
152 import {ref, nextTick} from 'vue' 156 import {ref, nextTick} from 'vue'
153 import config from '@/config.js' 157 import config from '@/config.js'
154 import {getCodeImg, getSmsCodeImg, pcLogin, loginByPhone} from '@/common/login.js' 158 import {getCodeImg, getSmsCodeImg, pcLogin, loginByPhone, getInfo} from '@/common/login.js'
155 159
156 const isActive = ref(0) 160 const isActive = ref(0)
157 const agree = ref(false) 161 const agree = ref(false)
...@@ -182,6 +186,14 @@ const countDown = ref({ ...@@ -182,6 +186,14 @@ const countDown = ref({
182 186
183 const app = getApp() 187 const app = getApp()
184 188
189 function goHomeAfterLogin() {
190 const deptType = app.globalData.deptType
191 const userType = app.globalData.userType
192 uni.reLaunch({
193 url: (deptType == 6 || deptType == '6' || userType == '4') ? '/pages/index/daoGuanPerson' : '/pages/index/home'
194 })
195 }
196
185 onLoad(() => { 197 onLoad(() => {
186 getCode() 198 getCode()
187 if (uni.showShareMenu) { 199 if (uni.showShareMenu) {
...@@ -220,9 +232,12 @@ function login() { ...@@ -220,9 +232,12 @@ function login() {
220 } 232 }
221 if (loading.value) return; 233 if (loading.value) return;
222 loading.value = true 234 loading.value = true
223 pcLogin(form.value).then((res) => { 235 pcLogin(form.value).then(() => {
224 app.globalData.isLogin = true 236 app.globalData.isLogin = true
225 uni.redirectTo({url: '/pages/index/home'}) 237 goHomeAfterLogin()
238 }).catch((err) => {
239 console.error('登录失败:', err)
240 uni.showToast({title: '登录失败', icon: 'none'})
226 }).finally(() => { 241 }).finally(() => {
227 loading.value = false 242 loading.value = false
228 }) 243 })
...@@ -244,9 +259,8 @@ function login() { ...@@ -244,9 +259,8 @@ function login() {
244 loading.value = true 259 loading.value = true
245 loginByPhone(form2.value.telNo, form2.value.code) 260 loginByPhone(form2.value.telNo, form2.value.code)
246 .then(() => { 261 .then(() => {
247 loading.value = false
248 app.globalData.isLogin = true 262 app.globalData.isLogin = true
249 uni.redirectTo({url: '/pages/index/home'}) 263 goHomeAfterLogin()
250 }).finally(() => { 264 }).finally(() => {
251 loading.value = false 265 loading.value = false
252 }) 266 })
......
...@@ -22,7 +22,7 @@ ...@@ -22,7 +22,7 @@
22 <!-- 温馨提示 --> 22 <!-- 温馨提示 -->
23 <view v-if="form.selfSelect == '1'" class="tip-box"> 23 <view v-if="form.selfSelect == '1'" class="tip-box">
24 <text class="tip-text">温馨提示: 24 <text class="tip-text">温馨提示:
25 您可以自行录入考官信息,如果暂时没有合适的考官,也可以选择由省跆协指派(支持多选)进行考点申报,同时请尽快完成考点考官的认证。 25 您可以自行录入考官信息,如果暂时没有考官,可以选择由省跆协指派进行考点申报,请尽快完成考点考官的认证。
26 </text> 26 </text>
27 </view> 27 </view>
28 28
......
...@@ -48,8 +48,12 @@ ...@@ -48,8 +48,12 @@
48 48
49 <!-- 金额说明 --> 49 <!-- 金额说明 -->
50 <view class="card notice-card"> 50 <view class="card notice-card">
51 <view class="notice-line">1. 请通过网上银行(网银)或银行柜台或手机银行向以下账号划转款项。</view> 51 <view class="danger-title">
52 <view class="notice-line">2. 转账金额与订单金额必须保持一致,不得多转、少转。</view> 52 <text>请使用认证机构下的账号进行对公转账。</text>
53 </view>
54 <view class="notice-line">1. 本订单将为您保留7天,请您及时支付;逾期未支付,订单将自动取消。</view>
55 <view class="notice-line">2. 请通过网上银行(网银)或银行柜台或手机银行向以下账号划转款项。</view>
56 <view class="notice-line">3. 转账金额与订单金额必须保持一致,不得多转、少转。</view>
53 </view> 57 </view>
54 58
55 <!-- 温馨提示 --> 59 <!-- 温馨提示 -->
...@@ -293,6 +297,14 @@ function handelClose() { ...@@ -293,6 +297,14 @@ function handelClose() {
293 } 297 }
294 } 298 }
295 } 299 }
300 .danger-title{
301 display: flex;
302 align-items: center;
303 font-size: 28rpx;
304 color: #F56C6C;
305 font-weight: 600;
306 margin-bottom: 16rpx;
307 }
296 308
297 /* 温馨提示 */ 309 /* 温馨提示 */
298 .warning-card { 310 .warning-card {
......
...@@ -20,6 +20,56 @@ ...@@ -20,6 +20,56 @@
20 } 20 }
21 }, 21 },
22 { 22 {
23 "path": "pages/index/daoGuanPerson",
24 "style": {
25 "navigationBarTitleText": "人员",
26 "backgroundColor": "#ffffff",
27 "navigationStyle": "custom",
28 "navigationBarTextStyle": "black",
29 "navigationBarBackgroundColor": "#ffffff"
30 }
31 },
32 {
33 "path": "pages/index/daoGuanLevel",
34 "style": {
35 "navigationBarTitleText": "级位",
36 "backgroundColor": "#ffffff",
37 "navigationStyle": "custom",
38 "navigationBarTextStyle": "black",
39 "navigationBarBackgroundColor": "#ffffff"
40 }
41 },
42 {
43 "path": "pages/index/daoGuanOrder",
44 "style": {
45 "navigationBarTitleText": "订单",
46 "backgroundColor": "#ffffff",
47 "navigationStyle": "custom",
48 "navigationBarTextStyle": "black",
49 "navigationBarBackgroundColor": "#ffffff"
50 }
51 },
52 {
53 "path": "pages/index/daoGuanNotice",
54 "style": {
55 "navigationBarTitleText": "通知",
56 "backgroundColor": "#ffffff",
57 "navigationStyle": "custom",
58 "navigationBarTextStyle": "black",
59 "navigationBarBackgroundColor": "#ffffff"
60 }
61 },
62 {
63 "path": "pages/index/daoGuanMy",
64 "style": {
65 "navigationBarTitleText": "我的",
66 "backgroundColor": "#ffffff",
67 "navigationStyle": "custom",
68 "navigationBarTextStyle": "black",
69 "navigationBarBackgroundColor": "#ffffff"
70 }
71 },
72 {
23 "path": "pages/webview/webview", 73 "path": "pages/webview/webview",
24 "style": { 74 "style": {
25 "navigationBarTitleText": "中国跆拳道协会", 75 "navigationBarTitleText": "中国跆拳道协会",
...@@ -189,6 +239,7 @@ ...@@ -189,6 +239,7 @@
189 } 239 }
190 } 240 }
191 ], 241 ],
242
192 "globalStyle": { 243 "globalStyle": {
193 "navigationStyle": "default", 244 "navigationStyle": "default",
194 "navigationBarTextStyle": "black", 245 "navigationBarTextStyle": "black",
......
1 <template>
2 <view class="level-page">
3 <view class="hero">
4 <image class="hero-bg" :src="config.baseUrl_api + '/fs/static/img/top.png'" mode="aspectFill"></image>
5 <view class="hero-brand">
6 <view class="brand-cn">中国跆拳道协会</view>
7 <view class="brand-en">CHINESE TAEKWONDO ASSOCIATION</view>
8 </view>
9 </view>
10
11 <view class="content-panel">
12 <image class="panel-bg" :src="config.baseUrl_api + '/fs/static/img/red_bg2.png'" mode="scaleToFill"></image>
13 <view class="panel-content">
14 <view class="section-title">
15 <view class="title-cn">级位考试</view>
16 <view style="width:50rpx;height:8rpx;background:#C30D23;margin-top:20rpx;"></view>
17 <view class="title-en">LEVEL EXAM</view>
18 </view>
19
20 <view class="level-grid">
21 <image class="level-card" :src="config.baseUrl_api + '/fs/static/img/jw_btn01.png'" mode="aspectFit" @click="goPath('/level/addApply')"></image>
22 <image class="level-card" :src="config.baseUrl_api + '/fs/static/img/jw_btn02.png'" mode="aspectFit" @click="goPath('/personalVip/addChangeLevel')"></image>
23 <image class="level-card" :src="config.baseUrl_api + '/fs/static/img/jw_btn03.png'" mode="aspectFit" @click="goPath('/level/apply')"></image>
24 <image class="level-card" :src="config.baseUrl_api + '/fs/static/img/jw_btn04.png'" mode="aspectFit" @click="goPath('/personalVip/changeLevel')"></image>
25 </view>
26 </view>
27 </view>
28
29 <dao-guan-tab-bar :currentIndex="3" @switch="onTabSwitch" />
30 </view>
31 </template>
32
33 <script setup>
34 import config from '@/config.js'
35 import DaoGuanTabBar from '@/components/dao-guan-tab-bar.vue'
36
37 const onTabSwitch = () => {
38 // tab switch handled by component
39 }
40
41 const goPath = (url) => {
42 uni.navigateTo({ url })
43 }
44 </script>
45
46 <style lang="scss" scoped>
47 .level-page {
48 position: relative;
49 min-height: 100vh;
50 overflow-x: hidden;
51 background: #ededf0;
52 overflow-y: hidden;
53 // padding-bottom: calc(120rpx + env(safe-area-inset-bottom));
54 box-sizing: border-box;
55 }
56
57 .hero {
58 position: relative;
59 height: 1060rpx;
60 overflow: hidden;
61 z-index: 1;
62 }
63
64 .hero-bg {
65 position: absolute;
66 left: 0;
67 top: -116px;
68 width: 100%;
69 height: 100%;
70 }
71
72 .hero-brand {
73 position: relative;
74 z-index: 1;
75 padding: calc(env(safe-area-inset-top) + 170rpx) 44rpx 0;
76 color: #fff;
77 }
78
79 .brand-cn {
80 font-size: 38rpx;
81 letter-spacing: 2rpx;
82 }
83
84 .brand-en {
85 margin-top: 8rpx;
86 color: rgba(255, 255, 255, 0.62);
87 font-size: 16rpx;
88 }
89
90 .content-panel {
91 position: relative;
92 z-index: 3;
93 min-height: 760rpx;
94 margin-top: -300rpx;
95 overflow: visible;
96 }
97
98 .panel-bg {
99 position: absolute;
100 left: 0;
101 top: -674rpx;
102 z-index:10;
103 width: 100%;
104 height: 1700rpx;
105 }
106
107 .panel-content {
108 position: relative;
109 z-index: 12;
110 padding: 0rpx 46rpx 40rpx;
111 }
112
113 .section-title {
114 margin-bottom: 30rpx;
115 }
116
117 .title-cn {
118 color: #2a2a2a;
119 font-size: 58rpx;
120 line-height: 1;
121 }
122
123 .title-en {
124 margin-top: 12rpx;
125 color: #9a9a9a;
126 font-size: 24rpx;
127 font-weight: 700;
128 }
129
130 .level-grid {
131 display: grid;
132 grid-template-columns: repeat(2, 1fr);
133 gap: 14rpx 14rpx;
134 }
135
136 .level-card {
137 width: 100%;
138 height: 236rpx;
139 border-radius: 10rpx;
140 }
141 </style>
1 <template>
2 <view class="page dao-my-page">
3 <image class="page-red-bg" :src="config.baseUrl_api + '/fs/static/img/red_bg.png'" mode="scaleToFill"></image>
4 <view class="profile-hero">
5 <view class="hero-content">
6 <view class="profile-row">
7 <view class="avatar-wrap">
8 <image v-if="state.user.avatar" :src="state.user.avatar" mode="aspectFill"/>
9 <image v-else :src="config.baseUrl_api + '/fs/static/nodata.png'" mode="aspectFill"/>
10 </view>
11 <!-- <view class="profile-main">
12 <view class="name-row">
13 <view class="dept-name">{{ state.user?.dept?.deptName || deptInfo.deptName || memberInfo.name || '--' }}</view>
14 <view class="member-badge">
15 <text class="badge-star"></text>
16 <text>金牌会员</text>
17 </view>
18 </view>
19 <view class="id-row">
20 <text>ID:{{ memberInfo.menCode || memberInfo.memberCode || memberInfo.memberNo || state.user?.userName || '--' }}</text>
21 <text class="join-days">您已加入{{ joinDays }}</text>
22 </view>
23 </view> -->
24 </view>
25 <view class="motto">每一次的成功都不是偶然,是千锤百炼,永不放弃的结果。{{ state.user?.dept?.deptName || '龙威天成跆拳道馆' }},以专业铸就辉煌!</view>
26 <view class="edit-btn" @click="goPath('/myCenter/teamInfo')">修改资料</view>
27 </view>
28 </view>
29
30 <view class="menu-panel">
31 <image class="menu-bg" :src="config.baseUrl_api + '/fs/static/img/red_bg2.png'" mode="scaleToFill"></image>
32 <view class="menu-item" @click="goPath('/myCenter/teamInfo')">
33 <view class="menu-left">
34 <image class="menu-icon" :src="config.baseUrl_api + '/fs/static/img/user01.png'" mode="aspectFit"></image>
35 <text>单位信息</text>
36 </view>
37 <text class="arrow">></text>
38 </view>
39
40 <view class="menu-item" @click="goPath('/myCenter/auth')">
41 <view class="menu-left">
42 <image class="menu-icon" :src="config.baseUrl_api + '/fs/static/img/user02.png'" mode="aspectFit"></image>
43 <text>会员认证</text>
44 </view>
45 <text class="arrow">></text>
46 </view>
47
48 <view class="menu-item" @click="goPath('/myCenter/safe')">
49 <view class="menu-left">
50 <image class="menu-icon" :src="config.baseUrl_api + '/fs/static/img/user03.png'" mode="aspectFit"></image>
51 <text>账号安全</text>
52 </view>
53 <text class="arrow">></text>
54 </view>
55 </view>
56
57 <view class="logout-area">
58 <button class="logout-btn" @click="loginOut">退出登录</button>
59 </view>
60
61 <!-- 底部导航 -->
62 <dao-guan-tab-bar :currentIndex="4" @switch="onTabSwitch" />
63 </view>
64 </template>
65
66 <script setup>
67 import * as api from '@/common/api.js';
68 import * as loginServer from '@/common/login.js';
69 import config from '@/config.js'
70 import {
71 onLoad,
72 onShow,
73 onReady,
74 onPullDownRefresh
75 } from '@dcloudio/uni-app';
76 import {
77 ref, reactive, computed,
78 getCurrentInstance
79 } from 'vue';
80 import DaoGuanTabBar from '@/components/dao-guan-tab-bar.vue'
81
82
83 const {
84 proxy
85 } = getCurrentInstance()
86 const app = getApp();
87 const userType = ref('1')
88 const memberInfo = ref({})
89 const deptInfo = ref({})
90 let proId;
91 const svId = ref(null);
92 const numData = ref({});
93
94 const messageList = ref([])
95 const state = reactive({
96 user: {},
97 roleGroup: {},
98 postGroup: {}
99 })
100
101 const joinDays = computed(() => {
102 const value = memberInfo.value.createTime || memberInfo.value.joinTime || memberInfo.value.createDate
103 if (!value) return '--'
104 const start = new Date(String(value).replace(/-/g, '/')).getTime()
105 if (!start) return '--'
106 const days = Math.floor((Date.now() - start) / (24 * 60 * 60 * 1000)) + 1
107 return days > 0 ? days : 1
108 })
109 onShow(() => {
110 if (app.globalData.isLogin) {
111 init()
112 } else {
113 app.firstLoadCallback = () => {
114 init()
115 };
116 }
117 })
118 onLoad(option => {
119 if (option.scene) {
120 proId = decodeURIComponent(option.scene);
121 } else {
122 proId = option.proId;
123 }
124 if (uni.showShareMenu) {
125 uni.showShareMenu({
126 withShareTicket: true,
127 menus: ['shareAppMessage', 'shareTimeline']
128 });
129 }
130 });
131
132 function loginOut() {
133 uni.showModal({
134 content: `确认退出吗?`,
135 success: function (res) {
136 if (res.confirm) {
137 loginServer.logout().finally(() => {
138 let path = '/login/login';
139 uni.reLaunch({
140 url: path
141 });
142 })
143 }
144 }
145 })
146 }
147
148 function getUser() {
149 api.getUserProfile().then((response) => {
150 state.user = response.data.user
151 if (state.user.avatar && state.user.avatar.indexOf('http') == -1) {
152 state.user.avatar = config.baseUrl_api + state.user.avatar
153 }
154 state.roleGroup = response.data.roleGroup
155 state.postGroup = response.data.postGroup
156 uni.hideLoading();
157 })
158 }
159
160 function init() {
161 uni.showLoading({
162 title: '加载中'
163 });
164 getUser()
165 loginServer.getMyOwnMemberInfo().then(res => {
166 userType.value = app.globalData.userType
167 memberInfo.value = app.globalData.memberInfo
168 deptInfo.value = app.globalData.dept || {}
169 uni.hideLoading();
170 })
171 }
172
173 function goPath(url) {
174 uni.navigateTo({
175 url: url
176 })
177 }
178
179 function onTabSwitch(index, url) {
180 // tab switch handled by component
181 }
182
183 </script>
184 <style lang="scss" scoped>
185 .dao-my-page {
186 position: relative;
187 min-height: 100vh;
188 width: 100vw;
189 overflow-x: hidden;
190 box-sizing: border-box;
191 padding-bottom: calc(210rpx + env(safe-area-inset-bottom));
192 background: #ededf0;
193 }
194
195 .page-red-bg {
196 position: absolute;
197 left: 0;
198 top: 0;
199 z-index: 0;
200 width: 100%;
201 height: 720rpx;
202 }
203
204 .profile-hero {
205 position: relative;
206 z-index: 1;
207 min-height: 460rpx;
208 }
209
210 .hero-content {
211 position: relative;
212 z-index: 2;
213 padding: calc(env(safe-area-inset-top) + 126rpx) 48rpx 0;
214 color: #fff;
215 }
216
217 .profile-row {
218 display: flex;
219 align-items: center;
220 }
221
222 .avatar-wrap {
223 width: 132rpx;
224 height: 132rpx;
225 padding: 6rpx;
226 flex: 0 0 132rpx;
227 overflow: hidden;
228 border-radius: 50%;
229 background: #fff;
230 box-shadow: 0 8rpx 26rpx rgba(65, 0, 0, 0.28);
231
232 image {
233 width: 100%;
234 height: 100%;
235 border-radius: 50%;
236 }
237 }
238
239 .profile-main {
240 flex: 1;
241 min-width: 0;
242 margin-left: 26rpx;
243 }
244
245 .name-row,
246 .id-row {
247 display: flex;
248 align-items: center;
249 justify-content: space-between;
250 }
251
252 .dept-name {
253 max-width: 330rpx;
254 overflow: hidden;
255 white-space: nowrap;
256 text-overflow: ellipsis;
257 font-size: 34rpx;
258 font-weight: 700;
259 }
260
261 .member-badge {
262 display: flex;
263 align-items: center;
264 gap: 8rpx;
265 color: #dba12d;
266 font-size: 24rpx;
267 white-space: nowrap;
268 }
269
270 .badge-star {
271 color: #f7c342;
272 font-size: 24rpx;
273 }
274
275 .id-row {
276 margin-top: 12rpx;
277 color: rgba(255, 255, 255, 0.86);
278 font-size: 26rpx;
279 }
280
281 .join-days {
282 margin-left: 18rpx;
283 white-space: nowrap;
284 }
285
286 .motto {
287 margin-top: 52rpx;
288 color: rgba(255, 255, 255, 0.86);
289 font-size: 24rpx;
290 line-height: 1.75;
291 }
292
293 .edit-btn {
294 width: 168rpx;
295 height: 48rpx;
296 margin: 34rpx 0 0 auto;
297 border-radius: 6rpx;
298 background: #fff;
299 color: #333;
300 font-size: 24rpx;
301 line-height: 48rpx;
302 text-align: center;
303 }
304
305 .menu-panel {
306 position: relative;
307 z-index: 2;
308 min-height: 560rpx;
309 margin-top: -72rpx;
310 padding: 178rpx 48rpx 0;
311 overflow: hidden;
312 }
313
314 .menu-bg {
315 position: absolute;
316 left: 0;
317 top: -400rpx;
318 z-index: 0;
319 width: 100%;
320 height: 1400rpx;
321 }
322
323 .menu-item {
324 position: relative;
325 z-index: 1;
326 display: flex;
327 align-items: center;
328 justify-content: space-between;
329 height: 132rpx;
330 color: #111;
331 font-size: 31rpx;
332 font-weight: 700;
333 }
334
335 .menu-left {
336 display: flex;
337 align-items: center;
338 }
339
340 .menu-icon {
341 width: 38rpx;
342 height: 38rpx;
343 margin-right: 18rpx;
344 }
345
346 .arrow {
347 color: #111;
348 font-size: 42rpx;
349 font-weight: 400;
350 line-height: 1;
351 }
352
353 .logout-area {
354 position: fixed;
355 left: 0;
356 right: 0;
357 bottom: calc(124rpx + env(safe-area-inset-bottom));
358 z-index: 9998;
359 padding: 16rpx 48rpx 18rpx;
360 background: transparent;
361 box-sizing: border-box;
362 }
363
364 .logout-btn {
365 height: 76rpx;
366 border-radius: 50rpx;
367 background: #ad181f;
368 color: #fff;
369 font-size: 28rpx;
370 line-height: 76rpx;
371 }
372
373 .logout-btn::after {
374 border: none;
375 }
376 </style>
1 <template>
2 <view class="notice-page">
3 <z-paging
4 ref="paging"
5 v-model="dataList"
6 class="notice-paging"
7 emptyViewImg="/static/nodata.png"
8 @query="queryList"
9 >
10 <template #top>
11 <view class="notice-hero">
12 <view class="hero-title-row">
13 <view>
14 <view class="hero-title">中国跆拳道协会</view>
15 <view class="hero-subtitle">CHINESE TAEKWONDO ASSOCIATION</view>
16 </view>
17 <view class="hero-page-title">
18 <text>协会资讯</text>
19 <view class="title-line"></view>
20 </view>
21 </view>
22
23 <view class="search-bar">
24 <uni-easyinput
25 v-model="query.keyword"
26 :input-border="false"
27 class="search-input"
28 placeholder="请输入公告标题"
29 placeholderStyle="font-size:28rpx;color:#999"
30 prefixIcon="search"
31 @confirm="handleSearch"
32 @clear="handleSearch"
33 />
34 <view class="search-btn" @click="handleSearch">搜索</view>
35 </view>
36 </view>
37
38 <!-- <view class="notice-tabs">
39 <view class="tab-item active">公告</view>
40 </view> -->
41 </template>
42
43 <view class="notice-list">
44 <view v-for="item in dataList" :key="item.id || item.noteId" class="notice-item" @click="goDetail(item)">
45 <view class="notice-title">{{ item.name || item.title || '--' }}</view>
46 <view v-if="item.introduction || item.remark || item.content" class="notice-summary">
47 {{ item.introduction || item.remark || item.content }}
48 </view>
49 <image
50 v-if="getCover(item)"
51 :src="getCover(item)"
52 class="notice-cover"
53 mode="aspectFill"
54 />
55 <view class="notice-meta">
56 <text>{{ formatDate(item.belongTime || item.createTime || item.publishTime) }}</text>
57 <!-- <view class="meta-right">
58 <text class="heart">♡</text>
59 <text>{{ item.readNum || item.views || item.likeNum || 0 }}</text>
60 <text class="more">...</text>
61 </view> -->
62 </view>
63 </view>
64 </view>
65 </z-paging>
66
67 <dao-guan-tab-bar :currentIndex="2" @switch="onTabSwitch" />
68 </view>
69 </template>
70
71 <script setup>
72 import { ref, reactive } from 'vue'
73 import * as api from '@/common/api.js'
74 import dayjs from 'dayjs'
75 import DaoGuanTabBar from '@/components/dao-guan-tab-bar.vue'
76
77 const dataList = ref([])
78 const paging = ref(null)
79 const query = reactive({
80 keyword: ''
81 })
82
83 const queryList = (pageNum, pageSize) => {
84 api.notice({
85 pageNum,
86 pageSize,
87 name: query.keyword
88 }).then(res => {
89 paging.value?.complete(res.rows || [])
90 }).catch(() => {
91 paging.value?.complete(false)
92 })
93 }
94
95 const handleSearch = () => {
96 paging.value?.reload()
97 }
98
99 const getCover = (item) => {
100 return item.coverUrl || item.cover || item.picUrl || item.imageUrl || item.imgUrl || ''
101 }
102
103 const formatDate = (value) => {
104 if (!value) return ''
105 return dayjs(value).format('YYYY-MM-DD')
106 }
107
108 const goDetail = (item) => {
109 uni.navigateTo({
110 url: `/pages/index/newsDetail?noteId=${item.noteId}`
111 })
112 }
113
114 const onTabSwitch = () => {
115 // tab switch handled by component
116 }
117 </script>
118
119 <style lang="scss" scoped>
120 .notice-page {
121 position: relative;
122 min-height: 100vh;
123 background: #ededf0;
124 box-sizing: border-box;
125 }
126
127 .notice-hero {
128 padding: calc(env(safe-area-inset-top) + 88rpx) 40rpx 34rpx;
129 background: linear-gradient(135deg, #b00005 0%, #760000 100%);
130 color: #fff;
131 }
132
133 .hero-title-row {
134 display: flex;
135 justify-content: space-between;
136 align-items: flex-end;
137 margin-bottom: 42rpx;
138 }
139
140 .hero-title {
141 font-size: 38rpx;
142 letter-spacing: 2rpx;
143 }
144
145 .hero-subtitle {
146 margin-top: 8rpx;
147 color: rgba(255, 255, 255, 0.6);
148 font-size: 16rpx;
149 }
150
151 .hero-page-title {
152 color: #f4b536;
153 font-size: 36rpx;
154 font-weight: 500;
155 text-align: right;
156 }
157
158 .title-line {
159 width: 54rpx;
160 height: 6rpx;
161 margin: 14rpx 0 0 auto;
162 border-radius: 10rpx;
163 background: #f4b536;
164 }
165
166 .search-bar {
167 display: flex;
168 align-items: center;
169 height: 64rpx;
170 border-radius: 34rpx;
171 background: #fff;
172 overflow: hidden;
173 }
174
175 .search-input {
176 flex: 1;
177
178 :deep(.uni-easyinput__content) {
179 height: 64rpx;
180 padding: 0 18rpx 0 28rpx;
181 border-radius: 34rpx;
182 background: #fff;
183 }
184 }
185
186 .search-btn {
187 width: 88rpx;
188 height: 52rpx;
189 margin-right: 6rpx;
190 border-radius: 28rpx;
191 background: #c91c34;
192 color: #fff;
193 font-size: 24rpx;
194 font-weight: 700;
195 line-height: 52rpx;
196 text-align: center;
197 }
198
199 .notice-tabs {
200 display: flex;
201 align-items: center;
202 padding: 24rpx 40rpx 8rpx;
203 }
204
205 .tab-item {
206 position: relative;
207 margin-right: 54rpx;
208 padding-bottom: 14rpx;
209 color: #555;
210 font-size: 30rpx;
211 }
212
213 .tab-item.active {
214 color: #c30d23;
215 font-weight: 700;
216 }
217
218 .tab-item.active::after {
219 content: '';
220 position: absolute;
221 left: 50%;
222 bottom: 0;
223 width: 52rpx;
224 height: 4rpx;
225 border-radius: 4rpx;
226 background: #c30d23;
227 transform: translateX(-50%);
228 }
229
230 .notice-paging {
231 height: 100vh;
232 background: #ededf0;
233 }
234
235 .notice-list {
236 padding: 0 10rpx calc(160rpx + env(safe-area-inset-bottom));
237 }
238
239 .notice-item {
240 margin-bottom: 34rpx;
241 background: #fff;
242 padding: 24rpx;
243 border-radius: 16rpx;
244 margin: 20rpx;
245 }
246
247 .notice-title {
248 color: #111;
249 font-size: 31rpx;
250 font-weight: 800;
251 line-height: 1.42;
252 }
253
254 .notice-summary {
255 display: -webkit-box;
256 margin-top: 12rpx;
257 overflow: hidden;
258 color: #666;
259 font-size: 25rpx;
260 line-height: 1.45;
261 text-overflow: ellipsis;
262 -webkit-box-orient: vertical;
263 -webkit-line-clamp: 2;
264 }
265
266 .notice-cover {
267 width: 100%;
268 height: 330rpx;
269 margin-top: 14rpx;
270 border-radius: 0;
271 background: #ddd;
272 }
273
274 .notice-meta {
275 display: flex;
276 align-items: center;
277 justify-content: space-between;
278 margin-top: 10rpx;
279 color: #999;
280 font-size: 24rpx;
281 }
282
283 .meta-right {
284 display: flex;
285 align-items: center;
286 gap: 8rpx;
287 }
288
289 .heart {
290 font-size: 28rpx;
291 }
292
293 .more {
294 margin-left: 14rpx;
295 letter-spacing: 2rpx;
296 }
297 </style>
...@@ -552,13 +552,14 @@ ...@@ -552,13 +552,14 @@
552 <uni-popup ref="examPointPopup" :mask-click="false" type="center"> 552 <uni-popup ref="examPointPopup" :mask-click="false" type="center">
553 <view class="dialog-wrapper exam-dialog"> 553 <view class="dialog-wrapper exam-dialog">
554 <view class="dialog-close" @click="closeExamPointDialog"></view> 554 <view class="dialog-close" @click="closeExamPointDialog"></view>
555 <view class="dialog-icon success-icon"> 555 <view class="dialog-icon success-icon">
556 <uni-icons color="#29c490" size="48" type="checkmark"></uni-icons> 556 <uni-icons color="#ffffff" size="40" type="check"></uni-icons>
557 </view> 557 </view>
558 <view class="dialog-title">申请成为考点</view> 558 <view class="dialog-title">申请成为考点</view>
559 <view class="dialog-message"> 559 <view class="dialog-message">
560 <text>恭喜您成为中国跆拳道协会团体会员!</text> 560 <text>恭喜您成为中国跆拳道协会单位会员!</text>
561 <text>根据协会考点管理办法,需成为考点单位才能进行考级业务的办理。</text> 561 <text>根据协会考点管理办法,需成为考点单位才能进行考级业务的办理。</text>
562 <text>是否现在申请成为考点?</text>
562 </view> 563 </view>
563 <view class="dialog-footer"> 564 <view class="dialog-footer">
564 <button class="dialog-btn cancel" @click="closeExamPointDialog">取消</button> 565 <button class="dialog-btn cancel" @click="closeExamPointDialog">取消</button>
...@@ -1049,11 +1050,11 @@ function checkDialogs() { ...@@ -1049,11 +1050,11 @@ function checkDialogs() {
1049 refreshCaptcha() 1050 refreshCaptcha()
1050 bindingPhonePopup.value.open() 1051 bindingPhonePopup.value.open()
1051 } 1052 }
1053 console.log(99,app.globalData.memberInfo?.activeStatus,app.globalData.authenticationStatus,user.hintFlag,app.globalData.deptType,memberInfoData.isPoints,app.globalData.deptType)
1052 1054
1053 // 申请考点条件: activeStatus=1 && authenticationStatus=2 && hintFlag=1 && deptType=6 && isPoints=1 1055 // 申请考点条件: activeStatus=1 && authenticationStatus=2 && hintFlag=1 && deptType=6 && isPoints=1
1054 if (app.globalData.memberInfo?.activeStatus == 1 && 1056 if (app.globalData.memberInfo?.activeStatus == 1 &&
1055 app.globalData.authenticationStatus == 2 && 1057 app.globalData.authenticationStatus == 2 &&
1056 user.hintFlag == 1 &&
1057 app.globalData.deptType == 6 && 1058 app.globalData.deptType == 6 &&
1058 memberInfoData.isPoints == 1) { 1059 memberInfoData.isPoints == 1) {
1059 examPointPopup.value.open() 1060 examPointPopup.value.open()
...@@ -1481,7 +1482,7 @@ function checkDialogs() { ...@@ -1481,7 +1482,7 @@ function checkDialogs() {
1481 } 1482 }
1482 1483
1483 .success-icon { 1484 .success-icon {
1484 color: #29c490; 1485 color: #29c490;
1485 } 1486 }
1486 1487
1487 /* 密码提示弹框样式 */ 1488 /* 密码提示弹框样式 */
......
...@@ -13,7 +13,8 @@ ...@@ -13,7 +13,8 @@
13 useUserStore 13 useUserStore
14 } from '../../store/modules/user'; 14 } from '../../store/modules/user';
15 15
16 const userStore = useUserStore() 16 const userStore = useUserStore()
17 const app = getApp()
17 18
18 onShow(() => { 19 onShow(() => {
19 let user = userStore.user 20 let user = userStore.user
...@@ -25,11 +26,21 @@ ...@@ -25,11 +26,21 @@
25 } 26 }
26 27
27 let userName = uni.getStorageSync('userName') 28 let userName = uni.getStorageSync('userName')
29 console.log('userName', userName)
30 console.log('app.globalData.userType ', app.globalData.userType )
28 if (userName) { 31 if (userName) {
29 uni.reLaunch({ 32 if(app.globalData.userType == 4){
33 uni.reLaunch({
34 url: '/pages/index/daoGuanPerson'
35 })
36 return
37 }else{
38 uni.reLaunch({
30 url: '/pages/index/home' 39 url: '/pages/index/home'
31 }) 40 })
32 return 41 return
42 }
43
33 } 44 }
34 45
35 let webUserName = uni.getStorageSync('webUserName') 46 let webUserName = uni.getStorageSync('webUserName')
...@@ -43,4 +54,4 @@ ...@@ -43,4 +54,4 @@
43 </script> 54 </script>
44 <style scope lang="scss"> 55 <style scope lang="scss">
45 56
46 </style>
...\ No newline at end of file ...\ No newline at end of file
57 </style>
......
...@@ -204,7 +204,6 @@ import { ...@@ -204,7 +204,6 @@ import {
204 import config from "/config.js"; 204 import config from "/config.js";
205 import { 205 import {
206 wxLogin, 206 wxLogin,
207 logout,
208 getWebInfo 207 getWebInfo
209 } from '@/common/login.js'; 208 } from '@/common/login.js';
210 import {useUserStore} from "@/store/modules/user.js"; 209 import {useUserStore} from "@/store/modules/user.js";
...@@ -238,6 +237,9 @@ const showConfirm = ref(false) ...@@ -238,6 +237,9 @@ const showConfirm = ref(false)
238 let hasOpenedBindPopup = false 237 let hasOpenedBindPopup = false
239 238
240 onShow(() => { 239 onShow(() => {
240 // 重置绑定弹框标志,确保每次进入页面都能正确弹出
241 hasOpenedBindPopup = false
242
241 let webUserName = uni.getStorageSync('webUserName') 243 let webUserName = uni.getStorageSync('webUserName')
242 if (!webUserName) { 244 if (!webUserName) {
243 // 登录后需要等待数据加载完成 245 // 登录后需要等待数据加载完成
...@@ -245,7 +247,13 @@ onShow(() => { ...@@ -245,7 +247,13 @@ onShow(() => {
245 getWebInfo().then(() => { 247 getWebInfo().then(() => {
246 // 数据加载完成后检查是否需要弹出绑定框 248 // 数据加载完成后检查是否需要弹出绑定框
247 checkAndOpenBindPopup() 249 checkAndOpenBindPopup()
250 }).catch(() => {
251 // getWebInfo 失败时也检查一下
252 checkAndOpenBindPopup()
248 }) 253 })
254 }).catch(() => {
255 // wxLogin 失败时也检查一下
256 checkAndOpenBindPopup()
249 }) 257 })
250 } else { 258 } else {
251 // 已登录,直接检查 259 // 已登录,直接检查
...@@ -516,14 +524,23 @@ const cancelLogout = () => { ...@@ -516,14 +524,23 @@ const cancelLogout = () => {
516 }; 524 };
517 525
518 // 确认退出登录 526 // 确认退出登录
519 const confirmLogout = () => { 527 const confirmLogout = async () => {
520 // 调用退出登录接口 528 showConfirm.value = false
521 logout().then(() => { 529
522 // 跳转到登录页 530 uni.showLoading({ title: '退出中...', mask: true })
523 uni.reLaunch({ 531
524 url: '/login/login' 532 // 调用解绑接口
525 }) 533 await to(unbindUser())
526 }); 534
535 // 清除缓存和用户信息
536 uni.removeStorageSync('webUserName')
537 userStore.setPerInfo(null)
538 userStore.setUser(null)
539
540 // 跳转到登录页
541 uni.reLaunch({
542 url: '/login/login'
543 })
527 }; 544 };
528 </script> 545 </script>
529 546
......
1 <template> 1 <template>
2 <view class="hasfixedbottom"> 2 <view class="hasfixedbottom">
3 <view class="searchbar"> 3 <view class="searchbar">
4
4 <uni-easyinput placeholderStyle="font-size:30rpx" :input-border="false" prefixIcon="search" 5 <uni-easyinput placeholderStyle="font-size:30rpx" :input-border="false" prefixIcon="search"
5 v-model="queryParams.perName" placeholder="搜索姓名或证件号码" @blur="getList" @clear="getList"> 6 v-model="queryParams.perName" placeholder="搜索姓名或证件号码" @blur="getList" @clear="getList">
6 </uni-easyinput> 7 </uni-easyinput>
7 <view class="invertedbtn-red" @click="goVipList">+ 添加会员</view> 8 <view class="invertedbtn-red" @click="showAddPopup">+ 添加</view>
9 <view class="invertedbtn-red" @click="goVipList">+ 在线选择</view>
8 </view> 10 </view>
9 <view style="padding:0 20rpx"> 11 <view style="padding:0 20rpx">
10 12
...@@ -58,6 +60,33 @@ ...@@ -58,6 +60,33 @@
58 </view> 60 </view>
59 </view> 61 </view>
60 </uni-popup> 62 </uni-popup>
63
64 <!-- 添加会员弹框 -->
65 <uni-popup ref="addPopup" type="center">
66 <view class="add-popup">
67 <view class="popup-title">添加会员</view>
68 <view class="popup-form">
69 <view class="form-item">
70 <view class="form-label">证件类型</view>
71 <view class="form-input">
72 <picker :value="idcListIndex" :range="idcList" range-key="label" @change="onIdcTypeChange">
73 <view class="picker-value">{{ idcList[idcListIndex]?.label }}</view>
74 </picker>
75 </view>
76 </view>
77 <view class="form-item">
78 <view class="form-label">证件号</view>
79 <view class="form-input">
80 <input v-model="addForm.idcCode" placeholder="请输入证件号" placeholder-class="placeholder-class"/>
81 </view>
82 </view>
83 </view>
84 <view class="popup-btns">
85 <view class="popup-btn cancel" @click="closeAddPopup">取消</view>
86 <view class="popup-btn confirm" @click="confirmAdd">确定</view>
87 </view>
88 </view>
89 </uni-popup>
61 </view> 90 </view>
62 </template> 91 </template>
63 92
...@@ -78,7 +107,18 @@ ...@@ -78,7 +107,18 @@
78 const nowYear = ref(1) 107 const nowYear = ref(1)
79 const nowItem = ref({}) 108 const nowItem = ref({})
80 const pickView = ref(null) 109 const pickView = ref(null)
110 const addPopup = ref(null)
81 const visible = ref(true) 111 const visible = ref(true)
112 const addForm = ref({
113 idcCode: '',
114 idType: '0'
115 })
116 const idcList = ref([
117 { label: '身份证', value: '0' },
118 { label: '来往大陆(内地)通行证', value: '1' },
119 { label: '香港身份证', value: '5' }
120 ])
121 const idcListIndex = ref(0)
82 const yearlist = ref([{ 122 const yearlist = ref([{
83 text: '一年', 123 text: '一年',
84 value: 1 124 value: 1
...@@ -197,6 +237,50 @@ ...@@ -197,6 +237,50 @@
197 url: `/myCenter/payOrder?rangeId=${queryParams.value.rangeId}` 237 url: `/myCenter/payOrder?rangeId=${queryParams.value.rangeId}`
198 }) 238 })
199 } 239 }
240
241 // 显示添加弹框
242 function showAddPopup() {
243 addForm.value.idcCode = ''
244 idcListIndex.value = 0
245 addPopup.value.open()
246 }
247
248 // 关闭添加弹框
249 function closeAddPopup() {
250 addPopup.value.close()
251 }
252
253 // 证件类型选择
254 function onIdcTypeChange(e) {
255 idcListIndex.value = e.detail.value
256 addForm.value.idType = idcList.value[idcListIndex.value].value
257 }
258
259 // 确认添加
260 async function confirmAdd() {
261 if (!addForm.value.idcCode) {
262 uni.showToast({ title: '请输入证件号', icon: 'none' })
263 return
264 }
265 if (!queryParams.value.rangeId) {
266 uni.showToast({ title: '缺少rangeId', icon: 'none' })
267 return
268 }
269
270 try {
271 await api.memberInsertPersons({
272 rangeId: queryParams.value.rangeId,
273 year: 1,
274 idcCode: addForm.value.idcCode
275 })
276 uni.showToast({ title: '添加成功', icon: 'success' })
277 closeAddPopup()
278 getList()
279 getCount()
280 } catch (e) {
281 console.error(e)
282 }
283 }
200 </script> 284 </script>
201 285
202 <style scoped lang="scss"> 286 <style scoped lang="scss">
...@@ -301,4 +385,86 @@ ...@@ -301,4 +385,86 @@
301 font-size: 32rpx; 385 font-size: 32rpx;
302 border: none; 386 border: none;
303 } 387 }
388
389 /* 添加会员弹框 */
390 .add-popup {
391 width: 600rpx;
392 background: #ffffff;
393 border-radius: 24rpx;
394 overflow: hidden;
395 }
396
397 .popup-title {
398 font-size: 32rpx;
399 font-weight: 500;
400 color: #333;
401 text-align: center;
402 padding: 40rpx 30rpx 20rpx;
403 }
404
405 .popup-form {
406 padding: 20rpx 30rpx 40rpx;
407 }
408
409 .form-item {
410 display: flex;
411 align-items: center;
412 margin-bottom: 24rpx;
413 }
414
415 .form-item:last-child {
416 margin-bottom: 0;
417 }
418
419 .form-label {
420 width: 140rpx;
421 font-size: 28rpx;
422 color: #333;
423 flex-shrink: 0;
424 }
425
426 .form-input {
427 flex: 1;
428 background: #f5f5f5;
429 border-radius: 12rpx;
430 padding: 20rpx 24rpx;
431 }
432
433 .form-input input {
434 font-size: 28rpx;
435 color: #333;
436 width: 100%;
437 }
438
439 .picker-value {
440 font-size: 28rpx;
441 color: #333;
442 }
443
444 .placeholder-class {
445 color: #999;
446 }
447
448 .popup-btns {
449 display: flex;
450 border-top: 1rpx solid #eee;
451 }
452
453 .popup-btn {
454 flex: 1;
455 height: 100rpx;
456 line-height: 100rpx;
457 text-align: center;
458 font-size: 30rpx;
459 }
460
461 .popup-btn.cancel {
462 color: #666;
463 border-right: 1rpx solid #eee;
464 }
465
466 .popup-btn.confirm {
467 color: #E60012;
468 font-weight: 500;
469 }
304 </style> 470 </style>
...\ No newline at end of file ...\ No newline at end of file
......
Styling with Markdown is supported
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!