refactor: 升级Vue SFC深度选择器语法为::v-deep

本次提交将项目中所有使用`::deep`的CSS深度选择器统一替换为Vue 3官方推荐的`::v-deep`语法,修复了旧版语法在新版本Vue生态中的兼容性问题,同时修正了部分组件的响应式表单定义方式,将`reactive`配合`Object.assign`的写法调整为更符合Vue 3组合式API规范的`ref`响应式状态写法,整体优化了代码的可维护性和兼容性。
This commit is contained in:
zhangtao
2026-05-11 15:46:18 +08:00
parent 4112942a14
commit 80d4f18e8b
64 changed files with 510 additions and 501 deletions
@@ -367,27 +367,27 @@ const highlightOnHoverHistory = (index: number) => {
</script>
<style lang="scss" scoped>
.layout-search {
::deep(.search-modal) {
::v-deep(.search-modal) {
background-color: rgb(0 0 0 / 20%);
}
::deep(.el-dialog__body) {
::v-deep(.el-dialog__body) {
padding: 5px 0 0 !important;
}
::deep(.el-dialog__header) {
::v-deep(.el-dialog__header) {
padding: 0;
}
.el-input {
::deep(.el-input__wrapper) {
::v-deep(.el-input__wrapper) {
background-color: var(--fa-gray-200);
border: 1px solid var(--default-border-dashed);
border-radius: calc(var(--custom-radius) / 2 + 2px) !important;
box-shadow: none;
}
::deep(.el-input__inner) {
::v-deep(.el-input__inner) {
color: var(--fa-gray-800) !important;
}
}
@@ -395,18 +395,18 @@ const highlightOnHoverHistory = (index: number) => {
.dark .layout-search {
.el-input {
::deep(.el-input__wrapper) {
::v-deep(.el-input__wrapper) {
background-color: #333;
border: 1px solid #4c4d50;
}
}
::deep(.search-modal) {
::v-deep(.search-modal) {
background-color: rgb(23 23 26 / 60%);
backdrop-filter: none;
}
::deep(.el-dialog) {
::v-deep(.el-dialog) {
background-color: #252526;
}
}
@@ -463,35 +463,35 @@ const openChat = (): void => {
}
/* Hover animation classes */
.refresh-btn:hover ::deep(.fa-svg-icon) {
.refresh-btn:hover ::v-deep(.fa-svg-icon) {
animation: rotate180 0.5s;
}
.language-btn:hover ::deep(.fa-svg-icon) {
.language-btn:hover ::v-deep(.fa-svg-icon) {
animation: moveUp 0.4s;
}
.setting-btn:hover ::deep(.fa-svg-icon) {
.setting-btn:hover ::v-deep(.fa-svg-icon) {
animation: rotate180 0.5s;
}
.full-screen-btn:hover ::deep(.fa-svg-icon) {
.full-screen-btn:hover ::v-deep(.fa-svg-icon) {
animation: expand 0.6s forwards;
}
::deep(.size-select-btn:hover .fa-svg-icon) {
::v-deep(.size-select-btn:hover .fa-svg-icon) {
animation: expand 0.6s forwards;
}
.exit-full-screen-btn:hover ::deep(.fa-svg-icon) {
.exit-full-screen-btn:hover ::v-deep(.fa-svg-icon) {
animation: shrink 0.6s forwards;
}
.notice-button:hover ::deep(.fa-svg-icon) {
.notice-button:hover ::v-deep(.fa-svg-icon) {
animation: shake 0.5s ease-in-out;
}
.chat-button:hover ::deep(.fa-svg-icon) {
.chat-button:hover ::v-deep(.fa-svg-icon) {
animation: shake 0.5s ease-in-out;
}
@@ -247,7 +247,7 @@ function closeUserMenu(): void {
}
/* ElPopover 基于 Tooltip:触发层默认 inline-block,与顶栏 flex 图标中线对齐 */
.fa-user-menu ::deep(.el-tooltip__trigger) {
.fa-user-menu .el-tooltip__trigger {
display: inline-flex !important;
align-items: center;
line-height: 1;
@@ -92,18 +92,18 @@ const filterMenuItems = (items: AppRouteRecord[]): AppRouteRecord[] => {
<style scoped>
/* Remove el-menu bottom border */
::deep(.el-menu) {
::v-deep(.el-menu) {
border-bottom: none !important;
}
/* Remove default styles for first-level menu items */
::deep(.el-menu-item[tabindex="0"]) {
::v-deep(.el-menu-item[tabindex="0"]) {
background-color: transparent !important;
border: none !important;
}
/* Remove bottom border from submenu titles */
::deep(.el-menu--horizontal .el-sub-menu__title) {
::v-deep(.el-menu--horizontal .el-sub-menu__title) {
padding: 0 30px 0 10px !important;
border: 0 !important;
}
@@ -106,7 +106,7 @@ const closeMenu = () => {
</script>
<style scoped>
::deep(.el-sub-menu__title .el-sub-menu__icon-arrow) {
::v-deep(.el-sub-menu__title .el-sub-menu__icon-arrow) {
right: 10px !important;
}
</style>
@@ -248,13 +248,13 @@ onMounted(initScrollState);
</style>
<style scoped>
::deep(.el-scrollbar__bar.is-horizontal) {
::v-deep(.el-scrollbar__bar.is-horizontal) {
bottom: 5px;
display: none;
height: 2px;
}
::deep(.scrollbar-wrapper) {
::v-deep(.scrollbar-wrapper) {
flex: 1;
min-width: 0;
margin: 0 50px 0 30px;
@@ -273,7 +273,7 @@ onMounted(initScrollState);
}
@media (width <= 1440px) {
::deep(.scrollbar-wrapper) {
::v-deep(.scrollbar-wrapper) {
margin: 0 45px;
}
}
@@ -10,11 +10,11 @@
}
// 自定义滚动条宽度
::deep(.el-scrollbar__bar.is-vertical) {
:deep(.el-scrollbar__bar.is-vertical) {
width: 4px;
}
::deep(.el-scrollbar__thumb) {
:deep(.el-scrollbar__thumb) {
right: -2px;
background-color: #ccc;
border-radius: 2px;
@@ -240,7 +240,7 @@
.layout-sidebar {
border-right: 1px solid rgb(255 255 255 / 13%);
::deep(.el-scrollbar__thumb) {
:deep(.el-scrollbar__thumb) {
background-color: #777;
}
@@ -203,7 +203,7 @@ const unlockLoading = ref(false);
const formRef = ref<FormInstance>();
const formData = reactive({
const formData = ref({
password: "",
});
@@ -388,11 +388,14 @@ const handleLock = async () => {
await formRef.value.validate((valid, fields) => {
if (valid) {
const encryptedPassword = CryptoJS.AES.encrypt(formData.password, ENCRYPT_KEY).toString();
const encryptedPassword = CryptoJS.AES.encrypt(
formData.value.password,
ENCRYPT_KEY
).toString();
userStore.setLockStatus(true);
userStore.setLockPassword(encryptedPassword);
visible.value = false;
formData.password = "";
formData.value.password = "";
showClock.value = true;
unlockPwd.value = "";
unlockErrMsg.value = false;
@@ -80,7 +80,7 @@
}
// 去除火狐浏览器滚动条
::deep(.el-drawer__body) {
:deep(.el-drawer__body) {
scrollbar-width: none;
}
@@ -33,7 +33,7 @@
padding: 20px;
overflow: auto;
::deep(.layout-content) {
:deep(.layout-content) {
box-sizing: border-box;
width: 100%;
min-width: 0;
@@ -80,7 +80,7 @@
overflow: visible;
#app-content {
::deep(.layout-content) {
:deep(.layout-content) {
width: calc(100% - 40px);
}
}
@@ -92,7 +92,7 @@
.app-layout {
#app-main {
#app-content {
::deep(.layout-content) {
:deep(.layout-content) {
width: calc(100% - 30px);
}
}
@@ -283,11 +283,11 @@ function downloadImg() {
}
}
::deep(.toolBoxControl) {
::v-deep(.toolBoxControl) {
z-index: 100;
}
::deep(.dockMain) {
::v-deep(.dockMain) {
right: 0;
bottom: -40px;
left: 0;
@@ -297,15 +297,15 @@ function downloadImg() {
opacity: 1;
}
::deep(.copyright) {
::v-deep(.copyright) {
display: none !important;
}
::deep(.i-dialog-footer) {
::v-deep(.i-dialog-footer) {
margin-top: 60px !important;
}
::deep(.dockBtn) {
::v-deep(.dockBtn) {
height: 26px;
padding: 0 10px;
font-size: 12px;
@@ -315,31 +315,31 @@ function downloadImg() {
border: 1px solid var(--el-color-primary-light-4) !important;
}
::deep(.dockBtnScrollBar) {
::v-deep(.dockBtnScrollBar) {
margin: 0 10px 0 6px;
background-color: var(--el-color-primary-light-1);
}
::deep(.scrollBarControl) {
::v-deep(.scrollBarControl) {
border-color: var(--el-color-primary);
}
::deep(.closeIcon) {
::v-deep(.closeIcon) {
line-height: 15px !important;
}
}
.dark {
.cutter-container {
::deep(.toolBox) {
::v-deep(.toolBox) {
border: transparent;
}
::deep(.dialogMain) {
::v-deep(.dialogMain) {
background-color: transparent !important;
}
::deep(.i-dialog-footer) {
::v-deep(.i-dialog-footer) {
.btn {
background-color: var(--el-color-primary) !important;
border: transparent;
@@ -119,7 +119,7 @@ const dialogAttrs = computed(() => {
align-items: center;
margin-left: auto;
::deep(.core-overlay-icon-btn.el-button) {
::v-deep(.core-overlay-icon-btn.el-button) {
min-width: 32px;
padding: 6px;
border-radius: var(--el-border-radius-base);
@@ -99,7 +99,7 @@ const drawerAttrs = computed(() => {
align-items: center;
margin-left: auto;
::deep(.core-overlay-icon-btn.el-button) {
::v-deep(.core-overlay-icon-btn.el-button) {
min-width: 32px;
padding: 6px;
border-radius: var(--el-border-radius-base);
@@ -205,45 +205,45 @@ const handleDeleteEvent = () => {
min-width: 0;
}
::deep(.el-calendar__header) {
::v-deep(.el-calendar__header) {
padding: 6px 4px;
border-bottom: none;
}
::deep(.el-calendar__title) {
::v-deep(.el-calendar__title) {
font-size: 14px;
font-weight: 600;
}
::deep(.el-calendar__header .el-button) {
::v-deep(.el-calendar__header .el-button) {
padding: 4px 8px;
}
::deep(.el-calendar__body) {
::v-deep(.el-calendar__body) {
padding: 2px 0 4px;
}
::deep(.el-calendar-table thead th) {
::v-deep(.el-calendar-table thead th) {
padding: 4px 0;
font-size: 11px;
font-weight: 500;
}
::deep(.is-selected) {
::v-deep(.is-selected) {
background-color: var(--el-color-warning-light-9) !important;
}
::deep(.el-calendar-day) {
::v-deep(.el-calendar-day) {
height: auto;
min-height: 3rem;
padding: 0;
}
::deep(.el-calendar-day:hover) {
::v-deep(.el-calendar-day:hover) {
background-color: transparent !important;
}
::deep(.el-dialog__body) {
::v-deep(.el-dialog__body) {
padding-top: 20px;
}
</style>
@@ -181,8 +181,8 @@ onMounted(() => {
</script>
<style scoped lang="scss">
.reference ::deep(.el-input__wrapper),
.reference ::deep(.el-input__inner) {
.reference :deep(.el-input__wrapper),
.reference :deep(.el-input__inner) {
cursor: pointer;
}
@@ -70,7 +70,7 @@ const renderedContent = computed(() => {
color: var(--el-text-color-primary);
word-wrap: break-word;
::deep(pre) {
::v-deep(pre) {
padding: 12px;
margin: 12px 0;
overflow-x: auto;
@@ -83,7 +83,7 @@ const renderedContent = computed(() => {
}
}
::deep(code) {
::v-deep(code) {
padding: 2px 6px;
font-family: "Courier New", Courier, monospace;
font-size: 13px;
@@ -91,21 +91,21 @@ const renderedContent = computed(() => {
border-radius: 3px;
}
::deep(p) {
::v-deep(p) {
margin: 8px 0;
}
::deep(ul),
::deep(ol) {
::v-deep(ul),
::v-deep(ol) {
padding-left: 24px;
margin: 8px 0;
}
::deep(li) {
::v-deep(li) {
margin: 4px 0;
}
::deep(a) {
::v-deep(a) {
color: var(--el-color-primary);
text-decoration: none;
@@ -114,14 +114,14 @@ const renderedContent = computed(() => {
}
}
::deep(blockquote) {
::v-deep(blockquote) {
padding: 8px 16px;
margin: 12px 0;
background: var(--el-fill-color-light);
border-left: 4px solid var(--el-color-primary);
}
::deep(table) {
::v-deep(table) {
width: 100%;
margin: 12px 0;
border-collapse: collapse;
@@ -384,7 +384,7 @@ defineExpose({
}
.menu-item.is-disabled i:not(.submenu-arrow),
.menu-item.is-disabled ::deep(.fa-svg-icon) {
.menu-item.is-disabled ::v-deep(.fa-svg-icon) {
color: var(--el-text-color-disabled) !important;
}
@@ -352,8 +352,8 @@ const popoverContentRef = ref();
</script>
<style scoped lang="scss">
.reference ::deep(.el-input__wrapper),
.reference ::deep(.el-input__inner) {
.reference ::v-deep(.el-input__wrapper),
.reference ::v-deep(.el-input__inner) {
cursor: pointer;
}
@@ -363,7 +363,7 @@ const popoverContentRef = ref();
margin-top: 6px;
}
// 隐藏全选按钮
.radio ::deep(.el-table__header th.el-table__cell:nth-child(1) .el-checkbox) {
.radio ::v-deep(.el-table__header th.el-table__cell:nth-child(1) .el-checkbox) {
visibility: hidden;
}
</style>
@@ -464,7 +464,7 @@ const onError = (error: any) => {
}
}
::deep(.el-upload--picture-card) {
::v-deep(.el-upload--picture-card) {
position: relative;
width: v-bind("props.style.width ?? '150px'");
height: v-bind("props.style.height ?? '150px'");
@@ -7,7 +7,7 @@
margin-top: 10px;
}
::deep(.el-loading-mask) {
:deep(.el-loading-mask) {
z-index: 100;
background-color: var(--default-box-color) !important;
}
@@ -23,7 +23,7 @@
// 空状态垂直居中
&.is-empty {
::deep(.el-scrollbar__wrap) {
:deep(.el-scrollbar__wrap) {
display: flex;
}
}
@@ -32,7 +32,7 @@
display: flex;
margin-top: 13px;
::deep(.el-select) {
:deep(.el-select) {
width: 102px !important;
}
@@ -51,7 +51,7 @@
// 自定义分页组件样式
&.custom-pagination {
::deep(.el-pagination) {
:deep(.el-pagination) {
.btn-prev,
.btn-next {
background-color: transparent;
@@ -89,7 +89,7 @@
// 移动端分页
@media (width <= 640px) {
::deep(.el-pagination) {
:deep(.el-pagination) {
display: flex;
flex-wrap: wrap;
gap: 15px 0;
@@ -88,7 +88,7 @@ watchEffect(() => {
width: 100%;
height: 100%;
::deep(svg) {
::v-deep(svg) {
width: 100%;
height: 100%;
}
@@ -256,7 +256,7 @@ const changeThemeColor = (color: string) => {
transform: translateY(-2px);
}
.auth-top-bar__action:hover ::deep(.fa-svg-icon) {
.auth-top-bar__action:hover ::v-deep(.fa-svg-icon) {
color: var(--el-color-primary);
}
@@ -314,15 +314,15 @@ const changeThemeColor = (color: string) => {
}
/* 调色盘:图标颜色与当前主题主色一致(含单独悬浮、整块调色区悬浮) */
.palette-btn ::deep(.fa-svg-icon) {
.palette-btn ::v-deep(.fa-svg-icon) {
color: v-bind("themeColorForCss");
}
.auth-top-bar__action.palette-btn:hover ::deep(.fa-svg-icon) {
.auth-top-bar__action.palette-btn:hover ::v-deep(.fa-svg-icon) {
color: v-bind("themeColorForCss");
}
.color-picker-expandable:hover .palette-btn ::deep(.fa-svg-icon) {
.color-picker-expandable:hover .palette-btn ::v-deep(.fa-svg-icon) {
color: v-bind("themeColorForCss");
}
</style>