diff --git a/client/src/app.config.ts b/client/src/app.config.ts
index 0d2dc78..c8f333d 100644
--- a/client/src/app.config.ts
+++ b/client/src/app.config.ts
@@ -2,7 +2,12 @@ export default defineAppConfig({
pages: [
'pages/index/index',
'pages/zone/index',
- 'pages/vip/index'
+ 'pages/vip/index',
+ 'pages/favorites/index',
+ 'pages/history/index',
+ 'pages/notifications/index',
+ 'pages/orders/index',
+ 'pages/activity/index'
],
window: {
backgroundTextStyle: 'light',
@@ -10,5 +15,17 @@ export default defineAppConfig({
navigationBarTitleText: 'LIMO来刻',
navigationBarTextStyle: 'white',
navigationStyle: 'custom'
+ },
+ // 声明需要的隐私接口
+ requiredPrivateInfos: [
+ 'getLocation',
+ 'chooseLocation',
+ 'chooseAddress'
+ ],
+ // 位置权限说明
+ permission: {
+ 'scope.userLocation': {
+ desc: '您的位置信息将用于推荐附近的运动场馆'
+ }
}
})
diff --git a/client/src/components/AuthModal/index.scss b/client/src/components/AuthModal/index.scss
new file mode 100644
index 0000000..2d15a37
--- /dev/null
+++ b/client/src/components/AuthModal/index.scss
@@ -0,0 +1,580 @@
+.auth-modal {
+ position: fixed;
+ top: 0;
+ left: 0;
+ right: 0;
+ bottom: 0;
+ z-index: 1000;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ padding: 32rpx;
+
+ .modal-overlay {
+ position: absolute;
+ top: 0;
+ left: 0;
+ right: 0;
+ bottom: 0;
+ background: rgba(0, 0, 0, 0.6);
+ animation: fadeIn 0.3s ease-out;
+ }
+
+ .modal-content {
+ position: relative;
+ z-index: 10;
+ background: #ffffff;
+ border-radius: 32rpx;
+ padding: 48rpx 32rpx;
+ width: 100%;
+ max-width: 640rpx;
+ animation: slideUp 0.3s ease-out;
+ box-shadow: 0 32rpx 96rpx rgba(0, 0, 0, 0.2);
+
+ .modal-header {
+ text-align: center;
+ margin-bottom: 32rpx;
+
+ .logo-container {
+ margin-bottom: 24rpx;
+
+ .app-logo {
+ width: 120rpx;
+ height: 120rpx;
+ }
+ }
+
+ .modal-title {
+ font-size: 36rpx;
+ font-weight: bold;
+ color: #111827;
+ display: block;
+ margin-bottom: 12rpx;
+ }
+
+ .modal-subtitle {
+ font-size: 26rpx;
+ color: #6B7280;
+ display: block;
+ }
+ }
+
+ // 步骤指示器
+ .step-indicator {
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ margin-bottom: 48rpx;
+ padding: 0 32rpx;
+
+ .step-item {
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ position: relative;
+
+ .step-number {
+ width: 64rpx;
+ height: 64rpx;
+ border-radius: 50%;
+ background: #F3F4F6;
+ color: #9CA3AF;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ font-size: 24rpx;
+ font-weight: 600;
+ margin-bottom: 12rpx;
+ border: 3rpx solid #E5E7EB;
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+ }
+
+ .step-text {
+ font-size: 20rpx;
+ color: #9CA3AF;
+ font-weight: 500;
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+ }
+
+ &.active {
+ .step-number {
+ background: linear-gradient(135deg, #05C7C7 0%, #04B5B5 100%);
+ color: #ffffff;
+ border-color: #05C7C7;
+ box-shadow: 0 8rpx 24rpx rgba(5, 199, 199, 0.3);
+ }
+
+ .step-text {
+ color: #05C7C7;
+ font-weight: 600;
+ }
+ }
+
+ &.completed {
+ .step-number {
+ background: #10B981;
+ color: #ffffff;
+ border-color: #10B981;
+ }
+
+ .step-text {
+ color: #10B981;
+ }
+ }
+ }
+
+ .step-line {
+ width: 80rpx;
+ height: 4rpx;
+ background: #E5E7EB;
+ margin: 0 24rpx;
+ margin-bottom: 32rpx;
+ border-radius: 2rpx;
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+
+ &.active {
+ background: linear-gradient(135deg, #05C7C7 0%, #04B5B5 100%);
+ box-shadow: 0 2rpx 8rpx rgba(5, 199, 199, 0.3);
+ }
+ }
+ }
+
+ // 授权步骤容器
+ .auth-step {
+ animation: fadeInUp 0.3s ease-out;
+ }
+
+ .auth-info {
+ margin-bottom: 48rpx;
+
+ .info-item {
+ display: flex;
+ align-items: center;
+ padding: 24rpx;
+ background: #F9FAFB;
+ border-radius: 24rpx;
+ margin-bottom: 24rpx;
+ border: 2rpx solid #F3F4F6;
+
+ &:last-child {
+ margin-bottom: 0;
+ }
+
+ .info-icon {
+ width: 80rpx;
+ height: 80rpx;
+ background: #ffffff;
+ border-radius: 20rpx;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ margin-right: 24rpx;
+ box-shadow: 0 4rpx 12rpx rgba(0, 0, 0, 0.05);
+
+ .icon-text {
+ font-size: 36rpx;
+ }
+ }
+
+ .info-content {
+ flex: 1;
+
+ .info-title {
+ font-size: 28rpx;
+ font-weight: 600;
+ color: #111827;
+ display: block;
+ margin-bottom: 0;
+ }
+
+ .info-desc {
+ font-size: 24rpx;
+ color: #6B7280;
+ line-height: 1;
+ }
+ }
+ }
+ }
+
+ .auth-buttons {
+ margin-bottom: 32rpx;
+
+ .auth-btn {
+ width: 100%;
+ height: 96rpx;
+ border-radius: 24rpx;
+ border: none;
+ font-size: 28rpx;
+ font-weight: 600;
+ margin-bottom: 24rpx;
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+ position: relative;
+ overflow: hidden;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+
+ &:last-child {
+ margin-bottom: 0;
+ }
+
+ &:active {
+ transform: scale(0.98);
+ }
+
+ &.primary {
+ background: linear-gradient(135deg, #05C7C7 0%, #04B5B5 100%);
+ color: #ffffff;
+
+ &:disabled {
+ background: #10B981;
+ opacity: 0.8;
+ }
+ }
+
+ &.secondary {
+ background: #F3F4F6;
+ color: #374151;
+ border: 2rpx solid #E5E7EB;
+
+ &:disabled {
+ background: #10B981;
+ color: #ffffff;
+ border-color: #10B981;
+ }
+ }
+
+ .btn-text {
+ position: relative;
+ z-index: 2;
+ line-height: 1;
+ }
+
+ // 按钮光泽效果
+ &::before {
+ content: '';
+ position: absolute;
+ top: 0;
+ left: -100%;
+ width: 100%;
+ height: 100%;
+ background: linear-gradient(90deg, transparent, rgba(255, 255, 255, 0.2), transparent);
+ transition: left 0.5s;
+ }
+
+ &:active::before {
+ left: 100%;
+ }
+ }
+ }
+
+ // 昵称输入区域
+ .nickname-input-section {
+ margin-bottom: 32rpx;
+
+ .input-label {
+ margin-bottom: 16rpx;
+
+ .label-text {
+ font-size: 28rpx;
+ font-weight: 600;
+ color: #111827;
+ }
+ }
+
+ .nickname-input {
+ width: 100%;
+ height: 96rpx;
+ background: #F9FAFB;
+ border: 2rpx solid #E5E7EB;
+ border-radius: 24rpx;
+ padding: 0 24rpx;
+ font-size: 28rpx;
+ color: #111827;
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+
+ &:focus {
+ border-color: #05C7C7;
+ background: #ffffff;
+ box-shadow: 0 0 0 6rpx rgba(5, 199, 199, 0.1);
+ }
+
+ &::placeholder {
+ color: #9CA3AF;
+ font-size: 26rpx;
+ }
+ }
+ }
+
+ .auth-actions {
+ margin-bottom: 32rpx;
+
+ .complete-btn {
+ width: 100%;
+ height: 88rpx;
+ background: linear-gradient(135deg, #FBBF24 0%, #F59E0B 100%);
+ border-radius: 24rpx;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+ box-shadow: 0 16rpx 48rpx rgba(251, 191, 36, 0.3);
+
+ &:active {
+ transform: scale(0.98);
+ }
+
+ .complete-text {
+ font-size: 32rpx;
+ font-weight: bold;
+ color: #ffffff;
+ text-shadow: 0 2rpx 8rpx rgba(0, 0, 0, 0.2);
+ }
+ }
+
+ .next-btn {
+ width: 100%;
+ height: 88rpx;
+ background: linear-gradient(135deg, #05C7C7 0%, #04B5B5 100%);
+ border-radius: 24rpx;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+ box-shadow: 0 16rpx 48rpx rgba(5, 199, 199, 0.3);
+
+ &:active {
+ transform: scale(0.98);
+ }
+
+ .next-text {
+ font-size: 32rpx;
+ font-weight: bold;
+ color: #ffffff;
+ text-shadow: 0 2rpx 8rpx rgba(0, 0, 0, 0.2);
+ }
+ }
+
+ .action-row {
+ display: flex;
+ gap: 24rpx;
+ align-items: center;
+
+ .back-btn {
+ flex: 1;
+ height: 80rpx;
+ background: #F3F4F6;
+ border-radius: 24rpx;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+ border: 2rpx solid #E5E7EB;
+
+ &:active {
+ transform: scale(0.98);
+ background: #E5E7EB;
+ }
+
+ .back-text {
+ font-size: 28rpx;
+ font-weight: 600;
+ color: #6B7280;
+ }
+ }
+
+ .skip-btn {
+ flex: 1;
+ text-align: center;
+ padding: 24rpx;
+
+ .skip-text {
+ font-size: 28rpx;
+ color: #9CA3AF;
+ text-decoration: underline;
+ }
+ }
+ }
+
+ .skip-btn {
+ text-align: center;
+ padding: 24rpx;
+
+ .skip-text {
+ font-size: 28rpx;
+ color: #9CA3AF;
+ text-decoration: underline;
+ }
+ }
+ }
+
+ .privacy-notice {
+ text-align: center;
+ padding: 0 16rpx;
+
+ .notice-text {
+ font-size: 24rpx;
+ color: #9CA3AF;
+ line-height: 1.5;
+
+ .link-text {
+ color: #05C7C7;
+ text-decoration: underline;
+ }
+ }
+ }
+ }
+}
+
+// 动画
+@keyframes fadeIn {
+ from {
+ opacity: 0;
+ }
+ to {
+ opacity: 1;
+ }
+}
+
+@keyframes slideUp {
+ from {
+ opacity: 0;
+ transform: translateY(100rpx);
+ }
+ to {
+ opacity: 1;
+ transform: translateY(0);
+ }
+}
+
+@keyframes fadeInUp {
+ from {
+ opacity: 0;
+ transform: translateY(20rpx);
+ }
+ to {
+ opacity: 1;
+ transform: translateY(0);
+ }
+}
+
+// 响应式设计
+@media (max-width: 480px) {
+ .auth-modal {
+ padding: 24rpx;
+
+ .modal-content {
+ padding: 40rpx 24rpx;
+
+ .modal-header {
+ margin-bottom: 24rpx;
+
+ .logo-container .app-logo {
+ width: 100rpx;
+ height: 100rpx;
+ }
+
+ .modal-title {
+ font-size: 32rpx;
+ }
+
+ .modal-subtitle {
+ font-size: 24rpx;
+ }
+ }
+
+ .step-indicator {
+ margin-bottom: 40rpx;
+ padding: 0 16rpx;
+
+ .step-item {
+ .step-number {
+ width: 56rpx;
+ height: 56rpx;
+ font-size: 22rpx;
+ margin-bottom: 8rpx;
+ }
+
+ .step-text {
+ font-size: 18rpx;
+ }
+ }
+
+ .step-line {
+ width: 60rpx;
+ margin: 0 16rpx;
+ margin-bottom: 24rpx;
+ }
+ }
+
+ .auth-info {
+ margin-bottom: 40rpx;
+
+ .info-item {
+ padding: 20rpx;
+
+ .info-icon {
+ width: 72rpx;
+ height: 72rpx;
+ margin-right: 20rpx;
+
+ .icon-text {
+ font-size: 32rpx;
+ }
+ }
+
+ .info-content {
+ .info-title {
+ font-size: 26rpx;
+ }
+
+ .info-desc {
+ font-size: 22rpx;
+ }
+ }
+ }
+ }
+
+ .auth-buttons .auth-btn {
+ height: 88rpx;
+ font-size: 26rpx;
+ }
+
+ .nickname-input-section {
+ margin-bottom: 24rpx;
+
+ .input-label .label-text {
+ font-size: 26rpx;
+ }
+
+ .nickname-input {
+ height: 80rpx;
+ font-size: 26rpx;
+ padding: 0 20rpx;
+
+ &::placeholder {
+ font-size: 24rpx;
+ }
+ }
+ }
+
+ .auth-actions {
+ .complete-btn, .next-btn {
+ height: 80rpx;
+
+ .complete-text, .next-text {
+ font-size: 28rpx;
+ }
+ }
+
+ .action-row .back-btn {
+ height: 72rpx;
+
+ .back-text {
+ font-size: 26rpx;
+ }
+ }
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/client/src/components/AuthModal/index.vue b/client/src/components/AuthModal/index.vue
new file mode 100644
index 0000000..038db53
--- /dev/null
+++ b/client/src/components/AuthModal/index.vue
@@ -0,0 +1,299 @@
+
+
+
+
+
+
+
+
+
+ 1
+ 手机号
+
+
+
+ 2
+ 个人信息
+
+
+
+
+
+
+
+
+ 📱
+
+
+ 手机号授权
+ 用于账号安全、登录验证和消息通知
+
+
+
+
+
+
+
+
+
+
+ 下一步
+
+
+ 暂不授权
+
+
+
+
+
+
+
+
+
+ 👤
+
+
+ 设置个人信息
+ 请选择头像并输入昵称,用于个性化展示
+
+
+
+
+
+
+
+
+
+
+
+ 请输入昵称
+
+
+
+
+
+
+ 完成设置
+
+
+
+ 上一步
+
+
+ 暂不授权
+
+
+
+
+
+
+
+ 我们承诺保护您的隐私安全,详见
+ 《隐私政策》
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/client/src/components/index.ts b/client/src/components/index.ts
index 2053896..4e404ea 100644
--- a/client/src/components/index.ts
+++ b/client/src/components/index.ts
@@ -1,4 +1,5 @@
/**
* 组件导出
*/
-export { default as CommonButton } from './CommonButton/index.vue'
\ No newline at end of file
+export { default as CommonButton } from './CommonButton/index.vue'
+export { default as AuthModal } from './AuthModal/index.vue'
\ No newline at end of file
diff --git a/client/src/pages/activity/index.config.ts b/client/src/pages/activity/index.config.ts
new file mode 100644
index 0000000..33f34e4
--- /dev/null
+++ b/client/src/pages/activity/index.config.ts
@@ -0,0 +1,6 @@
+export default definePageConfig({
+ navigationBarTitleText: '历史活动',
+ navigationBarBackgroundColor: '#ffffff',
+ navigationBarTextStyle: 'black',
+ navigationStyle: 'default'
+})
\ No newline at end of file
diff --git a/client/src/pages/activity/index.scss b/client/src/pages/activity/index.scss
new file mode 100644
index 0000000..37040db
--- /dev/null
+++ b/client/src/pages/activity/index.scss
@@ -0,0 +1,137 @@
+.activity-page {
+ min-height: 100vh;
+ background: #f9fafb;
+
+ // Empty State
+ .empty-state {
+ padding: 120rpx 48rpx;
+ display: flex;
+ justify-content: center;
+
+ .empty-container {
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ text-align: center;
+
+ .empty-icon {
+ font-size: 120rpx;
+ margin-bottom: 32rpx;
+ opacity: 0.6;
+ }
+
+ .empty-title {
+ font-size: 32rpx;
+ font-weight: 600;
+ color: #374151;
+ margin-bottom: 16rpx;
+ }
+
+ .empty-subtitle {
+ font-size: 26rpx;
+ color: #9ca3af;
+ line-height: 1.5;
+ }
+ }
+ }
+
+ // Activity List
+ .activity-list {
+ padding: 24rpx;
+
+ .date-group {
+ margin-bottom: 48rpx;
+
+ &:last-child {
+ margin-bottom: 24rpx;
+ }
+
+ .date-header {
+ margin-bottom: 24rpx;
+ padding: 0 8rpx;
+
+ .date-text {
+ font-size: 28rpx;
+ font-weight: 600;
+ color: #374151;
+ position: relative;
+
+ &::after {
+ content: '';
+ position: absolute;
+ bottom: -8rpx;
+ left: 0;
+ width: 48rpx;
+ height: 4rpx;
+ background: linear-gradient(135deg, #05c7c7 0%, #04b5b5 100%);
+ border-radius: 2rpx;
+ }
+ }
+ }
+
+ .activities {
+ .activity-item {
+ background: #ffffff;
+ border-radius: 20rpx;
+ padding: 24rpx;
+ margin-bottom: 16rpx;
+ border: 2rpx solid #f3f4f6;
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+
+ &:active {
+ transform: scale(0.995);
+ box-shadow: 0 8rpx 24rpx rgba(0, 0, 0, 0.08);
+ }
+
+ &:last-child {
+ margin-bottom: 0;
+ }
+
+ .activity-content {
+ width: 100%;
+
+ .activity-title {
+ font-size: 28rpx;
+ font-weight: 600;
+ color: #111827;
+ margin-bottom: 8rpx;
+ line-height: 1.4;
+ display: block;
+ }
+
+ .activity-description {
+ font-size: 24rpx;
+ color: #6b7280;
+ margin-bottom: 12rpx;
+ line-height: 1.4;
+ display: block;
+ }
+
+ .activity-time {
+ font-size: 22rpx;
+ color: #9ca3af;
+ display: block;
+ }
+ }
+ }
+ }
+ }
+ }
+
+ // Load More
+ .load-more {
+ padding: 32rpx 24rpx;
+ text-align: center;
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+
+ &:active {
+ transform: scale(0.98);
+ }
+
+ .load-more-text {
+ font-size: 26rpx;
+ color: #6b7280;
+ font-weight: 500;
+ }
+ }
+}
\ No newline at end of file
diff --git a/client/src/pages/activity/index.vue b/client/src/pages/activity/index.vue
new file mode 100644
index 0000000..a61dfd3
--- /dev/null
+++ b/client/src/pages/activity/index.vue
@@ -0,0 +1,202 @@
+
+
+
+
+
+ 📝
+ 暂无活动记录
+ 开始使用LIMO来刻,记录您的运动时光
+
+
+
+
+
+
+
+
+
+
+
+
+ {{ activity.title }}
+ {{ activity.description }}
+ {{ activity.time }}
+
+
+
+
+
+
+
+
+ {{ loading ? '加载中...' : '加载更多' }}
+
+
+
+
+
\ No newline at end of file
diff --git a/client/src/pages/favorites/index.config.ts b/client/src/pages/favorites/index.config.ts
new file mode 100644
index 0000000..96fe731
--- /dev/null
+++ b/client/src/pages/favorites/index.config.ts
@@ -0,0 +1,6 @@
+export default definePageConfig({
+ navigationBarTitleText: '我的收藏',
+ navigationBarBackgroundColor: '#ffffff',
+ navigationBarTextStyle: 'black',
+ navigationStyle: 'default'
+})
\ No newline at end of file
diff --git a/client/src/pages/favorites/index.scss b/client/src/pages/favorites/index.scss
new file mode 100644
index 0000000..1b04170
--- /dev/null
+++ b/client/src/pages/favorites/index.scss
@@ -0,0 +1,166 @@
+.favorites-page {
+ min-height: 100vh;
+ background: #f8fafc;
+ padding-bottom: 32rpx;
+}
+
+.page-header {
+ background: #ffffff;
+ padding: 48rpx 32rpx 32rpx 32rpx;
+ border-bottom: 2rpx solid #f1f5f9;
+}
+
+.header-title {
+ font-size: 36rpx;
+ font-weight: bold;
+ color: #1e293b;
+ display: block;
+ margin-bottom: 8rpx;
+}
+
+.header-subtitle {
+ font-size: 26rpx;
+ color: #64748b;
+ display: block;
+}
+
+.empty-state {
+ padding: 120rpx 32rpx;
+ min-height: 600rpx;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+}
+
+.empty-container {
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ text-align: center;
+ gap: 24rpx;
+}
+
+.empty-icon {
+ font-size: 96rpx;
+ margin-bottom: 16rpx;
+}
+
+.empty-title {
+ font-size: 32rpx;
+ font-weight: 600;
+ color: #374151;
+}
+
+.empty-subtitle {
+ font-size: 26rpx;
+ color: #6b7280;
+ line-height: 1.5;
+ max-width: 400rpx;
+}
+
+.empty-button {
+ background: linear-gradient(135deg, #05c7c7 0%, #04b5b5 100%);
+ color: #ffffff;
+ padding: 24rpx 48rpx;
+ border-radius: 32rpx;
+ margin-top: 16rpx;
+ box-shadow: 0 8rpx 24rpx rgba(5, 199, 199, 0.2);
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+}
+
+.empty-button:active {
+ transform: scale(0.95);
+}
+
+.favorites-list {
+ padding: 16rpx;
+}
+
+.venue-card {
+ background: #ffffff;
+ border-radius: 16rpx;
+ margin-bottom: 16rpx;
+ padding: 24rpx;
+ border: 2rpx solid #f1f5f9;
+}
+
+.venue-info {
+ width: 100%;
+}
+
+.venue-name {
+ font-size: 30rpx;
+ font-weight: bold;
+ color: #1e293b;
+ margin-bottom: 8rpx;
+ display: block;
+}
+
+.venue-address {
+ font-size: 24rpx;
+ color: #64748b;
+ line-height: 1.4;
+ margin-bottom: 16rpx;
+ display: block;
+}
+
+.venue-footer {
+ display: flex;
+ align-items: center;
+ justify-content: space-between;
+}
+
+.venue-distance {
+ font-size: 22rpx;
+ color: #05c7c7;
+ font-weight: 500;
+}
+
+.venue-actions {
+ display: flex;
+ gap: 12rpx;
+}
+
+.action-btn {
+ padding: 12rpx 20rpx;
+ border-radius: 20rpx;
+ font-size: 22rpx;
+ font-weight: 500;
+ transition: all 0.3s ease;
+}
+
+.action-btn:active {
+ transform: scale(0.95);
+}
+
+.remove-btn {
+ background: #f8f9fa;
+ color: #6c757d;
+ border: 2rpx solid #e9ecef;
+}
+
+.remove-btn:active {
+ background: #e9ecef;
+}
+
+.zone-btn {
+ background: linear-gradient(135deg, #05c7c7 0%, #04b5b5 100%);
+ color: #ffffff;
+}
+
+.zone-btn:active {
+ background: linear-gradient(135deg, #04b5b5 0%, #039a9a 100%);
+}
+
+.btn-text {
+ font-size: 22rpx;
+}
+
+@keyframes pulse {
+ 0%, 100% {
+ opacity: 1;
+ }
+ 50% {
+ opacity: 0.5;
+ }
+}
\ No newline at end of file
diff --git a/client/src/pages/favorites/index.vue b/client/src/pages/favorites/index.vue
new file mode 100644
index 0000000..7b6ed61
--- /dev/null
+++ b/client/src/pages/favorites/index.vue
@@ -0,0 +1,113 @@
+
+
+
+
+
+
+
+
+ 💝
+ 暂无收藏场馆
+ 快去发现喜欢的运动场馆吧
+
+ 去发现
+
+
+
+
+
+
+
+
+ {{ venue.name }}
+ {{ venue.address }}
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/client/src/pages/history/index.config.ts b/client/src/pages/history/index.config.ts
new file mode 100644
index 0000000..f37d4ef
--- /dev/null
+++ b/client/src/pages/history/index.config.ts
@@ -0,0 +1,6 @@
+export default definePageConfig({
+ navigationBarTitleText: '观看历史',
+ navigationBarBackgroundColor: '#ffffff',
+ navigationBarTextStyle: 'black',
+ navigationStyle: 'default'
+})
\ No newline at end of file
diff --git a/client/src/pages/history/index.scss b/client/src/pages/history/index.scss
new file mode 100644
index 0000000..d6a7bc9
--- /dev/null
+++ b/client/src/pages/history/index.scss
@@ -0,0 +1,233 @@
+.history-page {
+ min-height: 100vh;
+ background: #f8fafc;
+ padding-bottom: 32rpx;
+}
+
+.page-header {
+ background: #ffffff;
+ padding: 48rpx 32rpx 32rpx 32rpx;
+ border-bottom: 2rpx solid #f1f5f9;
+}
+
+.header-title {
+ font-size: 36rpx;
+ font-weight: bold;
+ color: #1e293b;
+ display: block;
+ margin-bottom: 8rpx;
+}
+
+.header-subtitle {
+ font-size: 26rpx;
+ color: #64748b;
+ display: block;
+}
+
+.empty-state {
+ padding: 120rpx 32rpx;
+ min-height: 600rpx;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+}
+
+.empty-container {
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ text-align: center;
+ gap: 24rpx;
+}
+
+.empty-icon {
+ font-size: 96rpx;
+ margin-bottom: 16rpx;
+}
+
+.empty-title {
+ font-size: 32rpx;
+ font-weight: 600;
+ color: #374151;
+}
+
+.empty-subtitle {
+ font-size: 26rpx;
+ color: #6b7280;
+ line-height: 1.5;
+ max-width: 400rpx;
+}
+
+.empty-button {
+ background: linear-gradient(135deg, #05c7c7 0%, #04b5b5 100%);
+ color: #ffffff;
+ padding: 24rpx 48rpx;
+ border-radius: 32rpx;
+ margin-top: 16rpx;
+ box-shadow: 0 8rpx 24rpx rgba(5, 199, 199, 0.2);
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+}
+
+.empty-button:active {
+ transform: scale(0.95);
+}
+
+.history-list {
+ padding: 16rpx;
+}
+
+.video-card {
+ background: #ffffff;
+ border-radius: 16rpx;
+ margin-bottom: 16rpx;
+ padding: 16rpx;
+ border: 2rpx solid #f1f5f9;
+ display: flex;
+ gap: 16rpx;
+ transition: all 0.3s ease;
+}
+
+.video-card:active {
+ background: #f8fafc;
+ transform: translateY(-1rpx);
+}
+
+.video-thumbnail {
+ position: relative;
+ width: 200rpx;
+ height: 120rpx;
+ flex-shrink: 0;
+}
+
+.thumbnail-placeholder {
+ width: 100%;
+ height: 100%;
+ border-radius: 12rpx;
+ overflow: hidden;
+ position: relative;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+}
+
+.ronin-bg {
+ background: linear-gradient(135deg, #3b82f6 0%, #dc2626 100%);
+}
+
+.panda-bg {
+ background: linear-gradient(135deg, #8b5cf6 0%, #06b6d4 100%);
+}
+
+.tennis-bg {
+ background: linear-gradient(135deg, #10b981 0%, #059669 100%);
+}
+
+.play-overlay {
+ position: absolute;
+ top: 50%;
+ left: 50%;
+ transform: translate(-50%, -50%);
+ width: 48rpx;
+ height: 48rpx;
+ background: rgba(0, 0, 0, 0.6);
+ border-radius: 50%;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+}
+
+.play-icon {
+ color: #ffffff;
+ font-size: 20rpx;
+ margin-left: 4rpx;
+}
+
+.video-duration {
+ position: absolute;
+ bottom: 8rpx;
+ right: 8rpx;
+ background: rgba(0, 0, 0, 0.8);
+ color: #ffffff;
+ padding: 4rpx 8rpx;
+ border-radius: 6rpx;
+ font-size: 18rpx;
+}
+
+
+
+.video-info {
+ flex: 1;
+ display: flex;
+ flex-direction: column;
+ justify-content: center;
+ gap: 8rpx;
+}
+
+.venue-name {
+ font-size: 28rpx;
+ font-weight: 600;
+ color: #1e293b;
+ line-height: 1.3;
+}
+
+.video-meta {
+ display: flex;
+ align-items: center;
+ gap: 16rpx;
+}
+
+.watch-time {
+ font-size: 22rpx;
+ color: #64748b;
+}
+
+.video-duration-text {
+ font-size: 22rpx;
+ color: #9ca3af;
+}
+
+.video-actions {
+ width: 48rpx;
+ height: 48rpx;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ border-radius: 50%;
+ transition: all 0.3s ease;
+}
+
+.video-actions:active {
+ background: #f3f4f6;
+}
+
+.more-icon {
+ font-size: 32rpx;
+ color: #9ca3af;
+ transform: rotate(90deg);
+}
+
+.clear-section {
+ padding: 48rpx 32rpx;
+ display: flex;
+ justify-content: center;
+}
+
+.clear-button {
+ background: #f8f9fa;
+ color: #dc3545;
+ padding: 20rpx 40rpx;
+ border-radius: 24rpx;
+ border: 2rpx solid #dc3545;
+ transition: all 0.3s ease;
+}
+
+.clear-button:active {
+ background: #dc3545;
+ color: #ffffff;
+ transform: scale(0.95);
+}
+
+.clear-text {
+ font-size: 26rpx;
+ font-weight: 500;
+}
\ No newline at end of file
diff --git a/client/src/pages/history/index.vue b/client/src/pages/history/index.vue
new file mode 100644
index 0000000..9265cb5
--- /dev/null
+++ b/client/src/pages/history/index.vue
@@ -0,0 +1,165 @@
+
+
+
+
+
+
+
+
+ 📺
+ 暂无观看记录
+ 去发现精彩的运动视频吧
+
+ 去发现
+
+
+
+
+
+
+
+
+
+
+
+ ▶
+
+
+ {{ record.videoDuration }}
+
+
+
+
+ {{ record.venueName }}
+
+ {{ record.watchTime }}
+ {{ record.videoDuration }}
+
+
+
+
+
+ ⋯
+
+
+
+
+
+
+
+ 清空观看历史
+
+
+
+
+
+
\ No newline at end of file
diff --git a/client/src/pages/index/index.scss b/client/src/pages/index/index.scss
index 803eeb0..a04f97f 100644
--- a/client/src/pages/index/index.scss
+++ b/client/src/pages/index/index.scss
@@ -1,3 +1,22 @@
+// 全局动画
+@keyframes pulse {
+ 0%, 100% {
+ opacity: 0.8;
+ }
+ 50% {
+ opacity: 0.4;
+ }
+}
+
+@keyframes spin {
+ 0% {
+ transform: rotate(0deg);
+ }
+ 100% {
+ transform: rotate(360deg);
+ }
+}
+
.limo-mobile {
min-height: 100vh;
background: #ffffff;
@@ -237,6 +256,12 @@
flex: 1;
color: #6B7280;
font-size: 24rpx;
+
+ &.location-loading {
+ color: #9CA3AF;
+ opacity: 0.8;
+ animation: pulse 1.5s infinite;
+ }
}
.location-switch {
@@ -247,6 +272,69 @@
}
}
+ // 位置状态提示页面
+ .location-status-section {
+ padding: 120rpx 32rpx;
+ min-height: 600rpx;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+
+ .status-container {
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ text-align: center;
+ gap: 32rpx;
+
+ .loading-spinner {
+ width: 80rpx;
+ height: 80rpx;
+ border: 6rpx solid #f3f3f3;
+ border-top: 6rpx solid #05C7C7;
+ border-radius: 50%;
+ animation: spin 1s linear infinite;
+ }
+
+ .status-icon {
+ font-size: 80rpx;
+ opacity: 0.5;
+ }
+
+ .status-title {
+ font-size: 32rpx;
+ font-weight: 600;
+ color: #374151;
+ }
+
+ .status-subtitle {
+ font-size: 24rpx;
+ color: #6B7280;
+ line-height: 1.5;
+ max-width: 400rpx;
+ }
+
+ .retry-button {
+ background: linear-gradient(135deg, #05C7C7 0%, #04B5B5 100%);
+ color: #ffffff;
+ padding: 24rpx 48rpx;
+ border-radius: 32rpx;
+ margin-top: 24rpx;
+ box-shadow: 0 8rpx 24rpx rgba(5, 199, 199, 0.2);
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+
+ &:active {
+ transform: scale(0.95);
+ }
+
+ .retry-text {
+ font-size: 28rpx;
+ font-weight: 600;
+ }
+ }
+ }
+ }
+
// Venue Cards with premium styling
.venue-section {
padding: 0 32rpx;
@@ -255,7 +343,7 @@
// Timeline
.timeline-container {
position: absolute;
- left: 80rpx;
+ left: 60rpx;
top: 0;
bottom: 0;
width: 2rpx;
@@ -265,7 +353,7 @@
top: 0;
bottom: 0;
width: 2rpx;
- background: linear-gradient(180deg, rgba(5, 199, 199, 0.3) 0%, #E5E7EB 30%, #E5E7EB 100%);
+ background: linear-gradient(180deg, rgba(5, 199, 199, 0.3) 0%, #E5E7EB 30%, #E5E7EB 80%, rgba(229, 231, 235, 0) 100%);
}
}
@@ -275,7 +363,7 @@
.timeline-dot {
position: absolute;
- left: 38rpx;
+ left: 18rpx;
top: 10rpx;
width: 24rpx;
height: 24rpx;
@@ -292,7 +380,7 @@
}
.venue-meta {
- margin-left: 96rpx;
+ margin-left: 76rpx;
margin-bottom: 24rpx;
display: flex;
align-items: center;
@@ -328,7 +416,7 @@
}
.venue-content {
- margin-left: 96rpx;
+ margin-left: 76rpx;
background: linear-gradient(135deg, #ffffff 0%, rgba(248, 250, 252, 0.5) 100%);
border-radius: 48rpx;
overflow: hidden;
@@ -962,7 +1050,7 @@
.stats-grid {
display: grid;
- grid-template-columns: repeat(3, 1fr);
+ grid-template-columns: repeat(2, 1fr);
gap: 24rpx;
.stat-card {
@@ -971,6 +1059,14 @@
padding: 24rpx;
text-align: center;
border: 2rpx solid #F3F4F6;
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+ cursor: pointer;
+
+ &:active {
+ background: #F9FAFB;
+ transform: scale(0.98);
+ border-color: #05C7C7;
+ }
.stat-number {
font-size: 48rpx;
@@ -1150,17 +1246,24 @@
}
}
- .activity-points {
- font-size: 20rpx;
- color: #05C7C7;
- font-weight: 600;
- background: #F0FDFD;
- padding: 6rpx 12rpx;
- border-radius: 12rpx;
- border: 1rpx solid #CCFBF1;
- white-space: nowrap;
- margin-top: 2rpx;
- }
+
+ }
+ }
+
+ .activity-more-link {
+ margin-top: 24rpx;
+ text-align: center;
+ padding: 16rpx;
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+
+ &:active {
+ transform: scale(0.98);
+ }
+
+ .more-link-text {
+ font-size: 26rpx;
+ color: #05C7C7;
+ font-weight: 500;
}
}
}
diff --git a/client/src/pages/index/index.vue b/client/src/pages/index/index.vue
index bc36d37..28199d1 100644
--- a/client/src/pages/index/index.vue
+++ b/client/src/pages/index/index.vue
@@ -57,13 +57,35 @@
📍
- 杭州市文一西路未来科技城万利大厦0701
- 切换
+ {{ currentLocation.address }}
+ {{ locationLoading ? '定位中' : (currentLocation.address.includes('请选择') ? '选择' : '切换') }}
-
-
+
+
+
+
+
+ 正在定位
+ 获取您的位置信息,为您推荐附近场馆
+
+
+
+
+
+
+ 📍
+ 选择您的位置
+ 在地图上选择位置,为您推荐附近的运动场馆
+
+ 在地图上选择
+
+
+
+
+
+
@@ -215,18 +237,14 @@
-
+
12
- 观看场次
+ 观看数量
-
+
5
收藏场馆
-
- 28
- 观看时长(h)
-
@@ -235,7 +253,7 @@
+
+
@@ -272,16 +297,17 @@
观看了 RONIN黄金篮球馆
2小时前 · 观看时长 45分钟
- +10
收藏了 Panda惊怒熊猫运动俱乐部
1天前
- +5
+
+ 查看历史活动
+
@@ -304,12 +330,23 @@
我的
+
+
+
diff --git a/client/src/pages/notifications/index.config.ts b/client/src/pages/notifications/index.config.ts
new file mode 100644
index 0000000..e782c15
--- /dev/null
+++ b/client/src/pages/notifications/index.config.ts
@@ -0,0 +1,6 @@
+export default definePageConfig({
+ navigationBarTitleText: '消息通知',
+ navigationBarBackgroundColor: '#ffffff',
+ navigationBarTextStyle: 'black',
+ navigationStyle: 'default'
+})
\ No newline at end of file
diff --git a/client/src/pages/notifications/index.scss b/client/src/pages/notifications/index.scss
new file mode 100644
index 0000000..d76ad92
--- /dev/null
+++ b/client/src/pages/notifications/index.scss
@@ -0,0 +1,158 @@
+.notifications-page {
+ min-height: 100vh;
+ background: #f8fafc;
+ padding-bottom: 32rpx;
+}
+
+.page-header {
+ background: #ffffff;
+ padding: 48rpx 32rpx 32rpx 32rpx;
+ border-bottom: 2rpx solid #f1f5f9;
+}
+
+.header-title {
+ font-size: 36rpx;
+ font-weight: bold;
+ color: #1e293b;
+ display: block;
+ margin-bottom: 8rpx;
+}
+
+.header-subtitle {
+ font-size: 26rpx;
+ color: #64748b;
+ display: block;
+}
+
+.actions-bar {
+ background: #ffffff;
+ padding: 16rpx 32rpx;
+ border-bottom: 2rpx solid #f1f5f9;
+ display: flex;
+ justify-content: flex-end;
+ gap: 24rpx;
+}
+
+.action-btn {
+ background: #f8fafc;
+ color: #64748b;
+ padding: 12rpx 24rpx;
+ border-radius: 16rpx;
+ border: 2rpx solid #e2e8f0;
+ transition: all 0.3s ease;
+}
+
+.action-btn:active {
+ background: #e2e8f0;
+ transform: scale(0.95);
+}
+
+.action-text {
+ font-size: 24rpx;
+ font-weight: 500;
+}
+
+.empty-state {
+ padding: 120rpx 32rpx;
+ min-height: 600rpx;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+}
+
+.empty-container {
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ text-align: center;
+ gap: 24rpx;
+}
+
+.empty-icon {
+ font-size: 96rpx;
+ margin-bottom: 16rpx;
+ opacity: 0.6;
+}
+
+.empty-title {
+ font-size: 32rpx;
+ font-weight: 600;
+ color: #374151;
+}
+
+.empty-subtitle {
+ font-size: 26rpx;
+ color: #6b7280;
+ line-height: 1.5;
+ max-width: 400rpx;
+}
+
+.notifications-list {
+ padding: 16rpx;
+}
+
+.notification-card {
+ background: #ffffff;
+ border-radius: 16rpx;
+ margin-bottom: 16rpx;
+ padding: 24rpx;
+ border: 2rpx solid #f1f5f9;
+ position: relative;
+ transition: all 0.3s ease;
+}
+
+.notification-card:active {
+ background: #f8fafc;
+ transform: translateY(-1rpx);
+}
+
+.notification-card.unread {
+ border-color: #e0f2fe;
+ background: #fefeff;
+}
+
+.notification-content {
+ width: 100%;
+}
+
+.notification-header {
+ display: flex;
+ align-items: flex-start;
+ justify-content: space-between;
+ margin-bottom: 8rpx;
+ gap: 16rpx;
+}
+
+.notification-title {
+ font-size: 28rpx;
+ font-weight: 600;
+ color: #1e293b;
+ line-height: 1.3;
+}
+
+.notification-time {
+ font-size: 20rpx;
+ color: #9ca3af;
+ white-space: nowrap;
+ margin-top: 2rpx;
+}
+
+.notification-message {
+ font-size: 24rpx;
+ color: #64748b;
+ line-height: 1.5;
+ overflow: hidden;
+ display: -webkit-box;
+ -webkit-line-clamp: 2;
+ -webkit-box-orient: vertical;
+}
+
+.unread-dot {
+ position: absolute;
+ top: 24rpx;
+ right: 24rpx;
+ width: 16rpx;
+ height: 16rpx;
+ background: #ef4444;
+ border-radius: 50%;
+}
\ No newline at end of file
diff --git a/client/src/pages/notifications/index.vue b/client/src/pages/notifications/index.vue
new file mode 100644
index 0000000..aeea841
--- /dev/null
+++ b/client/src/pages/notifications/index.vue
@@ -0,0 +1,180 @@
+
+
+
+
+
+
+
+
+ 全部已读
+
+
+ 清空通知
+
+
+
+
+
+
+ 🔔
+ 暂无消息通知
+ 有新消息时会在这里显示
+
+
+
+
+
+
+
+
+
+ {{ notification.message }}
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/client/src/pages/orders/index.config.ts b/client/src/pages/orders/index.config.ts
new file mode 100644
index 0000000..39e845d
--- /dev/null
+++ b/client/src/pages/orders/index.config.ts
@@ -0,0 +1,6 @@
+export default definePageConfig({
+ navigationBarTitleText: '我的订单',
+ navigationBarBackgroundColor: '#ffffff',
+ navigationBarTextStyle: 'black',
+ navigationStyle: 'default'
+})
\ No newline at end of file
diff --git a/client/src/pages/orders/index.scss b/client/src/pages/orders/index.scss
new file mode 100644
index 0000000..83e9580
--- /dev/null
+++ b/client/src/pages/orders/index.scss
@@ -0,0 +1,323 @@
+.orders-page {
+ min-height: 100vh;
+ background: #f9fafb;
+
+ // Status Tabs
+ .status-tabs {
+ background: #ffffff;
+ padding: 24rpx 24rpx 0 24rpx;
+ display: flex;
+ border-bottom: 2rpx solid #f3f4f6;
+ position: sticky;
+ top: 0;
+ z-index: 10;
+
+ .tab-item {
+ flex: 1;
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ padding: 24rpx 16rpx;
+ position: relative;
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+
+ &:active {
+ transform: scale(0.98);
+ }
+
+ .tab-text {
+ font-size: 28rpx;
+ color: #6b7280;
+ font-weight: 500;
+ transition: color 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+ }
+
+ .tab-badge {
+ position: absolute;
+ top: 12rpx;
+ right: 12rpx;
+ background: #ef4444;
+ border-radius: 20rpx;
+ min-width: 32rpx;
+ height: 32rpx;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ padding: 0 8rpx;
+
+ .badge-text {
+ color: #ffffff;
+ font-size: 20rpx;
+ font-weight: 600;
+ }
+ }
+
+ &.active {
+ .tab-text {
+ color: #05c7c7;
+ font-weight: 600;
+ }
+
+ &::after {
+ content: '';
+ position: absolute;
+ bottom: 0;
+ left: 50%;
+ transform: translateX(-50%);
+ width: 64rpx;
+ height: 6rpx;
+ background: linear-gradient(135deg, #05c7c7 0%, #04b5b5 100%);
+ border-radius: 6rpx;
+ }
+ }
+ }
+ }
+
+ // Empty State
+ .empty-state {
+ padding: 120rpx 48rpx;
+ display: flex;
+ justify-content: center;
+
+ .empty-container {
+ display: flex;
+ flex-direction: column;
+ align-items: center;
+ text-align: center;
+
+ .empty-icon {
+ font-size: 120rpx;
+ margin-bottom: 32rpx;
+ opacity: 0.6;
+ }
+
+ .empty-title {
+ font-size: 32rpx;
+ font-weight: 600;
+ color: #374151;
+ margin-bottom: 16rpx;
+ }
+
+ .empty-subtitle {
+ font-size: 26rpx;
+ color: #9ca3af;
+ margin-bottom: 48rpx;
+ line-height: 1.5;
+ }
+
+ .empty-button {
+ background: linear-gradient(135deg, #05c7c7 0%, #04b5b5 100%);
+ color: #ffffff;
+ padding: 20rpx 40rpx;
+ border-radius: 28rpx;
+ box-shadow: 0 8rpx 24rpx rgba(5, 199, 199, 0.3);
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+
+ &:active {
+ transform: scale(0.98);
+ }
+
+ .button-text {
+ font-size: 26rpx;
+ font-weight: 600;
+ }
+ }
+ }
+ }
+
+ // Orders List
+ .orders-list {
+ padding: 24rpx;
+
+ .order-card {
+ background: #ffffff;
+ border-radius: 24rpx;
+ border: 2rpx solid #f3f4f6;
+ margin-bottom: 24rpx;
+ overflow: hidden;
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+
+ &:active {
+ transform: scale(0.995);
+ box-shadow: 0 8rpx 32rpx rgba(0, 0, 0, 0.08);
+ }
+
+ &:last-child {
+ margin-bottom: 0;
+ }
+
+ .order-header {
+ display: flex;
+ justify-content: space-between;
+ align-items: flex-start;
+ padding: 32rpx 32rpx 24rpx 32rpx;
+ border-bottom: 2rpx solid #f9fafb;
+
+ .order-info {
+ display: flex;
+ flex-direction: column;
+
+ .order-number {
+ font-size: 26rpx;
+ color: #6b7280;
+ margin-bottom: 8rpx;
+ }
+
+ .order-date {
+ font-size: 24rpx;
+ color: #9ca3af;
+ }
+ }
+
+ .order-status {
+ .status-text {
+ font-size: 24rpx;
+ font-weight: 600;
+ }
+
+ &.pending {
+ .status-text {
+ color: #d97706;
+ }
+ }
+
+ &.completed {
+ .status-text {
+ color: #047857;
+ }
+ }
+
+ &.cancelled {
+ .status-text {
+ color: #dc2626;
+ }
+ }
+ }
+ }
+
+ .order-content {
+ padding: 24rpx 32rpx 32rpx 32rpx;
+
+ .member-info {
+ display: flex;
+ justify-content: space-between;
+ align-items: center;
+ margin-bottom: 32rpx;
+
+ .member-card {
+ display: flex;
+ align-items: center;
+ flex: 1;
+
+ .card-icon {
+ width: 80rpx;
+ height: 80rpx;
+ background: linear-gradient(135deg, #fbbf24 0%, #f59e0b 100%);
+ border-radius: 20rpx;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ margin-right: 24rpx;
+
+ .icon-text {
+ font-size: 36rpx;
+ }
+ }
+
+ .member-details {
+ display: flex;
+ flex-direction: column;
+
+ .member-type {
+ font-size: 28rpx;
+ font-weight: 600;
+ color: #111827;
+ margin-bottom: 6rpx;
+ }
+
+ .member-duration {
+ font-size: 24rpx;
+ color: #6b7280;
+ }
+ }
+ }
+
+ .order-amount {
+ display: flex;
+ flex-direction: column;
+ align-items: flex-end;
+
+ .amount-label {
+ font-size: 22rpx;
+ color: #9ca3af;
+ margin-bottom: 6rpx;
+ }
+
+ .amount-value {
+ font-size: 32rpx;
+ font-weight: 700;
+ color: #ef4444;
+ }
+ }
+ }
+
+ .order-actions {
+ display: flex;
+ gap: 16rpx;
+ justify-content: flex-end;
+
+ .action-btn {
+ padding: 16rpx 24rpx;
+ border-radius: 20rpx;
+ border: 2rpx solid;
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+
+ &:active {
+ transform: scale(0.95);
+ }
+
+ .btn-text {
+ font-size: 24rpx;
+ font-weight: 600;
+ }
+
+ &.cancel-btn {
+ background: #ffffff;
+ border-color: #d1d5db;
+
+ .btn-text {
+ color: #6b7280;
+ }
+
+ &:active {
+ background: #f9fafb;
+ }
+ }
+
+ &.pay-btn {
+ background: linear-gradient(135deg, #05c7c7 0%, #04b5b5 100%);
+ border-color: #05c7c7;
+ box-shadow: 0 4rpx 16rpx rgba(5, 199, 199, 0.3);
+
+ .btn-text {
+ color: #ffffff;
+ }
+ }
+
+
+
+ &.reorder-btn {
+ background: linear-gradient(135deg, #10b981 0%, #059669 100%);
+ border-color: #10b981;
+ box-shadow: 0 4rpx 16rpx rgba(16, 185, 129, 0.3);
+
+ .btn-text {
+ color: #ffffff;
+ }
+ }
+ }
+ }
+ }
+ }
+ }
+}
\ No newline at end of file
diff --git a/client/src/pages/orders/index.vue b/client/src/pages/orders/index.vue
new file mode 100644
index 0000000..6464916
--- /dev/null
+++ b/client/src/pages/orders/index.vue
@@ -0,0 +1,310 @@
+
+
+
+
+
+ {{ tab.label }}
+
+ {{ tab.count }}
+
+
+
+
+
+
+
+ 📋
+ 暂无相关订单
+ {{ getEmptyMessage() }}
+
+ 立即开通会员
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ 👑
+
+
+ {{ order.memberType }}
+ {{ order.duration }}
+
+
+
+ 实付金额
+ ¥{{ order.amount }}
+
+
+
+
+
+
+ 取消订单
+
+
+ 立即支付
+
+
+
+ 重新购买
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/client/src/pages/vip/index.vue b/client/src/pages/vip/index.vue
index f33b3a1..03b7332 100644
--- a/client/src/pages/vip/index.vue
+++ b/client/src/pages/vip/index.vue
@@ -13,42 +13,12 @@
-
-
-
-
-
👑
LIMO VIP会员
- 开启专属运动体验
-
-
-
-
-
- 👥
-
- 50万+
- 活跃用户
-
-
-
- ⭐
-
- 98%
- 满意度
-
-
-
- 🏆
-
- 1000+
- 场馆覆盖
-
-
+ 解锁专属运动特权
@@ -128,46 +98,7 @@
-
-
-
- 用户好评
-
-
-
- "VIP服务真的很棒,预约场馆再也不用排队了!"
-
-
-
- "专属客服响应很快,解决问题很及时,值得推荐!"
-
-
-
-
+
@@ -185,20 +116,6 @@
立即开通VIP会员
-
-
- 🛡️
- 安全支付
-
-
-
- ✓
- 随时取消
-
-
- 7天无理由退款
-
-
开通即表示同意《VIP会员服务协议》
@@ -217,20 +134,10 @@ import './index.scss'
const backIcon = require('@/assets/images/back.svg')
// 响应式状态
-const selectedPlan = ref('monthly')
+const selectedPlan = ref('quarterly')
// 套餐数据
const plans = ref([
- {
- id: 'daily',
- name: '体验版',
- duration: '1天',
- price: 9.9,
- originalPrice: 19.9,
- discount: '限时5折',
- popular: false,
- colorClass: 'blue-gradient',
- },
{
id: 'monthly',
name: '月度会员',
@@ -238,7 +145,7 @@ const plans = ref([
price: 68,
originalPrice: 98,
discount: '7折优惠',
- popular: true,
+ popular: false,
colorClass: 'purple-gradient',
},
{
@@ -247,9 +154,9 @@ const plans = ref([
duration: '3个月',
price: 168,
originalPrice: 294,
- discount: '超值4.3折',
- popular: false,
- colorClass: 'pink-gradient',
+ discount: '超值优惠',
+ popular: true,
+ colorClass: 'orange-gradient',
},
{
id: 'yearly',
@@ -257,50 +164,32 @@ const plans = ref([
duration: '1年',
price: 588,
originalPrice: 1176,
- discount: '超值5折',
+ discount: '最划算',
popular: false,
- colorClass: 'orange-gradient',
+ colorClass: 'pink-gradient',
},
])
// 特权数据
const privileges = ref([
- {
- icon: '👑',
- title: '专属身份标识',
- desc: 'VIP专属标识,彰显尊贵身份',
- colorClass: 'yellow-gradient',
- },
{
icon: '⚡',
title: '优先预约权',
desc: '热门场馆优先预约,不再排队等待',
- colorClass: 'blue-gradient',
+ colorClass: 'orange-gradient',
},
{
icon: '🎁',
title: '专属折扣',
desc: '场馆预订享受VIP专属折扣优惠',
- colorClass: 'green-gradient',
+ colorClass: 'purple-gradient',
},
{
icon: '🛡️',
title: '免费取消',
desc: '预约后可免费取消,无违约金',
- colorClass: 'purple-gradient',
- },
- {
- icon: '⭐',
- title: '专属客服',
- desc: '7x24小时VIP专属客服服务',
colorClass: 'pink-gradient',
},
- {
- icon: '✓',
- title: '高清回放',
- desc: '无限制观看高清比赛回放视频',
- colorClass: 'indigo-gradient',
- },
])
// 计算属性:选中的套餐信息
diff --git a/client/src/pages/zone/index.scss b/client/src/pages/zone/index.scss
index ffa1704..4cdb5c1 100644
--- a/client/src/pages/zone/index.scss
+++ b/client/src/pages/zone/index.scss
@@ -15,7 +15,11 @@
left: 0;
right: 0;
bottom: 0;
- background: linear-gradient(135deg, #1f2937 0%, #3b82f6 50%, #ef4444 100%);
+ background-size: cover;
+ background-position: center;
+ background-repeat: no-repeat;
+ filter: blur(2rpx);
+ transform: scale(1.1);
z-index: 1;
}
@@ -25,7 +29,7 @@
left: 0;
right: 0;
bottom: 0;
- background: rgba(0, 0, 0, 0.4);
+ background: rgba(0, 0, 0, 0.6);
z-index: 2;
}
@@ -35,7 +39,7 @@
left: 0;
right: 0;
bottom: 0;
- background: linear-gradient(180deg, rgba(0, 0, 0, 0.2) 0%, transparent 40%, rgba(0, 0, 0, 0.6) 100%);
+ background: linear-gradient(180deg, rgba(0, 0, 0, 0.3) 0%, transparent 30%, rgba(0, 0, 0, 0.8) 100%);
z-index: 3;
}
@@ -51,7 +55,7 @@
.control-btn {
width: 64rpx;
height: 64rpx;
- background: rgba(0, 0, 0, 0.3);
+ background: rgba(255, 255, 255, 0.15);
border-radius: 24rpx;
display: flex;
align-items: center;
@@ -174,6 +178,9 @@
padding: 12rpx 24rpx;
box-shadow: 0 8rpx 24rpx rgba(5, 199, 199, 0.3);
transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
+ display: flex;
+ align-items: center;
+ justify-content: center;
&:active {
transform: scale(0.95);
@@ -183,6 +190,7 @@
font-size: 24rpx;
color: #ffffff;
font-weight: 600;
+ line-height: 1;
}
}
diff --git a/client/src/pages/zone/index.vue b/client/src/pages/zone/index.vue
index 1bac619..4e3fce2 100644
--- a/client/src/pages/zone/index.vue
+++ b/client/src/pages/zone/index.vue
@@ -2,7 +2,7 @@