ソースを参照

fix: 修复代码编辑器,以及工具栏;部分提交

lj1559651600@163.com 3 日 前
コミット
0ecdfda3c8
1 ファイル変更79 行追加0 行削除
  1. 79 0
      apps/web/src/utils/useLocalEditorTheme.ts

+ 79 - 0
apps/web/src/utils/useLocalEditorTheme.ts

@@ -0,0 +1,79 @@
+/*
+ * @Author: liuJie
+ * @Date: 2026-01-30 19:47:19
+ * @LastEditors: liuJie
+ * @LastEditTime: 2026-01-30 20:20:59
+ * @Describe: 单独抽离换肤
+ */
+import { ref, onMounted, onBeforeUnmount } from 'vue'
+import * as monaco from 'monaco-editor'
+
+type EditorTheme = 'vs-light' | 'vs-dark'
+type ThemeClass = 'light' | 'dark'
+
+interface UseLocalEditorThemeOptions {
+    defaultTheme?: EditorTheme
+    autoToggleTheme?: boolean
+}
+
+export function useLocalEditorTheme(
+    options: UseLocalEditorThemeOptions = {}
+) {
+    const {
+        defaultTheme = 'vs-light',
+        autoToggleTheme = false
+    } = options
+
+    /** 当前 Monaco 主题(语法) */
+    const monacoTheme = ref<EditorTheme>(defaultTheme)
+
+    /** 当前 UI 主题(样式) */
+    const themeClass = ref<ThemeClass>(
+        defaultTheme === 'vs-dark' ? 'dark' : 'light'
+    )
+
+    /** 系统暗黑监听 */
+    let mediaQuery: MediaQueryList | null = null
+
+    const applyTheme = (theme: EditorTheme) => {
+        monacoTheme.value = theme
+        themeClass.value = theme === 'vs-dark' ? 'dark' : 'light'
+
+        monaco.editor.setTheme(theme)
+    }
+
+    /** 手动切换 */
+    const toggleTheme = () => {
+        applyTheme(
+            monacoTheme.value === 'vs-light' ? 'vs-dark' : 'vs-light'
+        )
+    }
+
+    /** 系统主题变化 */
+    const handleSystemThemeChange = (e: MediaQueryListEvent) => {
+        applyTheme(e.matches ? 'vs-dark' : 'vs-light')
+    }
+
+    onMounted(() => {
+        applyTheme(defaultTheme)
+
+        if (autoToggleTheme) {
+            mediaQuery = window.matchMedia('(prefers-color-scheme: dark)')
+            applyTheme(mediaQuery.matches ? 'vs-dark' : 'vs-light')
+            mediaQuery.addEventListener('change', handleSystemThemeChange)
+        }
+    })
+
+    onBeforeUnmount(() => {
+        if (mediaQuery) {
+            mediaQuery.removeEventListener('change', handleSystemThemeChange)
+        }
+    })
+
+    return {
+        monacoTheme,
+        themeClass,
+        toggleTheme,
+        setTheme: applyTheme
+    }
+}