2025-10-27 23:13:08 +08:00

1139 lines
25 KiB
Vue
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<template>
<view class="profile-page">
<!-- 移动设备顶部状态栏 -->
<view class="top_bar flex w-full" v-if="isMobile">
<view class="chat-header">
<view class="header-left">
<i class="fas fa-bell header-icon" @click="handleNotification"></i>
</view>
<view class="header-title">我的</view>
<view class="header-right">
<i class="fas fa-search header-icon" @click="handleSearch"></i>
</view>
</view>
</view>
<!-- 浏览器环境顶部导航栏 -->
<view class="unified-header" v-else>
<view class="header-content">
<view class="header-left">
<i class="fas fa-bell header-icon" @click="handleNotification"></i>
</view>
<view class="header-title">我的</view>
<view class="header-right">
<i class="fas fa-search header-icon" @click="handleSearch"></i>
</view>
</view>
</view>
<!-- 页面内容 -->
<scroll-view scroll-y class="unified-content">
<!-- 个人信息卡片 -->
<view class="profile-card">
<!-- 已登录状态 -->
<view v-if="isLogin" class="profile-content">
<view class="profile-header" @click="editProfile">
<view class="profile-avatar">
<view class="avatar">
<text class="avatar-text">{{(userInfo.nickname || '未').charAt(0)}}</text>
</view>
<view class="edit-icon">
<i class="fas fa-camera"></i>
</view>
</view>
<view class="profile-info">
<text class="profile-name">{{userInfo.nickname || '未登录'}}</text>
<text class="profile-dept">{{userInfo.dept?.name || '未知部门'}}</text>
<text class="profile-id">工号{{userInfo.employeeId || 'N/A'}}</text>
</view>
<view class="profile-arrow">
<i class="fas fa-chevron-right"></i>
</view>
</view>
<!-- {
"id": 1,
"username": "admin",
"nickname": "江苏美天智能科技",
"email": "admin@126.com",
"mobile": "18888888888",
"sex": 1,
"avatar": "http://demo1.meteteme.top/admin-api/infra/file/4/get/5d6c4478d03b3f0971269e3f13ce8984221623f089248d1fb6069dbfcd8baf5e.png",
"loginIp": "218.92.65.85",
"loginDate": 1760610192000,
"createTime": 1609837427000,
"roles": [
{
"id": 1,
"name": "超级管理员"
},
{
"id": 2,
"name": "普通角色"
},
{
"id": 3,
"name": "CRM 管理员"
}
],
"dept": {
"id": 100,
"name": "江苏美天智能科技有限公司",
"parentId": 0
},
"posts": [
{
"id": 1,
"name": "董事长"
},
{
"id": 5,
"name": "部门主管"
}
],
"socialUsers": []
} -->
<!-- 数据统计 -->
<view class="stats-grid">
<view class="stat-item" @click="goToAttendance">
<view class="stat-content">
<text class="stat-number">{{ userInfo.attendanceRate ?? 0 }}%</text>
<text class="stat-label">考勤率</text>
</view>
</view>
<view class="stat-item" @click="goToTasks">
<view class="stat-content">
<text class="stat-number">{{ userInfo.completedTasks ?? 0 }}</text>
<text class="stat-label">待完成</text>
</view>
</view>
<view class="stat-item" @click="goToReimbursement">
<view class="stat-content">
<text class="stat-number">¥{{ (userInfo.pendingAmount !== undefined && userInfo.pendingAmount !== null) ? userInfo.pendingAmount.toFixed(2) : '0.00' }}</text>
<text class="stat-label">待报销</text>
</view>
</view>
</view>
</view>
<!-- 未登录状态 -->
<view v-else class="login-prompt">
<view class="login-icon">
<i class="fas fa-user-circle"></i>
</view>
<view class="login-content">
<text class="login-title">请先登录</text>
<text class="login-desc">登录后查看个人信息和工作数据</text>
</view>
<view class="login-btn" @click="goToLogin">
<text class="login-btn-text">立即登录</text>
<i class="fas fa-arrow-right"></i>
</view>
</view>
</view>
<!-- 功能设置卡片 -->
<view class="functions-card">
<view class="card-header">
<text class="card-title">功能设置</text>
</view>
<view class="module-grid">
<view class="module-item" @click="toggleMessageSwitch">
<view class="module-icon" :style="getMessageIconStyle()">
<i :class="getMessageIcon()"></i>
</view>
<text class="module-name">消息提醒</text>
</view>
<view class="module-item" @click="themeSettings">
<view class="module-icon" :style="getThemeIconStyle()">
<i :class="getThemeIcon()"></i>
</view>
<text class="module-name">主题切换</text>
</view>
<view class="module-item" @click="changePassword">
<view class="module-icon" style="background: linear-gradient(135deg, #FF6B6B 0%, #e17055 100%)">
<i class="fas fa-lock"></i>
</view>
<text class="module-name">修改密码</text>
</view>
<view class="module-item" @click="bindPhone">
<view class="module-icon" style="background: linear-gradient(135deg, #4ECDC4 0%, #26c6da 100%)">
<i class="fas fa-mobile-alt"></i>
</view>
<text class="module-name">绑定手机</text>
</view>
<view class="module-item" @click="showCacheInfo">
<view class="module-icon" style="background: linear-gradient(135deg, #FECA57 0%, #f9d423 100%)">
<i class="fas fa-trash-alt"></i>
</view>
<text class="module-name">清除缓存</text>
</view>
<view class="module-item" @click="showVersionInfo">
<view class="module-icon" style="background: linear-gradient(135deg, #FF6B6B 0%, #e17055 100%)">
<i class="fas fa-sync-alt"></i>
</view>
<text class="module-name">版本更新</text>
</view>
<view class="module-item none"></view>
<view class="module-item none"></view>
<view class="module-item none"></view>
<view class="module-item none"></view>
</view>
</view>
<!-- 帮助与反馈卡片 -->
<view class="help-card">
<view class="card-header">
<text class="card-title">帮助与反馈</text>
</view>
<view class="module-grid">
<view class="module-item" @click="showFAQ">
<view class="module-icon" style="background: linear-gradient(135deg, #4ECDC4 0%, #26c6da 100%)">
<i class="fas fa-question-circle"></i>
</view>
<text class="module-name">常见问题</text>
</view>
<view class="module-item" @click="feedback">
<view class="module-icon" style="background: linear-gradient(135deg, #45B7D1 0%, #168aad 100%)">
<i class="fas fa-comment-dots"></i>
</view>
<text class="module-name">意见反馈</text>
</view>
<view class="module-item" @click="contactService">
<view class="module-icon" style="background: linear-gradient(135deg, #96CEB4 0%, #3ad29f 100%)">
<i class="fas fa-headset"></i>
</view>
<text class="module-name">客服联系</text>
</view>
<view class="module-item none"></view>
<view class="module-item none"></view>
</view>
</view>
<!-- 账号管理卡片 -->
<view class="account-card">
<view class="card-header">
<text class="card-title">账号管理</text>
</view>
<view class="module-grid">
<view class="module-item" @click="handleLogout">
<view class="module-icon" style="background: linear-gradient(135deg, #95a5a6 0%, #7f8c8d 100%)">
<i class="fas fa-sign-out-alt"></i>
</view>
<text class="module-name">退出登录</text>
</view>
<view class="module-item" @click="accountLogout">
<view class="module-icon" style="background: linear-gradient(135deg, #e74c3c 0%, #c0392b 100%)">
<i class="fas fa-user-slash"></i>
</view>
<text class="module-name">账号注销</text>
</view>
<view class="module-item none"></view>
<view class="module-item none"></view>
<view class="module-item none"></view>
</view>
</view>
</scroll-view>
</view>
</template>
<script>
import { ref, reactive, computed, onMounted } from 'vue'
import { useAuthStore } from '../../src/store/authStore.js'
import { redirectAfterLogout } from '../../src/utils/routeGuard.js'
export default {
setup() {
const authStore = useAuthStore()
// 响应式数据
const unreadCount = ref(2)
const messageEnabled = ref(true)
const currentTheme = ref('浅色模式')
const cacheSize = ref('12.5MB')
const appVersion = ref('v1.0.0')
// 用户信息 - 从 Pinia store 获取
const userInfo = computed(() => {
return authStore.userInfo || {
nickname: '未登录',
name: '未登录',
department: '未知部门',
dept: { name: '未知部门' },
employeeId: 'N/A',
avatar: 'static\\imgs\\default_avatar.png',
attendanceRate: 0,
completedTasks: 0,
pendingAmount: '0'
}
})
// 登录状态
const isLogin = computed(() => {
return authStore.isAuthenticated
})
// 设备检测
const isMobile = computed(() => {
return getApp().globalData.isMobile
})
// 方法
const handleSearch = () => {
uni.showToast({
title: '搜索功能',
icon: 'none'
})
}
const handleNotification = () => {
uni.switchTab({
url: '/pages/message/message'
})
}
const editProfile = () => {
// 跳转到编辑个人资料页面
uni.navigateTo({
url: '/pages/profile/editprofile'
})
}
const goToAttendance = () => {
uni.showToast({
title: '查看考勤详情',
icon: 'none'
})
}
const goToTasks = () => {
uni.showToast({
title: '查看任务详情',
icon: 'none'
})
}
const goToReimbursement = () => {
uni.showToast({
title: '查看报销详情',
icon: 'none'
})
}
const changePassword = () => {
uni.showToast({
title: '修改密码',
icon: 'none'
})
}
const bindPhone = () => {
uni.showToast({
title: '绑定手机',
icon: 'none'
})
}
const accountLogout = () => {
uni.showModal({
title: '确认注销',
content: '注销后账号将无法恢复,确定要注销吗?',
success: (res) => {
if (res.confirm) {
uni.showToast({
title: '账号注销成功',
icon: 'none'
})
}
}
})
}
// 登出功能
const handleLogout = () => {
uni.showModal({
title: '确认登出',
content: '确定要退出登录吗?',
success: (res) => {
if (res.confirm) {
// 使用 Pinia store 登出
authStore.logout()
uni.showToast({
title: '已退出登录',
icon: 'success'
})
// 跳转到登录页面
setTimeout(() => {
redirectAfterLogout()
}, 500)
}
}
})
}
// 跳转到登录页面
const goToLogin = () => {
uni.navigateTo({
url: '/pages/login/index'
})
}
const messageSettings = () => {
uni.showToast({
title: '消息设置',
icon: 'none'
})
}
const toggleMessage = (value) => {
uni.showToast({
title: value ? '消息提醒已开启' : '消息提醒已关闭',
icon: 'none'
})
}
const themeSettings = () => {
uni.showActionSheet({
itemList: ['浅色模式', '深色模式', '跟随系统'],
success: (res) => {
const themes = ['浅色模式', '深色模式', '跟随系统']
currentTheme.value = themes[res.tapIndex]
uni.showToast({
title: `已切换到${themes[res.tapIndex]}`,
icon: 'none'
})
}
})
}
const clearCache = () => {
uni.showModal({
title: '清除缓存',
content: '确定要清除应用缓存吗?',
success: (res) => {
if (res.confirm) {
cacheSize.value = '0MB'
uni.showToast({
title: '缓存清除成功',
icon: 'none'
})
}
}
})
}
const checkUpdate = () => {
uni.showToast({
title: '检查更新中...',
icon: 'none'
})
setTimeout(() => {
uni.showToast({
title: '已是最新版本',
icon: 'none'
})
}, 2000)
}
const showFAQ = () => {
uni.showToast({
title: '常见问题',
icon: 'none'
})
}
const feedback = () => {
uni.showToast({
title: '意见反馈',
icon: 'none'
})
}
const contactService = () => {
uni.showToast({
title: '客服联系',
icon: 'none'
})
}
const toggleSwitch = () => {
messageEnabled.value = !messageEnabled.value
toggleMessage(messageEnabled.value)
}
// 获取主题图标
const getThemeIcon = () => {
const themeIcons = {
'浅色模式': 'fas fa-sun',
'深色模式': 'fas fa-moon',
'跟随系统': 'fas fa-desktop'
}
return themeIcons[currentTheme.value] || 'fas fa-palette'
}
// 获取主题图标背景样式
const getThemeIconStyle = () => {
const themeStyles = {
'浅色模式': 'background: linear-gradient(135deg, #FFD700 0%, #FFA500 100%)', // 金黄色渐变
'深色模式': 'background: linear-gradient(135deg, #4A4A4A 0%, #2C2C2C 100%)', // 深灰色渐变
'跟随系统': 'background: linear-gradient(135deg, #96CEB4 0%, #3ad29f 100%)' // 绿色渐变
}
return themeStyles[currentTheme.value] || 'background: linear-gradient(135deg, #96CEB4 0%, #3ad29f 100%)'
}
// 获取消息提醒图标
const getMessageIcon = () => {
return messageEnabled.value ? 'fas fa-bell' : 'fas fa-bell-slash'
}
// 获取消息提醒图标背景样式
const getMessageIconStyle = () => {
return messageEnabled.value
? 'background: linear-gradient(135deg, #45B7D1 0%, #168aad 100%)' // 开启状态:蓝色渐变
: 'background: linear-gradient(135deg, #95a5a6 0%, #7f8c8d 100%)' // 关闭状态:灰色渐变
}
// 切换消息提醒状态
const toggleMessageSwitch = () => {
messageEnabled.value = !messageEnabled.value
toggleMessage(messageEnabled.value)
}
// 显示缓存信息弹窗
const showCacheInfo = () => {
uni.showModal({
title: '缓存信息',
content: `当前缓存大小:${cacheSize.value}\n\n点击确定清除缓存`,
confirmText: '清除缓存',
cancelText: '取消',
success: (res) => {
if (res.confirm) {
clearCache()
}
}
})
}
// 显示版本信息弹窗
const showVersionInfo = () => {
uni.showModal({
title: '版本信息',
content: `当前版本:${appVersion.value}\n\n点击确定检查更新`,
confirmText: '检查更新',
cancelText: '取消',
success: (res) => {
if (res.confirm) {
checkUpdate()
}
}
})
}
return {
unreadCount,
messageEnabled,
currentTheme,
cacheSize,
appVersion,
userInfo,
isLogin,
isMobile,
handleSearch,
handleNotification,
editProfile,
goToAttendance,
goToTasks,
goToReimbursement,
changePassword,
bindPhone,
accountLogout,
handleLogout,
goToLogin,
messageSettings,
toggleMessage,
themeSettings,
clearCache,
checkUpdate,
showFAQ,
feedback,
contactService,
toggleSwitch,
getThemeIcon,
getThemeIconStyle,
getMessageIcon,
getMessageIconStyle,
toggleMessageSwitch,
showCacheInfo,
showVersionInfo
}
}
}
</script>
<style lang="scss" scoped>
.profile-page {
min-height: 100vh;
width: 100%;
background-color: var(--background);
box-sizing: border-box;
}
/* 浏览器环境下的顶部间距 */
.unified-header + .unified-content {
margin-top: calc(var(--status-bar-height) + 88rpx);
padding-top: 30rpx;
}
/* 支持安全区域的设备 - 移动设备不需要额外的 padding-top因为使用了 top_bar */
/* 移动设备顶部状态栏 */
.top_bar {
background: var(--gradient-primary);
box-shadow: var(--shadow-lg);
z-index: 9999;
position: fixed;
top: 0;
left: 0;
right: 0;
height: calc(var(--status-bar-height) + 88rpx);
display: flex;
align-items: flex-end;
padding-top: var(--status-bar-height);
box-sizing: border-box;
}
/* 支持安全区域的设备 */
@supports (padding: max(0px)) {
.top_bar {
height: calc(var(--status-bar-height) + 88rpx + env(safe-area-inset-top));
padding-top: calc(var(--status-bar-height) + env(safe-area-inset-top));
}
.top_bar + .unified-content {
margin-top: calc(var(--status-bar-height) + 88rpx + env(safe-area-inset-top));
padding-top: 30rpx;
}
}
/* 移动设备下的导航栏样式 */
.top_bar .chat-header {
background: transparent;
border-bottom: none;
box-shadow: none;
width: 100%;
height: 88rpx;
padding: 0 20rpx;
box-sizing: border-box;
display: flex;
justify-content: space-between;
align-items: center;
}
.top_bar .header-title {
color: var(--white);
font-weight: 600;
font-size: 36rpx;
}
.top_bar .header-left i,
.top_bar .header-right i {
color: var(--white);
font-size: 32rpx;
}
.top_bar .header-icon {
font-size: 32rpx;
color: var(--white);
}
.header-left,
.header-right {
width: 80rpx;
height: 88rpx;
display: flex;
align-items: center;
justify-content: center;
transition: background-color 0.2s ease;
}
.top_bar .header-left:active,
.top_bar .header-right:active {
background-color: rgba(255, 255, 255, 0.2);
border-radius: 8rpx;
}
/* 移动设备下为内容添加顶部间距 */
.top_bar + .unified-content {
margin-top: calc(var(--status-bar-height) + 88rpx);
padding-top: 30rpx;
}
/* 浏览器环境顶部导航栏 */
.unified-header {
background: var(--gradient-primary);
box-shadow: var(--shadow-lg);
position: fixed;
top: 0;
left: 0;
right: 0;
z-index: 9999;
height: calc(var(--status-bar-height) + 88rpx);
}
.unified-header .header-content {
padding: 20rpx 30rpx;
padding-top: calc(var(--status-bar-height) + 20rpx);
display: flex;
align-items: center;
justify-content: space-between;
height: 100%;
box-sizing: border-box;
}
.unified-header .header-title {
flex: 1;
text-align: center;
color: var(--white);
font-size: 32rpx;
font-weight: 600;
margin: 0 20rpx;
}
.unified-header .header-left,
.unified-header .header-right {
display: flex;
align-items: center;
min-width: 80rpx;
}
.unified-header .header-right {
justify-content: flex-end;
}
.unified-header .header-icon {
color: var(--white);
font-size: 36rpx;
padding: 10rpx;
transition: all 0.3s ease;
}
.unified-header .header-icon:active {
background: rgba(255, 255, 255, 0.2);
transform: scale(0.95);
}
/* 支持安全区域的设备 */
@supports (padding: max(0px)) {
.unified-header {
height: calc(var(--status-bar-height) + 88rpx + env(safe-area-inset-top));
}
.unified-header .header-content {
padding-top: calc(var(--status-bar-height) + 20rpx + env(safe-area-inset-top));
}
.unified-header + .unified-content {
margin-top: calc(var(--status-bar-height) + 88rpx + env(safe-area-inset-top));
}
}
.custom-navbar {
background: var(--gradient-primary);
padding: 20rpx 30rpx;
padding-top: calc(var(--status-bar-height) + 20rpx);
}
.navbar-content {
display: flex;
align-items: center;
justify-content: space-between;
}
.search-box {
flex: 1;
background-color: rgba(255, 255, 255, 0.2);
border-radius: 25rpx;
padding: 15rpx 20rpx;
margin-right: 20rpx;
display: flex;
align-items: center;
}
.search-placeholder {
color: rgba(255, 255, 255, 0.8);
font-size: 28rpx;
margin-left: 10rpx;
}
.notification {
position: relative;
padding: 10rpx;
}
.page-content {
height: 100vh;
padding: 20rpx;
box-sizing: border-box;
width: 100%;
}
/* 卡片基础样式 */
.profile-card, .functions-card, .help-card, .account-card {
background: var(--white);
border-radius: 20rpx;
margin-bottom: 20rpx;
box-shadow: var(--shadow-md);
overflow: hidden;
width: 100%;
box-sizing: border-box;
}
/* 个人信息卡片 */
.profile-card {
background: var(--gradient-primary);
color: var(--white);
}
.profile-content {
padding: 40rpx;
}
.profile-header {
display: flex;
align-items: center;
margin-bottom: 30rpx;
}
.profile-avatar {
position: relative;
margin-right: 30rpx;
}
.avatar {
width: 120rpx;
height: 120rpx;
border-radius: 60rpx;
background: rgba(255, 255, 255, 0.2);
display: flex;
align-items: center;
justify-content: center;
backdrop-filter: blur(10rpx);
border: 2rpx solid rgba(255, 255, 255, 0.3);
}
.avatar-text {
color: var(--white);
font-size: 48rpx;
font-weight: 600;
}
.edit-icon {
position: absolute;
bottom: 0;
right: 0;
width: 36rpx;
height: 36rpx;
background: rgba(255, 255, 255, 0.9);
border-radius: 50%;
display: flex;
align-items: center;
justify-content: center;
font-size: 20rpx;
color: #667eea;
}
.profile-info {
flex: 1;
}
.profile-name {
font-size: 36rpx;
font-weight: 700;
color: var(--white);
margin-bottom: 8rpx;
display: block;
}
.profile-dept {
font-size: 28rpx;
color: rgba(255, 255, 255, 0.8);
margin-bottom: 6rpx;
display: block;
}
.profile-id {
font-size: 24rpx;
color: rgba(255, 255, 255, 0.7);
}
.profile-arrow {
margin-left: 20rpx;
font-size: 24rpx;
color: rgba(255, 255, 255, 0.7);
}
/* 数据统计网格 */
.stats-grid {
display: flex;
gap: 20rpx;
}
.stat-item {
flex: 1;
background: rgba(255, 255, 255, 0.15);
border-radius: 16rpx;
padding: 24rpx;
display: flex;
align-items: center;
backdrop-filter: blur(10rpx);
border: 1rpx solid rgba(255, 255, 255, 0.2);
transition: all 0.3s ease;
}
.stat-item:active {
transform: scale(0.95);
background: rgba(255, 255, 255, 0.25);
}
.stat-icon {
width: 48rpx;
height: 48rpx;
border-radius: 24rpx;
background: rgba(255, 255, 255, 0.3);
display: flex;
align-items: center;
justify-content: center;
margin-right: 16rpx;
font-size: 24rpx;
color: #fff;
}
.stat-content {
flex: 1;
}
.stat-number {
font-size: 28rpx;
font-weight: 700;
color: var(--white);
display: block;
margin-bottom: 4rpx;
}
.stat-label {
font-size: 22rpx;
color: rgba(255, 255, 255, 0.8);
}
/* 未登录提示 */
.login-prompt {
display: flex;
align-items: center;
padding: 40rpx;
background: rgba(255, 255, 255, 0.1);
border-radius: 16rpx;
border: 2rpx dashed rgba(255, 255, 255, 0.3);
backdrop-filter: blur(10rpx);
}
.login-icon {
font-size: 80rpx;
color: rgba(255, 255, 255, 0.8);
margin-right: 24rpx;
}
.login-content {
flex: 1;
margin-right: 20rpx;
}
.login-title {
display: block;
font-size: 32rpx;
font-weight: 600;
color: var(--white);
margin-bottom: 8rpx;
}
.login-desc {
font-size: 26rpx;
color: rgba(255, 255, 255, 0.8);
line-height: 1.4;
}
.login-btn {
display: flex;
align-items: center;
gap: 8rpx;
padding: 16rpx 24rpx;
background: rgba(255, 255, 255, 0.2);
border-radius: 25rpx;
border: 1rpx solid rgba(255, 255, 255, 0.3);
transition: all 0.3s ease;
}
.login-btn:active {
transform: scale(0.95);
background: rgba(255, 255, 255, 0.3);
}
.login-btn-text {
font-size: 26rpx;
font-weight: 600;
color: var(--white);
}
.login-btn i {
font-size: 20rpx;
color: var(--white);
}
/* 卡片头部 */
.card-header {
padding: 30rpx 30rpx 20rpx;
border-bottom: 1rpx solid var(--border-light);
}
.card-title {
font-size: 32rpx;
font-weight: 600;
color: var(--text-color);
}
/* 模块网格布局 */
.module-grid {
display: flex;
flex-wrap: wrap;
padding: 20rpx;
gap: 16rpx;
align-items: flex-start;
}
.module-item {
width: calc(20% - 12.8rpx);
display: flex;
flex-direction: column;
align-items: center;
justify-content: flex-start;
background: var(--gray-lighter);
border-radius: 16rpx;
padding: 20rpx 12rpx;
transition: all 0.3s ease;
position: relative;
min-height: auto;
height: auto;
}
.module-item:active {
transform: scale(0.95);
background: var(--gray);
}
.module-item.none {
background: transparent;
pointer-events: none;
}
.module-icon {
width: 56rpx;
height: 56rpx;
border-radius: 14rpx;
display: flex;
align-items: center;
justify-content: center;
margin-bottom: 12rpx;
font-size: 28rpx;
color: #fff;
box-shadow: 0 4rpx 12rpx rgba(0, 0, 0, 0.15);
flex-shrink: 0;
}
.module-name {
font-size: 20rpx;
color: var(--text-color);
font-weight: 500;
text-align: center;
line-height: 1.3;
margin-bottom: 8rpx;
word-break: break-all;
hyphens: auto;
}
.module-value {
font-size: 20rpx;
color: var(--text-secondary);
text-align: center;
line-height: 1.3;
margin-bottom: 8rpx;
word-break: break-all;
}
.module-switch {
margin-top: 4rpx;
flex-shrink: 0;
}
/* 开关样式 */
.switch {
width: 48rpx;
height: 24rpx;
background-color: #e0e0e0;
border-radius: 12rpx;
position: relative;
transition: all 0.3s ease;
}
.switch.active {
background-color: #3498db;
}
.switch-handle {
width: 20rpx;
height: 20rpx;
background-color: #fff;
border-radius: 50%;
position: absolute;
top: 2rpx;
left: 2rpx;
transition: all 0.3s ease;
box-shadow: 0 1rpx 3rpx rgba(0, 0, 0, 0.2);
}
.switch.active .switch-handle {
transform: translateX(24rpx);
}
.search-icon, .notification-icon {
font-size: 32rpx;
margin-right: 10rpx;
color: var(--white);
}
.badge {
position: absolute;
top: 0rpx;
right: 15rpx;
background-color: var(--error);
color: var(--white);
font-size: 20rpx;
padding: 2rpx 8rpx;
border-radius: 50%;
// min-width: 30rpx;
text-align: center;
line-height: 1.2;
}
</style>