diff --git a/public/index.html b/public/index.html index 925455c..8b2b4f9 100644 --- a/public/index.html +++ b/public/index.html @@ -4,7 +4,7 @@ - + <%= webpackConfig.name %> diff --git a/src/assets/styles/element-ui.scss b/src/assets/styles/element-ui.scss index 363092a..4a1e0f6 100644 --- a/src/assets/styles/element-ui.scss +++ b/src/assets/styles/element-ui.scss @@ -89,4 +89,448 @@ > .el-submenu__title .el-submenu__icon-arrow { display: none; +} + +// 移动端 Element UI 组件优化 +@media (max-width: 768px) { + // 表格优化 + .el-table { + font-size: 12px; + + .el-table__header-wrapper, + .el-table__body-wrapper { + overflow-x: auto; + -webkit-overflow-scrolling: touch; + } + + th, + td { + padding: 8px 5px !important; + font-size: 12px; + } + + .el-table__cell { + padding: 8px 5px !important; + } + + // 操作列按钮优化 + .el-button { + padding: 5px 8px; + font-size: 12px; + margin: 2px; + + &.el-button--mini { + padding: 4px 6px; + font-size: 11px; + } + } + } + + // 表格工具栏优化 + .el-table__header-wrapper { + .el-table__header { + th { + font-size: 12px; + font-weight: 600; + } + } + } + + // 表单优化 + .el-form { + .el-form-item { + margin-bottom: 18px; + } + + .el-form-item__label { + font-size: 14px; + line-height: 1.5; + padding-bottom: 5px; + width: 100% !important; + text-align: left !important; + } + + .el-form-item__content { + margin-left: 0 !important; + } + + // 表单项内联优化 + .el-form-item--mini, + .el-form-item--small { + .el-form-item__label { + font-size: 13px; + } + } + } + + // 输入框优化 + .el-input { + .el-input__inner { + font-size: 16px; // 防止iOS自动缩放 + height: 44px; // 增大触摸目标 + line-height: 44px; + } + } + + // 选择器优化 + .el-select { + width: 100%; + + .el-input__inner { + font-size: 16px; + height: 44px; + line-height: 44px; + } + } + + // 日期选择器优化 + .el-date-editor { + width: 100% !important; + + .el-input__inner { + font-size: 16px; + height: 44px; + line-height: 44px; + } + } + + // 按钮优化 + .el-button { + min-height: 44px; // 增大触摸目标 + padding: 10px 15px; + font-size: 14px; + + &.el-button--mini { + min-height: 36px; + padding: 6px 10px; + font-size: 12px; + } + + &.el-button--small { + min-height: 40px; + padding: 8px 12px; + font-size: 13px; + } + } + + // 对话框优化 + .el-dialog { + width: 95% !important; + margin: 5vh auto !important; + border-radius: 8px; + + .el-dialog__header { + padding: 15px; + font-size: 16px; + } + + .el-dialog__body { + padding: 15px; + max-height: calc(90vh - 120px); + overflow-y: auto; + -webkit-overflow-scrolling: touch; + } + + .el-dialog__footer { + padding: 10px 15px; + + .el-button { + width: 100%; + margin: 5px 0; + } + } + } + + // 消息框优化 + .el-message-box { + width: 90% !important; + + .el-message-box__content { + padding: 15px; + } + + .el-message-box__btns { + .el-button { + width: 48%; + margin: 0 1%; + } + } + } + + // 抽屉优化 + .el-drawer { + width: 85% !important; + + .el-drawer__header { + padding: 15px; + font-size: 16px; + } + + .el-drawer__body { + padding: 15px; + overflow-y: auto; + -webkit-overflow-scrolling: touch; + } + } + + // 分页优化 + .el-pagination { + display: flex; + flex-wrap: wrap; + justify-content: center; + align-items: center; + gap: 5px; + padding: 10px 0; + + .el-pagination__sizes, + .el-pagination__total, + .el-pagination__jump { + display: none; + } + + .btn-prev, + .btn-next, + .el-pager li { + min-width: 36px; + height: 36px; + line-height: 36px; + font-size: 13px; + } + } + + // 标签页优化 + .el-tabs { + .el-tabs__header { + margin: 0 0 15px 0; + } + + .el-tabs__nav-wrap { + &::after { + height: 1px; + } + } + + .el-tabs__item { + padding: 0 12px; + font-size: 14px; + height: 44px; + line-height: 44px; + } + + .el-tabs__content { + padding: 10px 0; + } + } + + // 卡片优化 + .el-card { + margin-bottom: 10px; + border-radius: 8px; + + .el-card__header { + padding: 12px 15px; + font-size: 14px; + font-weight: 600; + } + + .el-card__body { + padding: 15px; + } + } + + // 步骤条优化 + .el-steps { + .el-step__title { + font-size: 12px; + } + + .el-step__description { + font-size: 11px; + } + } + + // 上传组件优化 + .el-upload { + width: 100%; + + .el-upload-dragger { + width: 100%; + padding: 20px; + } + } + + // 标签优化 + .el-tag { + font-size: 12px; + padding: 4px 8px; + margin: 2px; + } + + // 开关优化 + .el-switch { + .el-switch__core { + min-width: 44px; + height: 24px; + } + } + + // 单选框组优化 + .el-radio-group { + display: flex; + flex-wrap: wrap; + gap: 10px; + + .el-radio { + margin-right: 0; + margin-bottom: 10px; + } + } + + // 复选框组优化 + .el-checkbox-group { + display: flex; + flex-wrap: wrap; + gap: 10px; + + .el-checkbox { + margin-right: 0; + margin-bottom: 10px; + } + } + + // 级联选择器优化 + .el-cascader { + width: 100%; + + .el-input__inner { + font-size: 16px; + height: 44px; + line-height: 44px; + } + } + + // 时间选择器优化 + .el-time-picker { + width: 100%; + + .el-input__inner { + font-size: 16px; + height: 44px; + line-height: 44px; + } + } + + // 数字输入框优化 + .el-input-number { + width: 100%; + + .el-input__inner { + font-size: 16px; + height: 44px; + line-height: 44px; + } + } + + // 滑块优化 + .el-slider { + margin: 15px 0; + + .el-slider__button { + width: 20px; + height: 20px; + } + } + + // 评分优化 + .el-rate { + .el-rate__item { + font-size: 20px; + } + } + + // 颜色选择器优化 + .el-color-picker { + .el-color-picker__trigger { + width: 44px; + height: 44px; + } + } + + // 穿梭框优化 + .el-transfer { + .el-transfer-panel { + width: 45%; + } + } + + // 树形控件优化 + .el-tree { + .el-tree-node__content { + height: 40px; + line-height: 40px; + } + } + + // 折叠面板优化 + .el-collapse { + .el-collapse-item__header { + font-size: 14px; + height: 44px; + line-height: 44px; + padding: 0 15px; + } + + .el-collapse-item__content { + padding: 15px; + font-size: 13px; + } + } + + // 时间线优化 + .el-timeline { + .el-timeline-item__content { + font-size: 13px; + } + } + + // 描述列表优化 + .el-descriptions { + .el-descriptions__label { + font-size: 13px; + width: 30%; + } + + .el-descriptions__content { + font-size: 13px; + } + } + + // 空状态优化 + .el-empty { + padding: 20px; + + .el-empty__description { + font-size: 13px; + } + } + + // 骨架屏优化 + .el-skeleton { + .el-skeleton__item { + margin-bottom: 10px; + } + } + + // 结果页优化 + .el-result { + padding: 20px; + + .el-result__title { + font-size: 16px; + } + + .el-result__subtitle { + font-size: 13px; + } + } } \ No newline at end of file diff --git a/src/assets/styles/index.scss b/src/assets/styles/index.scss index bb87292..2e65737 100644 --- a/src/assets/styles/index.scss +++ b/src/assets/styles/index.scss @@ -4,6 +4,7 @@ @import './element-ui.scss'; @import './sidebar.scss'; @import './btn.scss'; +@import './mobile.scss'; body { height: 100%; @@ -122,6 +123,10 @@ aside { //main-container全局样式 .app-container { padding: 20px; + + @media (max-width: 768px) { + padding: 10px; + } } .components-container { @@ -176,3 +181,214 @@ aside { margin-bottom: 10px; } } + +// 移动端响应式优化 +@media (max-width: 768px) { + // 全局容器优化 + .app-container { + padding: 10px !important; + } + + .components-container { + margin: 15px 10px !important; + } + + // 表单优化 + .el-form { + .el-form-item { + margin-bottom: 18px; + } + + .el-form-item__label { + font-size: 14px; + padding-bottom: 5px; + } + + .el-input, + .el-select, + .el-date-picker { + width: 100% !important; + } + } + + // 按钮组优化 + .el-button-group { + display: flex; + flex-wrap: wrap; + gap: 8px; + + .el-button { + flex: 1; + min-width: 80px; + } + } + + // 对话框优化 + .el-dialog { + width: 95% !important; + margin: 5vh auto !important; + max-height: 90vh; + overflow-y: auto; + + .el-dialog__body { + padding: 15px; + max-height: calc(90vh - 120px); + overflow-y: auto; + } + } + + // 抽屉优化 + .el-drawer { + width: 85% !important; + } + + // 分页优化 + .pagination-container { + padding: 10px 0; + + .el-pagination { + display: flex; + flex-wrap: wrap; + justify-content: center; + gap: 5px; + + .el-pagination__sizes, + .el-pagination__total, + .el-pagination__jump { + display: none; // 移动端隐藏部分分页信息 + } + } + } + + // 卡片优化 + .el-card { + margin-bottom: 10px; + + .el-card__header { + padding: 12px 15px; + font-size: 14px; + } + + .el-card__body { + padding: 15px; + } + } + + // 标签页优化 + .el-tabs { + .el-tabs__header { + margin: 0 0 15px 0; + } + + .el-tabs__item { + padding: 0 12px; + font-size: 14px; + } + } + + // 表格容器优化 + .table-container { + overflow-x: auto; + -webkit-overflow-scrolling: touch; + + .el-table { + min-width: 600px; // 保持最小宽度,允许横向滚动 + } + } + + // 搜索表单优化 + .search-form { + .el-form-item { + width: 100% !important; + margin-right: 0 !important; + } + } + + // 操作按钮区域优化 + .toolbar { + display: flex; + flex-wrap: wrap; + gap: 8px; + margin-bottom: 15px; + + .el-button { + flex: 1; + min-width: 80px; + } + } + + // 文本溢出处理 + .text-ellipsis { + overflow: hidden; + text-overflow: ellipsis; + white-space: nowrap; + } + + // 触摸优化 + * { + -webkit-tap-highlight-color: rgba(0, 0, 0, 0.1); + } + + // 移动端卡片列表优化 + .mobile-card-list { + background: #f5f7fa; + padding: 12px; + } + + // 移动端搜索表单优化 + .mobile-search-form { + .search-bar { + background: #fff; + border-radius: 8px; + margin-bottom: 12px; + } + } + + // 移动端按钮组优化 + .mobile-button-group { + .mobile-buttons { + background: #fff; + border-radius: 8px; + margin-bottom: 12px; + } + } + + // 移动端表格容器优化 + .table-container { + @media (max-width: 768px) { + .el-table { + display: none; // 移动端隐藏表格,使用卡片视图 + } + } + } + + // 输入框优化(防止iOS自动缩放) + input[type="text"], + input[type="password"], + input[type="number"], + input[type="email"], + input[type="tel"], + textarea, + select { + font-size: 16px !important; + } + + // 禁用文本选择(移动端长按优化) + .no-select { + -webkit-user-select: none; + -moz-user-select: none; + -ms-user-select: none; + user-select: none; + } +} + +// 平板设备优化 +@media (min-width: 769px) and (max-width: 1024px) { + .app-container { + padding: 15px !important; + } + + .components-container { + margin: 20px 30px !important; + } +} \ No newline at end of file diff --git a/src/assets/styles/mobile.scss b/src/assets/styles/mobile.scss new file mode 100644 index 0000000..0856897 --- /dev/null +++ b/src/assets/styles/mobile.scss @@ -0,0 +1,394 @@ +/** + * 移动端专用样式 + */ + +// 移动端全局优化 +@media (max-width: 768px) { + // 页面容器 + .app-container { + padding: 12px !important; + background: #f5f7fa; + min-height: calc(100vh - 48px - 60px); // 减去头部和底部导航 + } + + // 卡片样式 + .el-card { + border-radius: 12px; + box-shadow: 0 2px 12px rgba(0, 0, 0, 0.08); + margin-bottom: 12px; + border: none; + + .el-card__header { + padding: 16px; + font-size: 16px; + font-weight: 600; + border-bottom: 1px solid #f0f0f0; + } + + .el-card__body { + padding: 16px; + } + } + + // 列表项优化 + .el-list-item { + padding: 16px; + border-bottom: 1px solid #f0f0f0; + + &:last-child { + border-bottom: none; + } + } + + // 分割线优化 + .el-divider { + margin: 16px 0; + } + + // 标签优化 + .el-tag { + font-size: 12px; + padding: 4px 10px; + border-radius: 12px; + margin: 2px; + } + + // 徽章优化 + .el-badge { + .el-badge__content { + font-size: 10px; + padding: 0 4px; + height: 16px; + line-height: 16px; + min-width: 16px; + } + } + + // 步骤条优化 + .el-steps { + .el-step__title { + font-size: 12px; + } + + .el-step__description { + font-size: 11px; + } + } + + // 时间线优化 + .el-timeline { + padding-left: 20px; + + .el-timeline-item__node { + width: 12px; + height: 12px; + } + + .el-timeline-item__content { + font-size: 13px; + } + } + + // 描述列表优化 + .el-descriptions { + .el-descriptions__label { + width: 35%; + font-size: 13px; + color: #909399; + } + + .el-descriptions__content { + font-size: 13px; + color: #303133; + } + } + + // 空状态优化 + .el-empty { + padding: 40px 20px; + + .el-empty__image { + width: 120px; + height: 120px; + } + + .el-empty__description { + font-size: 14px; + color: #909399; + margin-top: 16px; + } + } + + // 骨架屏优化 + .el-skeleton { + padding: 16px; + + .el-skeleton__item { + margin-bottom: 12px; + border-radius: 4px; + } + } + + // 结果页优化 + .el-result { + padding: 30px 20px; + + .el-result__icon { + font-size: 60px; + } + + .el-result__title { + font-size: 18px; + margin-top: 20px; + } + + .el-result__subtitle { + font-size: 14px; + margin-top: 12px; + } + } + + // 加载优化 + .el-loading-mask { + border-radius: 8px; + } + + // 消息提示优化 + .el-message { + min-width: auto; + width: 90%; + left: 50%; + transform: translateX(-50%); + border-radius: 8px; + padding: 12px 16px; + + .el-message__content { + font-size: 14px; + } + } + + // 通知优化 + .el-notification { + width: 90%; + border-radius: 8px; + padding: 16px; + + .el-notification__title { + font-size: 15px; + } + + .el-notification__content { + font-size: 13px; + margin-top: 8px; + } + } + + // 弹出层优化 + .el-popover { + border-radius: 8px; + padding: 12px; + max-width: 90vw; + } + + // 工具提示优化 + .el-tooltip__popper { + font-size: 12px; + padding: 8px 12px; + border-radius: 6px; + } + + // 下拉菜单优化 + .el-dropdown-menu { + border-radius: 8px; + padding: 8px 0; + + .el-dropdown-menu__item { + padding: 12px 20px; + font-size: 14px; + + &:hover { + background: #f5f7fa; + } + } + } + + // 选择器下拉优化 + .el-select-dropdown { + border-radius: 8px; + + .el-select-dropdown__item { + padding: 12px 20px; + font-size: 14px; + } + } + + // 日期选择器优化 + .el-picker-panel { + width: 95%; + left: 2.5% !important; + border-radius: 8px; + + .el-date-picker__header { + padding: 12px 16px; + } + + .el-picker-panel__content { + padding: 8px; + } + } + + // 级联选择器优化 + .el-cascader-menus { + border-radius: 8px; + + .el-cascader-menu { + min-width: 120px; + } + } + + // 穿梭框优化 + .el-transfer { + display: flex; + flex-direction: column; + gap: 16px; + + .el-transfer-panel { + width: 100%; + border-radius: 8px; + } + } + + // 树形控件优化 + .el-tree { + .el-tree-node__content { + height: 44px; + padding: 0 12px; + + &:hover { + background: #f5f7fa; + } + } + + .el-tree-node__label { + font-size: 14px; + } + } + + // 折叠面板优化 + .el-collapse { + border: none; + + .el-collapse-item { + margin-bottom: 12px; + border: 1px solid #e4e7ed; + border-radius: 8px; + overflow: hidden; + + .el-collapse-item__header { + padding: 16px; + font-size: 15px; + font-weight: 500; + } + + .el-collapse-item__content { + padding: 16px; + font-size: 14px; + } + } + } + + // 进度条优化 + .el-progress { + .el-progress__text { + font-size: 12px; + } + } + + // 滑块优化 + .el-slider { + margin: 20px 0; + + .el-slider__button { + width: 20px; + height: 20px; + border: 2px solid #409eff; + } + } + + // 评分优化 + .el-rate { + .el-rate__item { + font-size: 24px; + margin-right: 8px; + } + } + + // 颜色选择器优化 + .el-color-picker { + .el-color-picker__trigger { + width: 50px; + height: 50px; + border-radius: 8px; + } + } + + // 上传组件优化 + .el-upload { + width: 100%; + + .el-upload-dragger { + width: 100%; + padding: 30px; + border-radius: 8px; + } + } + + // 图片预览优化 + .el-image-viewer__wrapper { + .el-image-viewer__canvas { + img { + max-width: 90vw; + max-height: 90vh; + } + } + } + + // 抽屉优化 + .el-drawer { + .el-drawer__header { + padding: 20px; + border-bottom: 1px solid #e4e7ed; + + .el-drawer__title { + font-size: 18px; + font-weight: 600; + } + } + + .el-drawer__body { + padding: 20px; + } + } + + // 固定定位元素优化(适配安全区域) + .fixed-bottom { + bottom: env(safe-area-inset-bottom); + } + + .fixed-top { + top: env(safe-area-inset-top); + } +} + +// 平板设备优化 +@media (min-width: 769px) and (max-width: 1024px) { + .app-container { + padding: 16px !important; + } + + .el-card { + border-radius: 10px; + margin-bottom: 16px; + } +} + diff --git a/src/assets/styles/ruoyi.scss b/src/assets/styles/ruoyi.scss index ab4a1d2..bc045f3 100644 --- a/src/assets/styles/ruoyi.scss +++ b/src/assets/styles/ruoyi.scss @@ -137,6 +137,68 @@ .pagination-container .el-pagination > .el-pagination__sizes { display: none !important; } + + // 表格移动端优化 + .el-table { + font-size: 12px; + + .el-table__header-wrapper, + .el-table__body-wrapper { + overflow-x: auto; + -webkit-overflow-scrolling: touch; + } + + th, td { + padding: 8px 5px !important; + font-size: 12px; + } + + .el-table__cell { + padding: 8px 5px !important; + } + } + + // 表单移动端优化 + .form-header { + font-size: 14px; + margin: 5px 5px 15px 5px; + padding-bottom: 5px; + } + + // 卡片移动端优化 + .el-card__header { + padding: 10px 12px 5px !important; + font-size: 14px; + } + + .el-card__body { + padding: 12px 15px 15px 15px !important; + } + + // 按钮组移动端优化 + .top-right-btn { + float: none; + margin-bottom: 10px; + width: 100%; + + .el-button { + width: 100%; + margin-bottom: 8px; + } + } + + // 工具类移动端优化 + .mb20, .mt20, .mr20, .ml20 { + margin: 10px !important; + } + + .mb10, .mt10, .mr10, .ml10 { + margin: 8px !important; + } + + .mb5, .mt5, .mr5, .ml5 { + margin: 5px !important; + } } .el-table .fixed-width .el-button--mini { diff --git a/src/components/MobileBottomNav/index.vue b/src/components/MobileBottomNav/index.vue new file mode 100644 index 0000000..dc0a270 --- /dev/null +++ b/src/components/MobileBottomNav/index.vue @@ -0,0 +1,174 @@ + + + + + + diff --git a/src/components/MobileButtonGroup/index.vue b/src/components/MobileButtonGroup/index.vue new file mode 100644 index 0000000..9e462c1 --- /dev/null +++ b/src/components/MobileButtonGroup/index.vue @@ -0,0 +1,188 @@ + + + + + + diff --git a/src/components/MobileSearchForm/index.vue b/src/components/MobileSearchForm/index.vue new file mode 100644 index 0000000..7f6adbc --- /dev/null +++ b/src/components/MobileSearchForm/index.vue @@ -0,0 +1,259 @@ + + + + + + diff --git a/src/components/MobileTable/index.vue b/src/components/MobileTable/index.vue new file mode 100644 index 0000000..5745c77 --- /dev/null +++ b/src/components/MobileTable/index.vue @@ -0,0 +1,403 @@ + + + + + + diff --git a/src/components/Pagination/index.vue b/src/components/Pagination/index.vue index 16b8f0f..a1708d2 100644 --- a/src/components/Pagination/index.vue +++ b/src/components/Pagination/index.vue @@ -42,7 +42,7 @@ export default { // 移动端页码按钮的数量端默认值5 pagerCount: { type: Number, - default: document.body.clientWidth < 992 ? 5 : 7 + default: 7 }, layout: { type: String, @@ -63,8 +63,19 @@ export default { }, data() { return { + isMobile: false } }, + mounted() { + this.isMobile = window.innerWidth < 768 + if (this.isMobile && this.layout === 'total, sizes, prev, pager, next, jumper') { + this.$emit('update:layout', 'prev, pager, next') + } + window.addEventListener('resize', this.handleResize) + }, + beforeDestroy() { + window.removeEventListener('resize', this.handleResize) + }, computed: { currentPage: { get() { @@ -84,6 +95,13 @@ export default { } }, methods: { + handleResize() { + const wasMobile = this.isMobile + this.isMobile = window.innerWidth < 768 + if (wasMobile !== this.isMobile) { + this.$forceUpdate() + } + }, handleSizeChange(val) { if (this.currentPage * val > this.total) { this.currentPage = 1 @@ -106,6 +124,33 @@ export default { diff --git a/src/layout/components/AppMain.vue b/src/layout/components/AppMain.vue index 9209165..2839caa 100644 --- a/src/layout/components/AppMain.vue +++ b/src/layout/components/AppMain.vue @@ -51,24 +51,47 @@ export default { width: 100%; position: relative; overflow: hidden; + + @media (max-width: 768px) { + min-height: calc(100vh - 48px); + overflow-x: hidden; + overflow-y: auto; + -webkit-overflow-scrolling: touch; + } } .app-main:has(.copyright) { padding-bottom: 36px; + + @media (max-width: 768px) { + padding-bottom: 30px; + } } .fixed-header + .app-main { padding-top: 50px; + + @media (max-width: 768px) { + padding-top: 48px; + } } .hasTagsView { .app-main { /* 84 = navbar + tags-view = 50 + 34 */ min-height: calc(100vh - 84px); + + @media (max-width: 768px) { + min-height: calc(100vh - 48px); + } } .fixed-header + .app-main { padding-top: 84px; + + @media (max-width: 768px) { + padding-top: 48px; + } } } diff --git a/src/layout/components/Navbar.vue b/src/layout/components/Navbar.vue index a6b61b5..f43ec6f 100644 --- a/src/layout/components/Navbar.vue +++ b/src/layout/components/Navbar.vue @@ -110,6 +110,12 @@ export default { background: #fff; box-shadow: 0 1px 4px rgba(0,21,41,.08); + // 移动端优化 + @media (max-width: 768px) { + height: 48px; + padding: 0 5px; + } + .hamburger-container { line-height: 46px; height: 100%; @@ -117,19 +123,41 @@ export default { cursor: pointer; transition: background .3s; -webkit-tap-highlight-color:transparent; + padding: 0 12px; + min-width: 44px; // 增大触摸目标 + display: flex; + align-items: center; + justify-content: center; + + @media (max-width: 768px) { + line-height: 48px; + padding: 0 10px; + } &:hover { background: rgba(0, 0, 0, .025) } + + &:active { + background: rgba(0, 0, 0, .05) + } } .breadcrumb-container { float: left; + + @media (max-width: 768px) { + display: none; // 移动端隐藏面包屑 + } } .topmenu-container { position: absolute; left: 50px; + + @media (max-width: 768px) { + left: 44px; + } } .errLog-container { @@ -141,19 +169,36 @@ export default { float: right; height: 100%; line-height: 50px; + display: flex; + align-items: center; + gap: 5px; + + @media (max-width: 768px) { + line-height: 48px; + gap: 2px; + } &:focus { outline: none; } .right-menu-item { - display: inline-block; + display: inline-flex; + align-items: center; + justify-content: center; padding: 0 8px; height: 100%; + min-width: 44px; // 增大触摸目标 font-size: 18px; color: #5a5e66; vertical-align: text-bottom; + @media (max-width: 768px) { + padding: 0 6px; + font-size: 16px; + min-width: 40px; + } + &.hover-effect { cursor: pointer; transition: background .3s; @@ -161,6 +206,10 @@ export default { &:hover { background: rgba(0, 0, 0, .025) } + + &:active { + background: rgba(0, 0, 0, .05) + } } } @@ -168,33 +217,71 @@ export default { margin-right: 0px; padding-right: 0px; + @media (max-width: 768px) { + margin-right: 0; + } + .avatar-wrapper { margin-top: 10px; position: relative; + display: flex; + align-items: center; + gap: 6px; + cursor: pointer; + padding: 0 4px; + min-height: 44px; // 增大触摸目标 + + @media (max-width: 768px) { + margin-top: 8px; + gap: 4px; + } .user-avatar { cursor: pointer; width: 30px; height: 30px; border-radius: 50%; + flex-shrink: 0; + + @media (max-width: 768px) { + width: 28px; + height: 28px; + } } .user-nickname{ position: relative; - bottom: 10px; font-size: 14px; font-weight: bold; + white-space: nowrap; + max-width: 80px; + overflow: hidden; + text-overflow: ellipsis; + + @media (max-width: 768px) { + font-size: 13px; + max-width: 60px; + display: none; // 移动端隐藏昵称 + } } .el-icon-caret-bottom { cursor: pointer; - position: absolute; - right: -20px; - top: 25px; font-size: 12px; + flex-shrink: 0; + + @media (max-width: 768px) { + font-size: 10px; + } } } } + + .setting { + @media (max-width: 768px) { + display: none; // 移动端隐藏设置按钮 + } + } } } diff --git a/src/layout/components/Sidebar/Logo.vue b/src/layout/components/Sidebar/Logo.vue index ac98e67..3138b38 100644 --- a/src/layout/components/Sidebar/Logo.vue +++ b/src/layout/components/Sidebar/Logo.vue @@ -65,6 +65,12 @@ export default { overflow: hidden; border-bottom: 1px solid rgba(255, 255, 255, 0.1); backdrop-filter: blur(10px); + + // 移动端优化 + @media (max-width: 768px) { + height: 50px; + line-height: 50px; + } & .sidebar-logo-link { height: 100%; @@ -73,6 +79,10 @@ export default { align-items: center; justify-content: center; padding: 0 20px; + + @media (max-width: 768px) { + padding: 0 15px; + } & .logo-icon { display: flex; @@ -86,11 +96,21 @@ export default { margin-right: 15px; transition: all 0.3s ease; box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1); + + @media (max-width: 768px) { + width: 36px; + height: 36px; + margin-right: 10px; + } i { font-size: 22px; color: #ffffff; text-shadow: 0 1px 2px rgba(0, 0, 0, 0.1); + + @media (max-width: 768px) { + font-size: 18px; + } } &:hover { @@ -99,6 +119,10 @@ export default { transform: scale(1.05); box-shadow: 0 4px 12px rgba(0, 0, 0, 0.15); } + + &:active { + transform: scale(0.95); + } } & .sidebar-title { @@ -110,6 +134,10 @@ export default { font-family: Avenir, Helvetica Neue, Arial, Helvetica, sans-serif; vertical-align: middle; text-shadow: 0 1px 2px rgba(0, 0, 0, 0.1); + + @media (max-width: 768px) { + font-size: 14px; + } } } diff --git a/src/layout/components/TagsView/index.vue b/src/layout/components/TagsView/index.vue index f0b0837..5593704 100644 --- a/src/layout/components/TagsView/index.vue +++ b/src/layout/components/TagsView/index.vue @@ -244,6 +244,14 @@ export default { background: #fff; border-bottom: 1px solid #d8dce5; box-shadow: 0 1px 3px 0 rgba(0, 0, 0, .12), 0 0 3px 0 rgba(0, 0, 0, .04); + + // 移动端优化 + @media (max-width: 768px) { + height: 0; + overflow: hidden; + display: none; // 移动端隐藏标签页 + } + .tags-view-wrapper { .tags-view-item { display: inline-block; @@ -258,11 +266,30 @@ export default { font-size: 12px; margin-left: 5px; margin-top: 4px; + white-space: nowrap; + max-width: 150px; + overflow: hidden; + text-overflow: ellipsis; + + @media (max-width: 768px) { + max-width: 120px; + font-size: 11px; + padding: 0 6px; + } + &:first-of-type { margin-left: 15px; + + @media (max-width: 768px) { + margin-left: 10px; + } } &:last-of-type { margin-right: 15px; + + @media (max-width: 768px) { + margin-right: 10px; + } } &.active { background-color: #42b983; @@ -298,13 +325,39 @@ export default { font-weight: 400; color: #333; box-shadow: 2px 2px 3px 0 rgba(0, 0, 0, .3); + min-width: 120px; + + @media (max-width: 768px) { + font-size: 14px; + min-width: 140px; + padding: 8px 0; + } + li { margin: 0; padding: 7px 16px; cursor: pointer; + min-height: 40px; + display: flex; + align-items: center; + + @media (max-width: 768px) { + padding: 10px 16px; + min-height: 44px; + } + &:hover { background: #eee; } + + &:active { + background: #ddd; + } + + i { + margin-right: 8px; + font-size: 14px; + } } } } diff --git a/src/layout/index.vue b/src/layout/index.vue index 05e2fa9..2ae9413 100644 --- a/src/layout/index.vue +++ b/src/layout/index.vue @@ -1,20 +1,23 @@ +``` + +### 2. MobileSearchForm - 移动端搜索表单 + +移动端自动折叠为快速搜索,点击筛选按钮展开完整表单。 + +```vue + +``` + +### 3. MobileButtonGroup - 移动端按钮组 + +移动端自动将按钮分组,主要按钮显示,其他按钮放入"更多"菜单。 + +```vue + + + +``` + +### 4. MobileBottomNav - 移动端底部导航 + +在移动端显示底部导航栏,方便快速切换页面。 + +```vue + + + +``` + +## 工具函数 + +### mobile.js + +提供移动端检测和优化工具函数: + +```javascript +import { isMobile, isIOS, initMobile } from '@/utils/mobile' + +// 检测是否为移动端 +if (isMobile()) { + // 移动端逻辑 +} + +// 初始化移动端优化 +initMobile() +``` + +## 混入 + +### mobile.js mixin + +提供移动端相关的计算属性和方法: + +```vue + +``` + +## 样式优化 + +### 响应式断点 + +- **移动端**:`max-width: 768px` +- **平板**:`769px - 1024px` +- **桌面端**:`min-width: 1025px` + +### 主要优化 + +1. **触摸目标**:所有可点击元素最小 44px × 44px +2. **字体大小**:输入框字体 16px 防止 iOS 自动缩放 +3. **间距优化**:移动端使用更紧凑的间距 +4. **圆角优化**:使用更大的圆角值(8px-12px) +5. **阴影优化**:使用更柔和的阴影效果 + +## 使用示例 + +### 完整列表页面示例 + +```vue + +``` + +## 注意事项 + +1. **组件注册**:移动端组件需要在使用前注册或导入 +2. **字典数据**:MobileTable 组件需要字典数据支持,确保字典已加载 +3. **路由配置**:底部导航需要配置正确的路由路径 +4. **性能优化**:大数据量时建议使用虚拟滚动或分页加载 + +## 浏览器支持 + +- iOS Safari 12+ +- Android Chrome 70+ +- 微信内置浏览器 +- 其他现代移动浏览器 + +## 更新日志 + +### v1.0.0 +- 初始版本 +- 支持移动端卡片式列表 +- 支持移动端折叠搜索 +- 支持移动端底部导航 +- 完整的响应式适配 +