release: v0.5.0 — 升级 MetonaEditor 0.4.0 / MetonaToast 0.5.0,数据库迁移 MetonaSqlark 0.4.1

- 编辑器升级 0.4.0:TypeScript 全模块重构、启用浮动格式工具栏
- 通知升级 0.5.0:钩子系统、新增动画
- 移除 Dexie.js,迁移至 MetonaSqlark 0.4.1(AriaEngine:LSM-Tree + WAL + MVCC)
- 数据库更换为 MarkLiteV2,旧 Dexie 数据放弃
- 修复 Editor 组件无条件重渲染(getActiveTab 返回新引用)
- 更新关于弹框、README、DESIGN 文档
This commit is contained in:
thzxx
2026-08-09 15:45:36 +08:00
parent d6ae9e3c8e
commit 20eb39efc5
47 changed files with 4981 additions and 3050 deletions
+56 -56
View File
@@ -1,56 +1,56 @@
import { create } from 'zustand'
import type { ViewMode, ThemeMode } from '../types/settings'
import type { MarkdownEditor } from '@metona-team/metona-editor'
// Module-level getter for the MetonaEditor instance
// Used by OutlinePanel for heading navigation
let _getEditor: (() => MarkdownEditor | null) | null = null
export function setMetonaEditorGetter(fn: () => MarkdownEditor | null) {
_getEditor = fn
}
export function getMetonaEditor(): MarkdownEditor | null {
return _getEditor ? _getEditor() : null
}
const THEME_CYCLE: ThemeMode[] = ['light', 'dark', 'warm']
interface EditorState {
viewMode: ViewMode
themeMode: ThemeMode
// AR-03: 外部修改检测状态,替代 DOM CustomEvent
externallyModified: { filePath: string } | null
// UX-02: 全局加载状态
loadingStates: Record<string, boolean>
setViewMode: (mode: ViewMode) => void
setThemeMode: (mode: ThemeMode) => void
cycleTheme: () => ThemeMode
setExternallyModified: (info: { filePath: string } | null) => void
// UX-02: 加载状态管理
setLoading: (key: string, loading: boolean) => void
isLoading: (key: string) => boolean
}
export const useEditorStore = create<EditorState>((set, get) => ({
viewMode: 'editor',
themeMode: 'light',
externallyModified: null,
loadingStates: {},
setViewMode: (mode: ViewMode) => set({ viewMode: mode }),
setThemeMode: (mode: ThemeMode) => set({ themeMode: mode }),
cycleTheme: () => {
const current = get().themeMode
const idx = THEME_CYCLE.indexOf(current)
const next = THEME_CYCLE[(idx + 1) % THEME_CYCLE.length]
set({ themeMode: next })
return next
},
setExternallyModified: (info: { filePath: string } | null) => set({ externallyModified: info }),
setLoading: (key: string, loading: boolean) => set(state => ({
loadingStates: { ...state.loadingStates, [key]: loading }
})),
isLoading: (key: string) => get().loadingStates[key] ?? false
}))
import { create } from 'zustand'
import type { ViewMode, ThemeMode } from '../types/settings'
import type { MarkdownEditor } from '@metona-team/metona-editor'
// Module-level getter for the MetonaEditor instance
// Used by OutlinePanel for heading navigation
let _getEditor: (() => MarkdownEditor | null) | null = null
export function setMetonaEditorGetter(fn: () => MarkdownEditor | null) {
_getEditor = fn
}
export function getMetonaEditor(): MarkdownEditor | null {
return _getEditor ? _getEditor() : null
}
const THEME_CYCLE: ThemeMode[] = ['light', 'dark', 'warm']
interface EditorState {
viewMode: ViewMode
themeMode: ThemeMode
// AR-03: 外部修改检测状态,替代 DOM CustomEvent
externallyModified: { filePath: string } | null
// UX-02: 全局加载状态
loadingStates: Record<string, boolean>
setViewMode: (mode: ViewMode) => void
setThemeMode: (mode: ThemeMode) => void
cycleTheme: () => ThemeMode
setExternallyModified: (info: { filePath: string } | null) => void
// UX-02: 加载状态管理
setLoading: (key: string, loading: boolean) => void
isLoading: (key: string) => boolean
}
export const useEditorStore = create<EditorState>((set, get) => ({
viewMode: 'editor',
themeMode: 'light',
externallyModified: null,
loadingStates: {},
setViewMode: (mode: ViewMode) => set({ viewMode: mode }),
setThemeMode: (mode: ThemeMode) => set({ themeMode: mode }),
cycleTheme: () => {
const current = get().themeMode
const idx = THEME_CYCLE.indexOf(current)
const next = THEME_CYCLE[(idx + 1) % THEME_CYCLE.length]
set({ themeMode: next })
return next
},
setExternallyModified: (info: { filePath: string } | null) => set({ externallyModified: info }),
setLoading: (key: string, loading: boolean) => set(state => ({
loadingStates: { ...state.loadingStates, [key]: loading }
})),
isLoading: (key: string) => get().loadingStates[key] ?? false
}))