diff --git a/src/components/common/dark-mode-switch.vue b/src/components/common/dark-mode-switch.vue index 3342c484..1e78337b 100644 --- a/src/components/common/dark-mode-switch.vue +++ b/src/components/common/dark-mode-switch.vue @@ -34,32 +34,35 @@ const darkMode = computed({ } }); -function handleSwitch(event: MouseEvent) { +async function handleSwitch(event: MouseEvent) { const x = event.clientX; const y = event.clientY; - const endRadius = Math.hypot(Math.max(x, innerWidth - x), Math.max(y, innerHeight - y)); - // @ts-expect-error: Transition API + if (!document.startViewTransition) { darkMode.value = !darkMode.value; return; } - // @ts-expect-error: Transition API + + const endRadius = Math.hypot(Math.max(x, innerWidth - x), Math.max(y, innerHeight - y)); + const transition = document.startViewTransition(() => { darkMode.value = !darkMode.value; }); - transition.ready.then(() => { - const clipPath = [`circle(0px at ${x}px ${y}px)`, `circle(${endRadius}px at ${x}px ${y}px)`]; - document.documentElement.animate( - { - clipPath: darkMode.value ? clipPath : [...clipPath].reverse() - }, - { - duration: 300, - easing: 'ease-in', - pseudoElement: darkMode.value ? '::view-transition-new(root)' : '::view-transition-old(root)' - } - ); - }); + + await transition.ready; + + const clipPath = [`circle(0px at ${x}px ${y}px)`, `circle(${endRadius}px at ${x}px ${y}px)`]; + + document.documentElement.animate( + { + clipPath: darkMode.value ? clipPath : [...clipPath].reverse() + }, + { + duration: 300, + easing: 'ease-in', + pseudoElement: darkMode.value ? '::view-transition-new(root)' : '::view-transition-old(root)' + } + ); } diff --git a/src/typings/global.d.ts b/src/typings/global.d.ts index a2f4eeb9..2d8b47ff 100644 --- a/src/typings/global.d.ts +++ b/src/typings/global.d.ts @@ -5,6 +5,14 @@ interface Window { $notification?: import('naive-ui').NotificationProviderInst; } +interface ViewTransition { + ready: Promise; +} + +interface Document { + startViewTransition?: (callback: () => Promise | void) => ViewTransition; +} + /** 通用类型 */ declare namespace Common { /**