Files
MoviePilot-Frontend/src/styles/themes/glass.scss
2026-07-23 07:05:43 +08:00

1045 lines
38 KiB
SCSS
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.
/* stylelint-disable no-descending-specificity */
/* stylelint-disable scss/at-rule-no-unknown */
// 材质只覆盖统一表面 token质量档只替换光学层不改变业务组件契约。
html[data-theme='glass'] {
--glass-surface: rgba(11, 19, 34, 22%);
--glass-surface-soft: rgba(11, 19, 34, 28%);
--glass-surface-raised: rgba(11, 19, 34, 36%);
--glass-control: rgba(11, 19, 34, 52%);
--glass-control-prominent: rgba(255, 255, 255, 7%);
--glass-control-prominent-focus: color-mix(in srgb, rgba(255, 255, 255, 10%) 84%, rgba(var(--v-theme-primary), 24%));
--glass-border: rgba(255, 255, 255, 10%);
--glass-border-raised: rgba(255, 255, 255, 14%);
--glass-border-hover: rgba(255, 255, 255, 20%);
--glass-control-prominent-border: rgba(255, 255, 255, 14%);
--glass-highlight: rgba(255, 255, 255, 14%);
--glass-sheen: linear-gradient(
135deg,
rgba(255, 255, 255, 9%),
transparent 28%,
rgba(255, 255, 255, 3%) 72%,
transparent
);
--glass-shadow:
0 10px 28px rgba(3, 7, 18, 24%), inset 0 1px 0 var(--glass-highlight), inset 0 -1px 0 rgba(2, 6, 16, 14%);
--glass-shadow-raised:
0 16px 40px rgba(3, 7, 18, 32%), inset 0 1px 0 rgba(255, 255, 255, 24%), inset 0 -1px 0 rgba(2, 6, 16, 18%);
--glass-shadow-hover:
0 18px 44px rgba(3, 7, 18, 36%), inset 0 1px 0 rgba(255, 255, 255, 28%), inset 0 -1px 0 rgba(2, 6, 16, 18%);
--glass-navbar-shadow:
0 3px 12px rgba(3, 7, 18, 18%), inset 0 1px 0 rgba(255, 255, 255, 10%), inset 0 -1px 0 rgba(2, 6, 16, 12%);
--glass-control-shadow: inset 0 1px 0 rgba(255, 255, 255, 12%), inset 0 -1px 0 rgba(2, 6, 16, 14%);
--glass-control-shadow-hover: inset 0 1px 0 rgba(255, 255, 255, 18%), inset 0 -1px 0 rgba(2, 6, 16, 12%);
--glass-control-shadow-active: inset 0 1px 0 rgba(255, 255, 255, 7%), inset 0 -1px 0 rgba(2, 6, 16, 20%);
--glass-control-prominent-shadow: inset 0 1px 0 rgba(255, 255, 255, 18%), inset 0 -1px 0 rgba(2, 6, 16, 18%);
--glass-control-prominent-focus-shadow:
0 0 0 2px rgba(var(--v-theme-primary), 16%), inset 0 1px 0 rgba(255, 255, 255, 24%),
inset 0 -1px 0 rgba(2, 6, 16, 16%);
--glass-surface-backdrop-filter: none;
--glass-raised-backdrop-filter: none;
--glass-control-backdrop-filter: none;
--glass-control-prominent-backdrop-filter: none;
--glass-control-icon-color: rgba(242, 245, 250, 70%);
--glass-control-placeholder-color: rgba(242, 245, 250, 54%);
--glass-control-shortcut-background: rgba(255, 255, 255, 8%);
--glass-control-shortcut-border: rgba(255, 255, 255, 12%);
--glass-control-shortcut-color: rgba(242, 245, 250, 68%);
--glass-button-surface: rgba(255, 255, 255, 8%);
--glass-button-surface-hover: rgba(255, 255, 255, 12%);
--glass-nav-active-background: linear-gradient(
90deg,
rgba(var(--v-theme-primary), 22%),
rgba(var(--v-theme-primary), 48%)
);
--glass-nav-active-border: 1px solid rgba(var(--v-theme-primary), 36%);
--glass-nav-active-shadow: inset 0 1px 0 rgba(255, 255, 255, 14%);
--glass-dashboard-backdrop-filter: none;
--glass-blur-surface: 16px;
--glass-blur: 22px;
--glass-blur-raised: 32px;
--glass-saturate: 145%;
--glass-motion: 180ms cubic-bezier(0.2, 0.8, 0.2, 1);
--app-card-rest-shadow: var(--glass-shadow);
--app-card-hover-shadow: var(--glass-shadow-hover);
--app-fab-shadow: var(--glass-control-shadow);
--app-fab-shadow-strong: var(--glass-control-shadow-hover);
--app-fab-shadow-hover: var(--glass-control-shadow-hover);
--app-fab-shadow-strong-hover: var(--glass-control-shadow-hover);
--app-fab-shadow-active: var(--glass-control-shadow-active);
--app-overlay-shadow: var(--glass-shadow-raised);
--app-surface-shadow: var(--glass-shadow);
--app-surface-hover-shadow: var(--glass-shadow-hover);
--app-surface-border-width: 1px;
--app-surface-border-opacity: 0.15;
--app-surface-border: 1px solid var(--glass-border);
--app-card-light-border-width: 1px;
--app-card-light-border-opacity: 0.15;
--app-card-light-border: 1px solid var(--glass-border);
--app-overlay-border: 1px solid var(--glass-border);
--app-grouped-list-background: var(--glass-surface);
--app-grouped-list-backdrop-filter: var(--glass-surface-backdrop-filter);
--app-grouped-list-border: 1px solid var(--glass-border);
--app-grouped-list-separator-color: rgba(255, 255, 255, 10%);
--app-grouped-list-header-color: rgba(242, 245, 250, 68%);
--app-grouped-list-chevron-color: rgba(242, 245, 250, 56%);
--app-grouped-list-hover-background: rgba(255, 255, 255, 8%);
--app-grouped-list-active-background: rgba(var(--v-theme-primary), 16%);
--mp-motion-duration-page: 180ms;
--mp-motion-duration-overlay: 180ms;
--mp-motion-ease-standard: cubic-bezier(0.2, 0.8, 0.2, 1);
background-color: #0b1322;
color-scheme: dark;
body {
background-color: #0b1322;
}
// 色调保持与透明材质接近的透光度,只叠加主色语义。
&[data-glass-appearance='tinted'] {
--glass-surface: color-mix(in srgb, rgba(11, 19, 34, 24%) 88%, rgba(var(--v-theme-primary), 28%));
--glass-surface-soft: color-mix(in srgb, rgba(11, 19, 34, 30%) 89%, rgba(var(--v-theme-primary), 26%));
--glass-surface-raised: color-mix(in srgb, rgba(11, 19, 34, 38%) 84%, rgba(var(--v-theme-primary), 32%));
--glass-control: color-mix(in srgb, rgba(11, 19, 34, 52%) 88%, rgba(var(--v-theme-primary), 28%));
--glass-control-prominent: color-mix(in srgb, rgba(255, 255, 255, 7%) 82%, rgba(var(--v-theme-primary), 24%));
--glass-control-prominent-focus: color-mix(
in srgb,
rgba(255, 255, 255, 10%) 76%,
rgba(var(--v-theme-primary), 32%)
);
--glass-border: color-mix(in srgb, rgba(255, 255, 255, 10%) 82%, rgba(var(--v-theme-primary), 26%));
--glass-border-raised: color-mix(in srgb, rgba(255, 255, 255, 14%) 80%, rgba(var(--v-theme-primary), 30%));
--glass-border-hover: color-mix(in srgb, rgba(255, 255, 255, 20%) 78%, rgba(var(--v-theme-primary), 36%));
--glass-control-prominent-border: color-mix(
in srgb,
rgba(255, 255, 255, 14%) 78%,
rgba(var(--v-theme-primary), 32%)
);
--glass-highlight: color-mix(in srgb, rgba(255, 255, 255, 14%) 86%, rgba(var(--v-theme-primary), 18%));
--glass-sheen: linear-gradient(
135deg,
rgba(255, 255, 255, 9%),
transparent 28%,
rgba(var(--v-theme-primary), 6%) 72%,
transparent
);
}
// 磨砂材质使用更亮的散射表面,但仍只让高价值层执行实时背景采样。
&[data-glass-appearance='frosted'] {
--glass-surface: rgba(255, 255, 255, 8%);
--glass-surface-soft: rgba(255, 255, 255, 7%);
--glass-surface-raised: rgba(255, 255, 255, 12%);
--glass-control: rgba(255, 255, 255, 9%);
--glass-control-prominent: rgba(255, 255, 255, 10%);
--glass-control-prominent-focus: rgba(255, 255, 255, 13%);
--glass-border: rgba(255, 255, 255, 15%);
--glass-border-raised: rgba(255, 255, 255, 18%);
--glass-border-hover: rgba(255, 255, 255, 28%);
--glass-control-prominent-border: rgba(255, 255, 255, 18%);
--glass-highlight: rgba(255, 255, 255, 22%);
--glass-sheen: linear-gradient(
135deg,
rgba(255, 255, 255, 7%),
transparent 24%,
rgba(255, 255, 255, 2%) 72%,
transparent
);
--glass-control-prominent-shadow: inset 0 1px 0 rgba(255, 255, 255, 28%), inset 0 -1px 0 rgba(2, 6, 16, 20%);
--glass-control-prominent-focus-shadow:
0 0 0 2px rgba(var(--v-theme-primary), 17%), inset 0 1px 0 rgba(255, 255, 255, 34%),
inset 0 -1px 0 rgba(2, 6, 16, 18%);
--glass-surface-backdrop-filter: blur(var(--glass-blur-surface)) saturate(var(--glass-saturate));
--glass-raised-backdrop-filter: blur(var(--glass-blur-raised)) saturate(var(--glass-saturate));
--glass-control-prominent-backdrop-filter: blur(24px) saturate(150%);
--glass-blur-surface: 28px;
--glass-saturate: 150%;
--glass-control-icon-color: rgba(242, 245, 250, 78%);
--glass-control-placeholder-color: rgba(242, 245, 250, 62%);
--glass-control-shortcut-background: rgba(255, 255, 255, 11%);
--glass-control-shortcut-border: rgba(255, 255, 255, 16%);
--glass-control-shortcut-color: rgba(242, 245, 250, 76%);
--glass-button-surface: rgba(255, 255, 255, 10%);
--glass-button-surface-hover: rgba(255, 255, 255, 14%);
--glass-nav-active-background: linear-gradient(270deg, rgb(var(--v-theme-primary)) 0%, rgb(255, 255, 255) 300%);
--glass-nav-active-border: 0 solid transparent;
--glass-nav-active-shadow:
0 4px 14px -4px rgba(3, 7, 18, 34%), 0 4px 8px -4px rgba(3, 7, 18, 24%), 0 4px 8px -4px rgba(3, 7, 18, 16%);
--glass-dashboard-backdrop-filter: blur(var(--glass-blur-surface)) saturate(var(--glass-saturate));
}
&[data-theme-radius='none'] {
--app-theme-surface-radius: 8px;
--app-field-radius: 8px;
--app-control-radius: 8px;
--app-overlay-radius: 10px;
}
&[data-theme-radius='small'] {
--app-theme-surface-radius: 12px;
--app-field-radius: 12px;
--app-control-radius: 10px;
--app-overlay-radius: 14px;
}
&[data-theme-radius='default'] {
--app-theme-surface-radius: 20px;
--app-field-radius: 16px;
--app-control-radius: 14px;
--app-overlay-radius: 22px;
}
&[data-theme-radius='large'] {
--app-theme-surface-radius: 24px;
--app-field-radius: 20px;
--app-control-radius: 16px;
--app-overlay-radius: 26px;
}
&[data-theme-radius='extra'] {
--app-theme-surface-radius: 28px;
--app-field-radius: 24px;
--app-control-radius: 18px;
--app-overlay-radius: 30px;
}
.app-wrapper::before {
position: fixed;
z-index: 0;
background-image: url("data:image/svg+xml,%3Csvg viewBox='0 0 180 180' xmlns='http://www.w3.org/2000/svg'%3E%3Cfilter id='noise'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='.82' numOctaves='3' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23noise)' opacity='.7'/%3E%3C/svg%3E");
block-size: 100%;
content: '';
inline-size: 100%;
inset: 0;
opacity: 0.025;
pointer-events: none;
}
.v-application,
.v-layout,
.v-main,
.layout-wrapper,
.layout-content-wrapper,
.page-content-container {
background: transparent;
}
.layout-page-content {
background-color: rgba(255, 255, 255, 2.5%);
}
&[data-glass-appearance='frosted'] .layout-page-content {
background-color: transparent;
}
.v-application {
position: relative;
z-index: 1;
}
// 页面路由只使用短距离透明度与位移反馈,避免触发整页滤镜重采样。
.mp-page-route--entering {
animation: glass-page-route-enter var(--mp-motion-duration-page) var(--mp-motion-ease-standard) both;
will-change: opacity, transform;
}
@keyframes glass-page-route-enter {
from {
opacity: 0.82;
transform: translate3d(0, 2px, 0);
}
to {
opacity: 1;
transform: none;
}
}
.mp-page-enter-active,
.mp-page-leave-active {
filter: none !important;
transition:
opacity var(--mp-motion-duration-page) var(--mp-motion-ease-standard),
transform var(--mp-motion-duration-page) var(--mp-motion-ease-standard);
}
.mp-page-enter-from {
filter: none !important;
opacity: 0.82;
transform: translate3d(0, 2px, 0);
}
:where(
.app-surface:not(.no-blur),
.v-card:not(.no-blur, .bg-primary, .bg-success, .bg-info, .bg-warning, .bg-error),
.v-sheet:not(.no-blur, .bg-primary, .bg-success, .bg-info, .bg-warning, .bg-error),
.v-expansion-panel,
.v-stepper,
.v-table
) {
border-color: var(--glass-border) !important;
-webkit-backdrop-filter: var(--glass-surface-backdrop-filter);
backdrop-filter: var(--glass-surface-backdrop-filter);
background-color: var(--glass-surface) !important;
background-image: var(--glass-sheen) !important;
box-shadow: var(--glass-shadow) !important;
}
:where(.v-list, .v-footer) {
border-color: var(--glass-border);
-webkit-backdrop-filter: var(--glass-surface-backdrop-filter);
backdrop-filter: var(--glass-surface-backdrop-filter);
background-color: var(--glass-surface) !important;
}
.v-toolbar {
border-color: var(--glass-border);
-webkit-backdrop-filter: var(--glass-raised-backdrop-filter);
backdrop-filter: var(--glass-raised-backdrop-filter);
background-color: var(--glass-surface) !important;
}
// Dashboard 顶层工作卡片允许一层业务布局容器,内部图表、列表与海报只使用静态光学表面。
.dashboard-grid-item-content > .dashboard-grid-auto-size > .dashboard-grid-content-measure > .v-card,
.dashboard-grid-item-content > .dashboard-grid-auto-size > .dashboard-grid-content-measure > :first-child > .v-card {
-webkit-backdrop-filter: var(--glass-dashboard-backdrop-filter);
backdrop-filter: var(--glass-dashboard-backdrop-filter);
}
:where(
.layout-navbar,
.footer-nav-card,
.theme-customizer-panel-host,
.agent-assistant-panel,
.Vue-Toastification__toast
) {
border-color: var(--glass-border-raised) !important;
-webkit-backdrop-filter: var(--glass-raised-backdrop-filter);
backdrop-filter: var(--glass-raised-backdrop-filter);
background-color: var(--glass-surface-raised) !important;
background-image: var(--glass-sheen) !important;
box-shadow: var(--glass-shadow-raised) !important;
}
// 顶栏使用更轻的投影,避免与下方内容形成内陷感。
.layout-navbar {
box-shadow: var(--glass-navbar-shadow) !important;
}
.layout-vertical-nav {
isolation: isolate;
border-inline-end: 0;
-webkit-backdrop-filter: none;
backdrop-filter: none;
background: transparent !important;
box-shadow: none !important;
// 导航材质与可变菜单内容分层,路由激活态切换不应重栅格化整块全高背板。
&::before {
position: absolute;
z-index: -1;
border-inline-end: 1px solid var(--glass-border-raised);
-webkit-backdrop-filter: var(--glass-raised-backdrop-filter);
backdrop-filter: var(--glass-raised-backdrop-filter);
background-color: var(--glass-surface-raised);
background-image: var(--glass-sheen);
box-shadow: var(--glass-shadow-raised);
content: '';
inset: 0;
pointer-events: none;
}
}
// 滚动条与导航材质边界保持间距,避免窄轨道参与全高背板的合成。
.layout-vertical-nav .ps__rail-y {
inset-inline-end: 0.5rem !important;
transition: opacity 120ms linear;
}
.layout-vertical-nav .ps__thumb-y,
.layout-vertical-nav .ps__rail-y:focus > .ps__thumb-y,
.layout-vertical-nav .ps__rail-y:hover > .ps__thumb-y,
.layout-vertical-nav .ps__rail-y.ps--clicking .ps__thumb-y {
background-color: rgba(255, 255, 255, 28%) !important;
inline-size: 2px !important;
inset-inline-end: 0.1875rem;
}
.layout-vertical-nav .nav-items.ps--scrolling-y > .ps__rail-y {
opacity: 0.42;
}
.layout-vertical-nav .nav-link > .router-link-exact-active {
border: var(--glass-nav-active-border);
background: var(--glass-nav-active-background) !important;
box-shadow: var(--glass-nav-active-shadow) !important;
}
.layout-wrapper.window-scrolled.layout-navbar-fixed .layout-navbar,
.layout-wrapper.layout-horizontal-nav-active.layout-horizontal-nav-scrolled.layout-navbar-fixed .layout-navbar {
border-color: var(--glass-border) !important;
-webkit-backdrop-filter: var(--glass-raised-backdrop-filter) !important;
backdrop-filter: var(--glass-raised-backdrop-filter) !important;
background-color: var(--glass-surface-raised) !important;
background-image: var(--glass-sheen) !important;
box-shadow: var(--glass-navbar-shadow) !important;
}
.layout-wrapper.window-scrolled.layout-navbar-fixed .layout-navbar .navbar-content-container,
.layout-wrapper.layout-horizontal-nav-active.layout-horizontal-nav-scrolled.layout-navbar-fixed
.navbar-content-container {
-webkit-backdrop-filter: none !important;
backdrop-filter: none !important;
background: transparent !important;
box-shadow: none !important;
}
:where(.search-desktop-activator, .search-header) .search-input-wrapper {
border: 1px solid var(--glass-control-prominent-border) !important;
-webkit-backdrop-filter: var(--glass-control-prominent-backdrop-filter);
backdrop-filter: var(--glass-control-prominent-backdrop-filter);
background-color: var(--glass-control-prominent) !important;
background-image: var(--glass-sheen) !important;
box-shadow: var(--glass-control-prominent-shadow);
}
:where(.search-desktop-activator, .search-header) .search-input-wrapper:focus-within {
border-color: rgba(var(--v-theme-primary), 70%) !important;
background: var(--glass-control-prominent-focus) !important;
box-shadow: var(--glass-control-prominent-focus-shadow);
}
:where(.search-desktop-activator, .search-header) .search-input-icon {
color: var(--glass-control-icon-color) !important;
}
:where(.search-desktop-activator, .search-header) .search-native-input::placeholder {
color: var(--glass-control-placeholder-color);
}
:where(.search-desktop-activator, .search-header) .search-shortcut-badge {
border: 1px solid var(--glass-control-shortcut-border);
background: var(--glass-control-shortcut-background);
color: var(--glass-control-shortcut-color);
}
.theme-customizer-panel,
.agent-assistant-shell {
background-color: transparent !important;
}
:where(.theme-customizer-border-scene, .theme-customizer-radius-scene) {
border-color: var(--glass-border) !important;
background:
linear-gradient(180deg, rgba(255, 255, 255, 4%), rgba(255, 255, 255, 7%)), rgba(255, 255, 255, 3%) !important;
box-shadow:
inset 0 1px 0 rgba(255, 255, 255, 12%),
inset 0 -1px 0 rgba(2, 6, 16, 18%);
}
:where(
.theme-customizer-border-scene__card,
.theme-customizer-border-scene__dialog,
.theme-customizer-border-scene__menu,
.theme-customizer-radius-scene__card
) {
border-color: rgba(255, 255, 255, 18%);
background: rgba(255, 255, 255, 7%) !important;
box-shadow:
inset 0 1px 0 rgba(255, 255, 255, 14%),
inset 0 -1px 0 rgba(2, 6, 16, 20%);
}
.theme-customizer-preview-option.is-active > :where(.theme-customizer-border-scene, .theme-customizer-radius-scene) {
border-color: rgb(var(--v-theme-primary)) !important;
background: rgba(var(--v-theme-primary), 8%) !important;
}
.agent-assistant-shell {
--agent-assistant-panel-bg: var(--glass-surface-raised);
--agent-assistant-panel-blur: var(--glass-blur-raised);
--agent-assistant-assistant-bg: var(--glass-surface);
}
.agent-assistant-fab__bubble,
.nav-button,
.compact-fab .v-btn,
.global-action-buttons .v-btn {
border: 1px solid var(--glass-border) !important;
-webkit-backdrop-filter: var(--glass-raised-backdrop-filter);
backdrop-filter: var(--glass-raised-backdrop-filter);
background-color: var(--glass-surface-raised) !important;
background-image: var(--glass-sheen) !important;
box-shadow: var(--glass-control-shadow) !important;
}
.v-overlay__scrim {
-webkit-backdrop-filter: var(--glass-surface-backdrop-filter);
backdrop-filter: var(--glass-surface-backdrop-filter);
background: rgba(3, 7, 18, 48%);
}
.v-dialog--fullscreen {
background-color: transparent !important;
}
.v-overlay__content {
border-radius: var(--app-overlay-radius);
> :where(.v-card, .v-sheet, .v-list) {
-webkit-backdrop-filter: var(--glass-raised-backdrop-filter) !important;
backdrop-filter: var(--glass-raised-backdrop-filter) !important;
background-color: var(--glass-surface-raised) !important;
background-image: var(--glass-sheen) !important;
box-shadow: var(--glass-shadow-raised) !important;
}
}
.v-tooltip > .v-overlay__content,
.v-snackbar__wrapper {
border: 1px solid var(--glass-border);
-webkit-backdrop-filter: var(--glass-raised-backdrop-filter);
backdrop-filter: var(--glass-raised-backdrop-filter);
background: rgba(11, 19, 34, 76%) !important;
box-shadow: var(--glass-shadow);
}
.v-field {
--v-field-border-opacity: 0.14;
--v-field-border-width: 1px;
border-radius: var(--app-field-radius);
-webkit-backdrop-filter: var(--glass-control-backdrop-filter);
backdrop-filter: var(--glass-control-backdrop-filter);
background-color: var(--glass-control) !important;
box-shadow: inset 0 1px 0 rgba(255, 255, 255, 8%);
transition:
background-color var(--glass-motion),
box-shadow var(--glass-motion);
}
.v-field--focused {
--v-field-border-opacity: 0.32;
background-color: color-mix(in srgb, var(--glass-control) 84%, rgba(var(--v-theme-primary), 32%)) !important;
background-image: none !important;
box-shadow:
0 0 0 3px rgba(var(--v-theme-primary), 14%),
inset 0 1px 0 rgba(255, 255, 255, 10%);
}
// Outlined 描边自身会为浮动标签留出缺口,移除贯穿整个顶部的 field 阴影线。
.v-field.v-field--variant-outlined {
box-shadow: inset 0 -1px 0 rgba(2, 6, 16, 22%);
}
.v-field.v-field--variant-underlined,
.v-field.v-field--variant-plain {
border-radius: 0;
-webkit-backdrop-filter: none;
backdrop-filter: none;
background-color: transparent !important;
box-shadow: none !important;
}
.v-field.v-field--variant-underlined.v-field--focused,
.v-field.v-field--variant-plain.v-field--focused {
background-color: transparent !important;
box-shadow: none !important;
}
.v-field input::placeholder,
.v-field textarea::placeholder {
color: rgba(242, 245, 250, 38%);
opacity: 1;
}
.v-btn {
letter-spacing: 0;
transition:
background-color var(--glass-motion),
border-color var(--glass-motion),
box-shadow var(--glass-motion);
}
.v-btn:not(.v-btn--variant-text, .v-btn--variant-plain) {
border: 1px solid var(--glass-border);
-webkit-backdrop-filter: var(--glass-control-backdrop-filter);
backdrop-filter: var(--glass-control-backdrop-filter);
background-color: var(--glass-button-surface) !important;
background-image: none !important;
box-shadow: var(--glass-control-shadow) !important;
}
.v-btn.bg-primary {
border-color: rgba(var(--v-theme-primary), 48%);
background-color: rgba(var(--v-theme-primary), 34%) !important;
}
.v-btn.bg-success {
border-color: rgba(var(--v-theme-success), 48%);
background-color: rgba(var(--v-theme-success), 34%) !important;
}
.v-btn.bg-info {
border-color: rgba(var(--v-theme-info), 48%);
background-color: rgba(var(--v-theme-info), 34%) !important;
}
.v-btn.bg-warning {
border-color: rgba(var(--v-theme-warning), 48%);
background-color: rgba(var(--v-theme-warning), 34%) !important;
}
.v-btn.bg-error {
border-color: rgba(var(--v-theme-error), 48%);
background-color: rgba(var(--v-theme-error), 34%) !important;
}
:where(.v-btn, .v-card--link, [role='button']):focus-visible {
outline: 0;
box-shadow:
0 0 0 3px rgba(var(--v-theme-primary), 18%),
var(--glass-control-shadow) !important;
}
.v-chip {
border-color: rgba(255, 255, 255, 16%);
background-color: rgba(255, 255, 255, 7%);
}
.v-table {
.v-table__wrapper > table > thead {
background-color: rgba(255, 255, 255, 6%);
}
.v-table__wrapper > table > tbody > tr:hover > td {
background-color: rgba(255, 255, 255, 6%);
}
}
.v-skeleton-loader {
background-color: var(--glass-surface-soft);
}
.app-card-colorful {
--app-card-accent-start-opacity: 0.018;
--app-card-accent-end-opacity: 0.008;
--app-card-border-opacity: 0.15;
--app-card-hover-border-opacity: 0.28;
--app-card-stripe-opacity: 0.12;
--app-card-surface-opacity: 0.08;
-webkit-backdrop-filter: var(--glass-surface-backdrop-filter);
backdrop-filter: var(--glass-surface-backdrop-filter);
}
// 文件整理、日历和缓存使用自定义容器,需要同时覆盖桌面与移动端表面。
.transfer-history-mobile-page {
--transfer-history-mobile-search-bg: var(--glass-surface-soft);
--transfer-history-mobile-muted-bg: var(--glass-surface-soft);
--transfer-history-mobile-border: var(--glass-border);
--transfer-history-mobile-surface-blur: var(--glass-surface-backdrop-filter);
}
.transfer-history-mobile-record,
.calendar-event-card,
.mobile-calendar-filter-card,
.mobile-calendar-event-card,
.cache-desktop-stat,
.cache-mobile-stat,
.cache-mobile-card,
.cache-panel-stat,
.recognition-cache-mobile-item {
border: 1px solid var(--glass-border);
-webkit-backdrop-filter: var(--glass-surface-backdrop-filter);
backdrop-filter: var(--glass-surface-backdrop-filter);
background: var(--glass-surface);
}
// 日志和定时服务的自定义表面通过变量接入主题,避免组件局部样式覆盖玻璃材质。
.logging-view,
.logging-view.is-dark-theme {
--logging-border: var(--glass-border);
--logging-record-bg-even: rgba(255, 255, 255, 6%);
--logging-record-bg-odd: rgba(255, 255, 255, 3%);
--logging-shadow: inset 0 1px 0 rgba(255, 255, 255, 10%);
--logging-shell-backdrop-filter: var(--glass-surface-backdrop-filter);
--logging-shell-background: var(--glass-surface-soft);
}
.mobile-scheduler-view {
--mobile-scheduler-card-backdrop-filter: var(--glass-surface-backdrop-filter);
--mobile-scheduler-card-background: var(--glass-surface);
--mobile-scheduler-card-border: 1px solid var(--glass-border);
--mobile-scheduler-card-shadow: var(--glass-shadow);
}
.mobile-subscribe-calendar {
--mobile-calendar-control-bg: var(--glass-surface-soft);
--mobile-calendar-placeholder-bg: var(--glass-surface-soft);
--mobile-calendar-surface-blur: var(--glass-surface-backdrop-filter);
}
// 磨砂卡片不参与仪表板整体透明度入场,避免合成层切换造成先透明后模糊的闪变。
&[data-glass-appearance='frosted'] .dashboard-grid {
opacity: 1;
transform: none;
transition: none;
}
// 用户权限编辑器由普通容器构成,通过主题变量接入玻璃表面材质。
.user-permission-editor {
--permission-editor-border: 1px solid var(--glass-border);
--permission-editor-muted-border: 1px solid rgba(255, 255, 255, 10%);
--permission-editor-panel-bg: var(--glass-surface-soft);
--permission-editor-hover-bg: rgba(255, 255, 255, 8%);
--permission-editor-active-bg: rgba(var(--v-theme-primary), 16%);
--permission-editor-selected-bg: rgba(var(--v-theme-primary), 12%);
--permission-editor-backdrop-filter: none;
--permission-editor-shadow: inset 0 1px 0 rgba(255, 255, 255, 8%);
}
// 智能助手折叠区使用均匀的玻璃描边,替换普通主题渐变产生的顶部黑边。
.ai-agent-settings-card {
border: 1px solid rgba(255, 255, 255, 10%) !important;
-webkit-backdrop-filter: var(--glass-surface-backdrop-filter) !important;
backdrop-filter: var(--glass-surface-backdrop-filter) !important;
background: var(--glass-surface-soft) !important;
box-shadow: none !important;
}
// 横向榜单的滚动容器需要完整容纳玻璃卡片向上下扩散的阴影。
.slider-container {
--slider-shadow-bleed-start: 48px;
--slider-shadow-bleed-end: 96px;
--slider-shadow-bleed-inline: 32px;
}
:where(.v-card, .v-sheet) :where(.app-surface, .v-card, .v-sheet, .v-list, .v-table, .v-expansion-panel, .v-stepper) {
border-color: transparent !important;
-webkit-backdrop-filter: none;
backdrop-filter: none;
box-shadow: none !important;
will-change: auto;
}
:where(.v-card, .v-sheet)
:where(
.app-surface:not(.bg-primary, .bg-success, .bg-info, .bg-warning, .bg-error),
.v-card:not(.bg-primary, .bg-success, .bg-info, .bg-warning, .bg-error),
.v-sheet:not(.bg-primary, .bg-success, .bg-info, .bg-warning, .bg-error),
.v-list,
.v-table,
.v-expansion-panel,
.v-stepper
) {
background-color: transparent !important;
}
@media (hover: hover) and (pointer: fine) {
.v-btn:not(.v-btn--variant-text, .v-btn--variant-plain):hover {
border-color: var(--glass-border-hover);
background-color: var(--glass-button-surface-hover) !important;
box-shadow: var(--glass-control-shadow-hover) !important;
}
.v-btn.bg-primary:hover {
border-color: rgba(var(--v-theme-primary), 62%);
background-color: rgba(var(--v-theme-primary), 42%) !important;
}
.v-btn.bg-success:hover {
border-color: rgba(var(--v-theme-success), 62%);
background-color: rgba(var(--v-theme-success), 42%) !important;
}
.v-btn.bg-info:hover {
border-color: rgba(var(--v-theme-info), 62%);
background-color: rgba(var(--v-theme-info), 42%) !important;
}
.v-btn.bg-warning:hover {
border-color: rgba(var(--v-theme-warning), 62%);
background-color: rgba(var(--v-theme-warning), 42%) !important;
}
.v-btn.bg-error:hover {
border-color: rgba(var(--v-theme-error), 62%);
background-color: rgba(var(--v-theme-error), 42%) !important;
}
.v-card--link:hover {
border-color: var(--glass-border-hover) !important;
box-shadow: var(--glass-shadow-hover) !important;
}
}
.v-btn:not(.v-btn--variant-text, .v-btn--variant-plain):active {
box-shadow: var(--glass-control-shadow-active) !important;
}
@media (width <= 960px) {
// 全屏快捷弹窗释放外层玻璃背景,让定时服务卡片直接采样全局壁纸。
.scheduler-shortcut-dialog-card {
-webkit-backdrop-filter: none !important;
backdrop-filter: none !important;
background: transparent !important;
box-shadow: none !important;
}
}
@supports not ((-webkit-backdrop-filter: blur(1px)) or (backdrop-filter: blur(1px))) {
:where(
.app-surface,
.v-card,
.v-sheet,
.v-list,
.v-toolbar,
.v-expansion-panel,
.layout-vertical-nav,
.layout-navbar,
.theme-customizer-panel-host,
.agent-assistant-panel
) {
background-color: rgba(18, 28, 45, 94%) !important;
}
}
@media (prefers-reduced-transparency: reduce) {
:where(
.app-surface,
.v-card,
.v-sheet,
.v-list,
.v-toolbar,
.layout-vertical-nav,
.layout-navbar,
.v-overlay__content
) {
-webkit-backdrop-filter: none !important;
backdrop-filter: none !important;
background-color: rgba(11, 19, 34, 94%) !important;
}
}
@media (prefers-reduced-motion: reduce) {
.v-btn,
.v-card,
.v-field,
.background-image {
transition-duration: 0.01ms !important;
}
}
}
// 光学档位只在 renderer ready 后接管背景采样,加载与失败状态继续使用标准 CSS 材质。
.glass-optical-layer {
position: fixed;
z-index: 0;
block-size: 100%;
inline-size: 100%;
inset: 0;
opacity: 0;
pointer-events: none;
transition: opacity 180ms ease-out;
}
// 壁纸交叉淡入期间停用折射输出,避免新纹理采样仍在混合的背景。
.glass-optical-layer--background-transition {
opacity: 0 !important;
}
// 登录卡片的壁纸副本与外层背景共享切换时序,避免卡片内部提前显示下一张图片。
html[data-theme='glass'] .app-wrapper--background-transition .login-card__wallpaper-refraction {
opacity: 0 !important;
}
html:is([data-glass-quality='balanced'], [data-glass-quality='high'])[data-glass-renderer-state='ready']
.glass-optical-layer {
opacity: 1;
}
html:is([data-glass-quality='balanced'], [data-glass-quality='high'])[data-glass-renderer-state='ready']
body[data-theme='glass'] {
.layout-vertical-nav::before,
.layout-navbar {
-webkit-backdrop-filter: var(--glass-surface-backdrop-filter) !important;
backdrop-filter: var(--glass-surface-backdrop-filter) !important;
}
.v-overlay__content > :where(.v-card, .v-sheet, .v-list) {
-webkit-backdrop-filter: var(--glass-surface-backdrop-filter) !important;
backdrop-filter: var(--glass-surface-backdrop-filter) !important;
}
.dashboard-grid-item-content > .dashboard-grid-auto-size > .dashboard-grid-content-measure > .v-card,
.dashboard-grid-item-content > .dashboard-grid-auto-size > .dashboard-grid-content-measure > :first-child > .v-card {
-webkit-backdrop-filter: none !important;
backdrop-filter: none !important;
}
}
// 磨砂材质的散射由 renderer 与有限的局部扩散共同构成。
html[data-glass-appearance='frosted']:is(
[data-glass-quality='balanced'],
[data-glass-quality='high']
)[data-glass-renderer-state='ready']
body[data-theme='glass'] {
.layout-vertical-nav::before,
.layout-navbar,
.v-overlay__content > :where(.v-card, .v-sheet, .v-list) {
-webkit-backdrop-filter: blur(18px) saturate(145%) !important;
backdrop-filter: blur(18px) saturate(145%) !important;
}
.dashboard-grid-item-content > .dashboard-grid-auto-size > .dashboard-grid-content-measure > .v-card,
.dashboard-grid-item-content > .dashboard-grid-auto-size > .dashboard-grid-content-measure > :first-child > .v-card {
-webkit-backdrop-filter: blur(24px) saturate(150%) !important;
backdrop-filter: blur(24px) saturate(150%) !important;
}
}
// 登录页只有一个高价值表面,三档质量共用局部实时材质,避免整屏 renderer 重复采样跨域壁纸。
html[data-theme='glass'] body[data-theme='glass'] {
.login-card {
box-shadow:
inset 0 0 0 1px rgba(255, 255, 255, 0.16),
inset 0 1px 0 rgba(255, 255, 255, 0.2),
0 24px 64px rgba(1, 6, 15, 0.22) !important;
}
.login-card__glass {
-webkit-backdrop-filter: var(--glass-surface-backdrop-filter) !important;
backdrop-filter: var(--glass-surface-backdrop-filter) !important;
background:
radial-gradient(
220px 190px at var(--login-card-light-x) var(--login-card-light-y),
rgba(255, 255, 255, 0.13),
rgba(var(--v-theme-primary), 0.045) 42%,
transparent 76%
),
linear-gradient(145deg, rgba(255, 255, 255, 0.1), transparent 36%), rgba(var(--v-theme-surface), 0.28) !important;
}
.login-card__wallpaper-refraction {
display: block;
background-attachment: fixed;
background-image: var(--login-wallpaper-image);
background-position: calc(50% + var(--login-refraction-shift-x)) calc(50% + var(--login-refraction-shift-y));
background-repeat: no-repeat;
background-size: cover;
filter: url('#login-liquid-refraction-clear') saturate(1.22) contrast(1.06) brightness(1.04);
opacity: 0.48;
transform: scale(1.025);
transition:
background-position 90ms linear,
opacity 180ms ease-out;
}
.login-card__glass-caustic {
inset-block-start: calc(var(--login-card-light-y) - 88px);
inset-inline-start: calc(var(--login-card-light-x) - 112px);
mix-blend-mode: screen;
opacity: calc(var(--optical-glass-caustic-opacity) + 0.12);
transform: scale(calc(var(--optical-glass-caustic-scale) + 0.08));
transition:
inset-block-start 90ms linear,
inset-inline-start 90ms linear,
opacity 160ms ease-out,
transform 180ms ease-out;
}
.native-login-field {
border-color: rgba(255, 255, 255, 0.15);
background: rgba(7, 16, 28, 0.2);
-webkit-backdrop-filter: var(--glass-control-backdrop-filter);
backdrop-filter: var(--glass-control-backdrop-filter);
}
}
html[data-theme='glass'][data-glass-appearance='tinted'] body[data-theme='glass'] {
.login-card__glass {
background:
radial-gradient(
220px 190px at var(--login-card-light-x) var(--login-card-light-y),
rgba(255, 255, 255, 0.13),
rgba(var(--v-theme-primary), 0.1) 44%,
transparent 76%
),
linear-gradient(145deg, rgba(255, 255, 255, 0.1), transparent 36%),
linear-gradient(rgba(var(--v-theme-primary), 0.1), rgba(var(--v-theme-primary), 0.04)),
rgba(var(--v-theme-surface), 0.28) !important;
}
.login-card__wallpaper-refraction {
filter: url('#login-liquid-refraction-clear') saturate(1.22) contrast(1.06) brightness(1.04);
opacity: 0.48;
}
.native-login-field {
border-color: rgba(255, 255, 255, 0.15);
background:
linear-gradient(rgba(var(--v-theme-primary), 0.07), rgba(var(--v-theme-primary), 0.07)), rgba(7, 16, 28, 0.2);
}
}
html[data-theme='glass'][data-glass-appearance='frosted'] body[data-theme='glass'] {
.login-card {
box-shadow: var(--glass-shadow-raised) !important;
}
.login-card__glass {
-webkit-backdrop-filter: var(--glass-raised-backdrop-filter) !important;
backdrop-filter: var(--glass-raised-backdrop-filter) !important;
background-color: var(--glass-surface-raised) !important;
background-image: var(--glass-sheen) !important;
}
.login-card__glass::after {
position: absolute;
z-index: 1;
background-color: rgba(255, 255, 255, 0.08);
background-image: var(--glass-sheen);
box-shadow:
inset 0 1px 0 rgba(255, 255, 255, 0.22),
inset 0 -1px 0 rgba(2, 6, 16, 0.16);
content: '';
inset: 0;
}
// 登录页位于独立合成边界,壁纸副本用于恢复导航表面的背景采样语义。
.login-card__wallpaper-refraction {
display: block;
background-image: linear-gradient(rgba(6, 10, 19, 0.3), rgba(6, 10, 19, 0.58)), var(--login-wallpaper-image);
background-attachment: fixed, fixed;
background-position:
center,
calc(50% + var(--login-refraction-shift-x)) calc(50% + var(--login-refraction-shift-y));
background-repeat: no-repeat;
background-size: cover;
filter: blur(52px) brightness(0.76) saturate(0.72);
opacity: 0.94;
transform: scale(1.24);
}
.login-card__glass-caustic {
opacity: calc(var(--optical-glass-caustic-opacity) + 0.08);
}
.native-login-field {
border-color: var(--glass-control-prominent-border);
background: var(--glass-control-prominent);
-webkit-backdrop-filter: var(--glass-control-prominent-backdrop-filter);
backdrop-filter: var(--glass-control-prominent-backdrop-filter);
box-shadow: var(--glass-control-prominent-shadow);
}
}
@media (prefers-reduced-motion: reduce) {
.glass-optical-layer {
transition: none;
}
}