diff --git a/frontend/bindings/github.com/wailsapp/wails/v3/pkg/application/index.ts b/frontend/bindings/github.com/wailsapp/wails/v3/pkg/application/index.ts new file mode 100644 index 0000000..c9d993a --- /dev/null +++ b/frontend/bindings/github.com/wailsapp/wails/v3/pkg/application/index.ts @@ -0,0 +1,4 @@ +// Cynhyrchwyd y ffeil hon yn awtomatig. PEIDIWCH Â MODIWL +// This file is automatically generated. DO NOT EDIT + +export * from "./models.js"; diff --git a/frontend/bindings/github.com/wailsapp/wails/v3/pkg/application/models.ts b/frontend/bindings/github.com/wailsapp/wails/v3/pkg/application/models.ts new file mode 100644 index 0000000..8f62500 --- /dev/null +++ b/frontend/bindings/github.com/wailsapp/wails/v3/pkg/application/models.ts @@ -0,0 +1,69 @@ +// Cynhyrchwyd y ffeil hon yn awtomatig. PEIDIWCH Â MODIWL +// This file is automatically generated. DO NOT EDIT + +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore: Unused imports +import {Create as $Create} from "@wailsio/runtime"; + +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore: Unused imports +import * as slog$0 from "../../../../../../log/slog/models.js"; + +export class App { + /** + * The main application menu + */ + "ApplicationMenu": Menu | null; + "Logger": slog$0.Logger | null; + + /** Creates a new App instance. */ + constructor($$source: Partial = {}) { + if (!("ApplicationMenu" in $$source)) { + this["ApplicationMenu"] = null; + } + if (!("Logger" in $$source)) { + this["Logger"] = null; + } + + Object.assign(this, $$source); + } + + /** + * Creates a new App instance from a string or object. + */ + static createFrom($$source: any = {}): App { + const $$createField0_0 = $$createType1; + const $$createField1_0 = $$createType3; + let $$parsedSource = typeof $$source === 'string' ? JSON.parse($$source) : $$source; + if ("ApplicationMenu" in $$parsedSource) { + $$parsedSource["ApplicationMenu"] = $$createField0_0($$parsedSource["ApplicationMenu"]); + } + if ("Logger" in $$parsedSource) { + $$parsedSource["Logger"] = $$createField1_0($$parsedSource["Logger"]); + } + return new App($$parsedSource as Partial); + } +} + +export class Menu { + + /** Creates a new Menu instance. */ + constructor($$source: Partial = {}) { + + Object.assign(this, $$source); + } + + /** + * Creates a new Menu instance from a string or object. + */ + static createFrom($$source: any = {}): Menu { + let $$parsedSource = typeof $$source === 'string' ? JSON.parse($$source) : $$source; + return new Menu($$parsedSource as Partial); + } +} + +// Private type creation functions +const $$createType0 = Menu.createFrom; +const $$createType1 = $Create.Nullable($$createType0); +const $$createType2 = slog$0.Logger.createFrom; +const $$createType3 = $Create.Nullable($$createType2); diff --git a/frontend/bindings/log/slog/index.ts b/frontend/bindings/log/slog/index.ts new file mode 100644 index 0000000..c9d993a --- /dev/null +++ b/frontend/bindings/log/slog/index.ts @@ -0,0 +1,4 @@ +// Cynhyrchwyd y ffeil hon yn awtomatig. PEIDIWCH Â MODIWL +// This file is automatically generated. DO NOT EDIT + +export * from "./models.js"; diff --git a/frontend/bindings/log/slog/models.ts b/frontend/bindings/log/slog/models.ts new file mode 100644 index 0000000..5dfa498 --- /dev/null +++ b/frontend/bindings/log/slog/models.ts @@ -0,0 +1,31 @@ +// Cynhyrchwyd y ffeil hon yn awtomatig. PEIDIWCH Â MODIWL +// This file is automatically generated. DO NOT EDIT + +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore: Unused imports +import {Create as $Create} from "@wailsio/runtime"; + +/** + * A Logger records structured information about each call to its + * Log, Debug, Info, Warn, and Error methods. + * For each call, it creates a [Record] and passes it to a [Handler]. + * + * To create a new Logger, call [New] or a Logger method + * that begins "With". + */ +export class Logger { + + /** Creates a new Logger instance. */ + constructor($$source: Partial = {}) { + + Object.assign(this, $$source); + } + + /** + * Creates a new Logger instance from a string or object. + */ + static createFrom($$source: any = {}): Logger { + let $$parsedSource = typeof $$source === 'string' ? JSON.parse($$source) : $$source; + return new Logger($$parsedSource as Partial); + } +} diff --git a/frontend/bindings/voidraft/internal/models/models.ts b/frontend/bindings/voidraft/internal/models/models.ts new file mode 100644 index 0000000..b2d1592 --- /dev/null +++ b/frontend/bindings/voidraft/internal/models/models.ts @@ -0,0 +1,577 @@ +// Cynhyrchwyd y ffeil hon yn awtomatig. PEIDIWCH Â MODIWL +// This file is automatically generated. DO NOT EDIT + +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore: Unused imports +import {Create as $Create} from "@wailsio/runtime"; + +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore: Unused imports +import * as time$0 from "../../../time/models.js"; + +/** + * AppConfig 应用配置 - 按照前端设置页面分类组织 + */ +export class AppConfig { + /** + * 通用设置 + */ + "general": GeneralConfig; + + /** + * 编辑设置 + */ + "editing": EditingConfig; + + /** + * 外观设置 + */ + "appearance": AppearanceConfig; + + /** + * 快捷键设置 + */ + "keyBindings": KeyBindingsConfig; + + /** + * 更新设置 + */ + "updates": UpdatesConfig; + + /** + * 配置元数据 + */ + "metadata": ConfigMetadata; + + /** Creates a new AppConfig instance. */ + constructor($$source: Partial = {}) { + if (!("general" in $$source)) { + this["general"] = (new GeneralConfig()); + } + if (!("editing" in $$source)) { + this["editing"] = (new EditingConfig()); + } + if (!("appearance" in $$source)) { + this["appearance"] = (new AppearanceConfig()); + } + if (!("keyBindings" in $$source)) { + this["keyBindings"] = (new KeyBindingsConfig()); + } + if (!("updates" in $$source)) { + this["updates"] = (new UpdatesConfig()); + } + if (!("metadata" in $$source)) { + this["metadata"] = (new ConfigMetadata()); + } + + Object.assign(this, $$source); + } + + /** + * Creates a new AppConfig instance from a string or object. + */ + static createFrom($$source: any = {}): AppConfig { + const $$createField0_0 = $$createType0; + const $$createField1_0 = $$createType1; + const $$createField2_0 = $$createType2; + const $$createField3_0 = $$createType3; + const $$createField4_0 = $$createType4; + const $$createField5_0 = $$createType5; + let $$parsedSource = typeof $$source === 'string' ? JSON.parse($$source) : $$source; + if ("general" in $$parsedSource) { + $$parsedSource["general"] = $$createField0_0($$parsedSource["general"]); + } + if ("editing" in $$parsedSource) { + $$parsedSource["editing"] = $$createField1_0($$parsedSource["editing"]); + } + if ("appearance" in $$parsedSource) { + $$parsedSource["appearance"] = $$createField2_0($$parsedSource["appearance"]); + } + if ("keyBindings" in $$parsedSource) { + $$parsedSource["keyBindings"] = $$createField3_0($$parsedSource["keyBindings"]); + } + if ("updates" in $$parsedSource) { + $$parsedSource["updates"] = $$createField4_0($$parsedSource["updates"]); + } + if ("metadata" in $$parsedSource) { + $$parsedSource["metadata"] = $$createField5_0($$parsedSource["metadata"]); + } + return new AppConfig($$parsedSource as Partial); + } +} + +/** + * AppearanceConfig 外观设置配置 + */ +export class AppearanceConfig { + /** + * 界面语言 + */ + "language": LanguageType; + + /** Creates a new AppearanceConfig instance. */ + constructor($$source: Partial = {}) { + if (!("language" in $$source)) { + this["language"] = ("" as LanguageType); + } + + Object.assign(this, $$source); + } + + /** + * Creates a new AppearanceConfig instance from a string or object. + */ + static createFrom($$source: any = {}): AppearanceConfig { + let $$parsedSource = typeof $$source === 'string' ? JSON.parse($$source) : $$source; + return new AppearanceConfig($$parsedSource as Partial); + } +} + +/** + * ConfigMetadata 配置元数据 + */ +export class ConfigMetadata { + /** + * 配置版本 + */ + "version": string; + + /** + * 最后更新时间 + */ + "lastUpdated": time$0.Time; + + /** Creates a new ConfigMetadata instance. */ + constructor($$source: Partial = {}) { + if (!("version" in $$source)) { + this["version"] = ""; + } + if (!("lastUpdated" in $$source)) { + this["lastUpdated"] = null; + } + + Object.assign(this, $$source); + } + + /** + * Creates a new ConfigMetadata instance from a string or object. + */ + static createFrom($$source: any = {}): ConfigMetadata { + let $$parsedSource = typeof $$source === 'string' ? JSON.parse($$source) : $$source; + return new ConfigMetadata($$parsedSource as Partial); + } +} + +/** + * Document 表示一个文档 + */ +export class Document { + /** + * 元数据 + */ + "meta": DocumentMeta; + + /** + * 文档内容 + */ + "content": string; + + /** Creates a new Document instance. */ + constructor($$source: Partial = {}) { + if (!("meta" in $$source)) { + this["meta"] = (new DocumentMeta()); + } + if (!("content" in $$source)) { + this["content"] = ""; + } + + Object.assign(this, $$source); + } + + /** + * Creates a new Document instance from a string or object. + */ + static createFrom($$source: any = {}): Document { + const $$createField0_0 = $$createType6; + let $$parsedSource = typeof $$source === 'string' ? JSON.parse($$source) : $$source; + if ("meta" in $$parsedSource) { + $$parsedSource["meta"] = $$createField0_0($$parsedSource["meta"]); + } + return new Document($$parsedSource as Partial); + } +} + +/** + * DocumentMeta 文档元数据 + */ +export class DocumentMeta { + /** + * 文档唯一标识 + */ + "id": string; + + /** + * 文档标题 + */ + "title": string; + + /** + * 最后更新时间 + */ + "lastUpdated": time$0.Time; + + /** + * 创建时间 + */ + "createdAt": time$0.Time; + + /** Creates a new DocumentMeta instance. */ + constructor($$source: Partial = {}) { + if (!("id" in $$source)) { + this["id"] = ""; + } + if (!("title" in $$source)) { + this["title"] = ""; + } + if (!("lastUpdated" in $$source)) { + this["lastUpdated"] = null; + } + if (!("createdAt" in $$source)) { + this["createdAt"] = null; + } + + Object.assign(this, $$source); + } + + /** + * Creates a new DocumentMeta instance from a string or object. + */ + static createFrom($$source: any = {}): DocumentMeta { + let $$parsedSource = typeof $$source === 'string' ? JSON.parse($$source) : $$source; + return new DocumentMeta($$parsedSource as Partial); + } +} + +/** + * EditingConfig 编辑设置配置 + */ +export class EditingConfig { + /** + * 字体设置 + * 字体大小 + */ + "fontSize": number; + + /** + * 字体族 + */ + "fontFamily": string; + + /** + * 字体粗细 + */ + "fontWeight": string; + + /** + * 行高 + */ + "lineHeight": number; + + /** + * Tab设置 + * 是否启用Tab缩进 + */ + "enableTabIndent": boolean; + + /** + * Tab大小 + */ + "tabSize": number; + + /** + * Tab类型(空格或Tab) + */ + "tabType": TabType; + + /** + * 保存选项 + * 自动保存延迟(毫秒) + */ + "autoSaveDelay": number; + + /** + * 变更字符阈值 + */ + "changeThreshold": number; + + /** + * 最小保存间隔(毫秒) + */ + "minSaveInterval": number; + + /** Creates a new EditingConfig instance. */ + constructor($$source: Partial = {}) { + if (!("fontSize" in $$source)) { + this["fontSize"] = 0; + } + if (!("fontFamily" in $$source)) { + this["fontFamily"] = ""; + } + if (!("fontWeight" in $$source)) { + this["fontWeight"] = ""; + } + if (!("lineHeight" in $$source)) { + this["lineHeight"] = 0; + } + if (!("enableTabIndent" in $$source)) { + this["enableTabIndent"] = false; + } + if (!("tabSize" in $$source)) { + this["tabSize"] = 0; + } + if (!("tabType" in $$source)) { + this["tabType"] = ("" as TabType); + } + if (!("autoSaveDelay" in $$source)) { + this["autoSaveDelay"] = 0; + } + if (!("changeThreshold" in $$source)) { + this["changeThreshold"] = 0; + } + if (!("minSaveInterval" in $$source)) { + this["minSaveInterval"] = 0; + } + + Object.assign(this, $$source); + } + + /** + * Creates a new EditingConfig instance from a string or object. + */ + static createFrom($$source: any = {}): EditingConfig { + let $$parsedSource = typeof $$source === 'string' ? JSON.parse($$source) : $$source; + return new EditingConfig($$parsedSource as Partial); + } +} + +/** + * GeneralConfig 通用设置配置 + */ +export class GeneralConfig { + /** + * 窗口是否置顶 + */ + "alwaysOnTop": boolean; + + /** + * 默认数据存储路径 + */ + "defaultDataPath": string; + + /** + * 数据存储路径配置 + * 是否使用自定义数据路径 + */ + "useCustomDataPath": boolean; + + /** + * 自定义数据存储路径 + */ + "customDataPath": string; + + /** + * 全局热键设置 + * 是否启用全局热键 + */ + "enableGlobalHotkey": boolean; + + /** + * 全局热键组合 + */ + "globalHotkey": HotkeyCombo; + + /** Creates a new GeneralConfig instance. */ + constructor($$source: Partial = {}) { + if (!("alwaysOnTop" in $$source)) { + this["alwaysOnTop"] = false; + } + if (!("defaultDataPath" in $$source)) { + this["defaultDataPath"] = ""; + } + if (!("useCustomDataPath" in $$source)) { + this["useCustomDataPath"] = false; + } + if (!("customDataPath" in $$source)) { + this["customDataPath"] = ""; + } + if (!("enableGlobalHotkey" in $$source)) { + this["enableGlobalHotkey"] = false; + } + if (!("globalHotkey" in $$source)) { + this["globalHotkey"] = (new HotkeyCombo()); + } + + Object.assign(this, $$source); + } + + /** + * Creates a new GeneralConfig instance from a string or object. + */ + static createFrom($$source: any = {}): GeneralConfig { + const $$createField5_0 = $$createType7; + let $$parsedSource = typeof $$source === 'string' ? JSON.parse($$source) : $$source; + if ("globalHotkey" in $$parsedSource) { + $$parsedSource["globalHotkey"] = $$createField5_0($$parsedSource["globalHotkey"]); + } + return new GeneralConfig($$parsedSource as Partial); + } +} + +/** + * HotkeyCombo 热键组合定义 + */ +export class HotkeyCombo { + /** + * Ctrl键 + */ + "ctrl": boolean; + + /** + * Shift键 + */ + "shift": boolean; + + /** + * Alt键 + */ + "alt": boolean; + + /** + * Win键 + */ + "win": boolean; + + /** + * 主键(如 'X', 'F1' 等) + */ + "key": string; + + /** Creates a new HotkeyCombo instance. */ + constructor($$source: Partial = {}) { + if (!("ctrl" in $$source)) { + this["ctrl"] = false; + } + if (!("shift" in $$source)) { + this["shift"] = false; + } + if (!("alt" in $$source)) { + this["alt"] = false; + } + if (!("win" in $$source)) { + this["win"] = false; + } + if (!("key" in $$source)) { + this["key"] = ""; + } + + Object.assign(this, $$source); + } + + /** + * Creates a new HotkeyCombo instance from a string or object. + */ + static createFrom($$source: any = {}): HotkeyCombo { + let $$parsedSource = typeof $$source === 'string' ? JSON.parse($$source) : $$source; + return new HotkeyCombo($$parsedSource as Partial); + } +} + +/** + * KeyBindingsConfig 快捷键设置配置 + */ +export class KeyBindingsConfig { + + /** Creates a new KeyBindingsConfig instance. */ + constructor($$source: Partial = {}) { + + Object.assign(this, $$source); + } + + /** + * Creates a new KeyBindingsConfig instance from a string or object. + */ + static createFrom($$source: any = {}): KeyBindingsConfig { + let $$parsedSource = typeof $$source === 'string' ? JSON.parse($$source) : $$source; + return new KeyBindingsConfig($$parsedSource as Partial); + } +} + +/** + * LanguageType 语言类型定义 + */ +export enum LanguageType { + /** + * The Go zero value for the underlying type of the enum. + */ + $zero = "", + + /** + * LangZhCN 中文简体 + */ + LangZhCN = "zh-CN", + + /** + * LangEnUS 英文-美国 + */ + LangEnUS = "en-US", +}; + +/** + * TabType 定义了制表符类型 + */ +export enum TabType { + /** + * The Go zero value for the underlying type of the enum. + */ + $zero = "", + + /** + * TabTypeSpaces 使用空格作为制表符 + */ + TabTypeSpaces = "spaces", + + /** + * TabTypeTab 使用Tab作为制表符 + */ + TabTypeTab = "tab", +}; + +/** + * UpdatesConfig 更新设置配置 + */ +export class UpdatesConfig { + + /** Creates a new UpdatesConfig instance. */ + constructor($$source: Partial = {}) { + + Object.assign(this, $$source); + } + + /** + * Creates a new UpdatesConfig instance from a string or object. + */ + static createFrom($$source: any = {}): UpdatesConfig { + let $$parsedSource = typeof $$source === 'string' ? JSON.parse($$source) : $$source; + return new UpdatesConfig($$parsedSource as Partial); + } +} + +// Private type creation functions +const $$createType0 = GeneralConfig.createFrom; +const $$createType1 = EditingConfig.createFrom; +const $$createType2 = AppearanceConfig.createFrom; +const $$createType3 = KeyBindingsConfig.createFrom; +const $$createType4 = UpdatesConfig.createFrom; +const $$createType5 = ConfigMetadata.createFrom; +const $$createType6 = DocumentMeta.createFrom; +const $$createType7 = HotkeyCombo.createFrom; diff --git a/frontend/bindings/voidraft/internal/services/configservice.ts b/frontend/bindings/voidraft/internal/services/configservice.ts new file mode 100644 index 0000000..dec2c99 --- /dev/null +++ b/frontend/bindings/voidraft/internal/services/configservice.ts @@ -0,0 +1,63 @@ +// Cynhyrchwyd y ffeil hon yn awtomatig. PEIDIWCH Â MODIWL +// This file is automatically generated. DO NOT EDIT + +/** + * ConfigService 提供基于 Viper 的配置管理功能 + * @module + */ + +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore: Unused imports +import {Call as $Call, Create as $Create} from "@wailsio/runtime"; + +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore: Unused imports +import * as models$0 from "../models/models.js"; + +/** + * Get 获取配置项 + */ +export function Get(key: string): Promise & { cancel(): void } { + let $resultPromise = $Call.ByID(807201772, key) as any; + return $resultPromise; +} + +/** + * GetConfig 获取完整应用配置 + */ +export function GetConfig(): Promise & { cancel(): void } { + let $resultPromise = $Call.ByID(1013336538) as any; + let $typingPromise = $resultPromise.then(($result: any) => { + return $$createType1($result); + }) as any; + $typingPromise.cancel = $resultPromise.cancel.bind($resultPromise); + return $typingPromise; +} + +/** + * ResetConfig 重置为默认配置 + */ +export function ResetConfig(): Promise & { cancel(): void } { + let $resultPromise = $Call.ByID(3593047389) as any; + return $resultPromise; +} + +/** + * Set 设置配置项 + */ +export function Set(key: string, value: any): Promise & { cancel(): void } { + let $resultPromise = $Call.ByID(2921955968, key, value) as any; + return $resultPromise; +} + +/** + * SetHotkeyChangeCallback 设置热键配置变更回调 + */ +export function SetHotkeyChangeCallback(callback: any): Promise & { cancel(): void } { + let $resultPromise = $Call.ByID(283872321, callback) as any; + return $resultPromise; +} + +// Private type creation functions +const $$createType0 = models$0.AppConfig.createFrom; +const $$createType1 = $Create.Nullable($$createType0); diff --git a/frontend/bindings/voidraft/internal/services/hotkeyservice.ts b/frontend/bindings/voidraft/internal/services/hotkeyservice.ts new file mode 100644 index 0000000..3b53efa --- /dev/null +++ b/frontend/bindings/voidraft/internal/services/hotkeyservice.ts @@ -0,0 +1,90 @@ +// Cynhyrchwyd y ffeil hon yn awtomatig. PEIDIWCH Â MODIWL +// This file is automatically generated. DO NOT EDIT + +/** + * HotkeyService 全局热键服务 + * @module + */ + +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore: Unused imports +import {Call as $Call, Create as $Create} from "@wailsio/runtime"; + +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore: Unused imports +import * as application$0 from "../../../github.com/wailsapp/wails/v3/pkg/application/models.js"; +// eslint-disable-next-line @typescript-eslint/ban-ts-comment +// @ts-ignore: Unused imports +import * as models$0 from "../models/models.js"; + +/** + * GetCurrentHotkey 获取当前注册的热键 + */ +export function GetCurrentHotkey(): Promise & { cancel(): void } { + let $resultPromise = $Call.ByID(2572811187) as any; + let $typingPromise = $resultPromise.then(($result: any) => { + return $$createType1($result); + }) as any; + $typingPromise.cancel = $resultPromise.cancel.bind($resultPromise); + return $typingPromise; +} + +/** + * Initialize 初始化热键服务 + */ +export function Initialize(app: application$0.App | null): Promise & { cancel(): void } { + let $resultPromise = $Call.ByID(3671360458, app) as any; + return $resultPromise; +} + +/** + * IsRegistered 检查是否已注册热键 + */ +export function IsRegistered(): Promise & { cancel(): void } { + let $resultPromise = $Call.ByID(106954156) as any; + return $resultPromise; +} + +/** + * RegisterHotkey 注册全局热键 + */ +export function RegisterHotkey(hotkey: models$0.HotkeyCombo | null): Promise & { cancel(): void } { + let $resultPromise = $Call.ByID(1103945691, hotkey) as any; + return $resultPromise; +} + +/** + * ServiceShutdown 关闭热键服务 + */ +export function ServiceShutdown(): Promise & { cancel(): void } { + let $resultPromise = $Call.ByID(157291181) as any; + return $resultPromise; +} + +/** + * ToggleWindow 切换窗口显示/隐藏 - 通过事件通知前端处理 + */ +export function ToggleWindow(): Promise & { cancel(): void } { + let $resultPromise = $Call.ByID(1318185132) as any; + return $resultPromise; +} + +/** + * UnregisterHotkey 取消注册全局热键 + */ +export function UnregisterHotkey(): Promise & { cancel(): void } { + let $resultPromise = $Call.ByID(3544283732) as any; + return $resultPromise; +} + +/** + * UpdateHotkey 更新热键配置 + */ +export function UpdateHotkey(enable: boolean, hotkey: models$0.HotkeyCombo | null): Promise & { cancel(): void } { + let $resultPromise = $Call.ByID(823285555, enable, hotkey) as any; + return $resultPromise; +} + +// Private type creation functions +const $$createType0 = models$0.HotkeyCombo.createFrom; +const $$createType1 = $Create.Nullable($$createType0); diff --git a/frontend/bindings/voidraft/internal/services/index.ts b/frontend/bindings/voidraft/internal/services/index.ts new file mode 100644 index 0000000..682734b --- /dev/null +++ b/frontend/bindings/voidraft/internal/services/index.ts @@ -0,0 +1,15 @@ +// Cynhyrchwyd y ffeil hon yn awtomatig. PEIDIWCH Â MODIWL +// This file is automatically generated. DO NOT EDIT + +import * as ConfigService from "./configservice.js"; +import * as DocumentService from "./documentservice.js"; +import * as HotkeyService from "./hotkeyservice.js"; +import * as SystemService from "./systemservice.js"; +export { + ConfigService, + DocumentService, + HotkeyService, + SystemService +}; + +export * from "./models.js"; diff --git a/frontend/package-lock.json b/frontend/package-lock.json index 424af96..c3960c3 100644 --- a/frontend/package-lock.json +++ b/frontend/package-lock.json @@ -30,7 +30,7 @@ "@codemirror/lang-wast": "^6.0.2", "@codemirror/lang-xml": "^6.1.0", "@codemirror/lang-yaml": "^6.1.2", - "@codemirror/language": "^6.11.0", + "@codemirror/language": "^6.11.1", "@codemirror/language-data": "^6.5.1", "@codemirror/legacy-modes": "^6.5.1", "@codemirror/lint": "^6.8.5", @@ -58,7 +58,7 @@ "eslint-plugin-vue": "^10.1.0", "globals": "^16.2.0", "typescript": "^5.8.3", - "typescript-eslint": "^8.33.0", + "typescript-eslint": "^8.33.1", "unplugin-vue-components": "^28.7.0", "vite": "^6.3.5", "vue-eslint-parser": "^10.1.3", @@ -400,9 +400,9 @@ } }, "node_modules/@codemirror/language": { - "version": "6.11.0", - "resolved": "https://registry.npmmirror.com/@codemirror/language/-/language-6.11.0.tgz", - "integrity": "sha512-A7+f++LodNNc1wGgoRDTt78cOwWm9KVezApgjOMp1W4hM0898nsqBXwF+sbePE7ZRcjN7Sa1Z5m2oN27XkmEjQ==", + "version": "6.11.1", + "resolved": "https://registry.npmmirror.com/@codemirror/language/-/language-6.11.1.tgz", + "integrity": "sha512-5kS1U7emOGV84vxC+ruBty5sUgcD0te6dyupyRVG2zaSjhTDM73LhVKUtVwiqSe6QwmEoA4SCiU8AKPFyumAWQ==", "license": "MIT", "dependencies": { "@codemirror/state": "^6.0.0", @@ -2065,17 +2065,17 @@ "license": "MIT" }, "node_modules/@typescript-eslint/eslint-plugin": { - "version": "8.33.0", - "resolved": "https://registry.npmmirror.com/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.33.0.tgz", - "integrity": "sha512-CACyQuqSHt7ma3Ns601xykeBK/rDeZa3w6IS6UtMQbixO5DWy+8TilKkviGDH6jtWCo8FGRKEK5cLLkPvEammQ==", + "version": "8.33.1", + "resolved": "https://registry.npmmirror.com/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.33.1.tgz", + "integrity": "sha512-TDCXj+YxLgtvxvFlAvpoRv9MAncDLBV2oT9Bd7YBGC/b/sEURoOYuIwLI99rjWOfY3QtDzO+mk0n4AmdFExW8A==", "dev": true, "license": "MIT", "dependencies": { "@eslint-community/regexpp": "^4.10.0", - "@typescript-eslint/scope-manager": "8.33.0", - "@typescript-eslint/type-utils": "8.33.0", - "@typescript-eslint/utils": "8.33.0", - "@typescript-eslint/visitor-keys": "8.33.0", + "@typescript-eslint/scope-manager": "8.33.1", + "@typescript-eslint/type-utils": "8.33.1", + "@typescript-eslint/utils": "8.33.1", + "@typescript-eslint/visitor-keys": "8.33.1", "graphemer": "^1.4.0", "ignore": "^7.0.0", "natural-compare": "^1.4.0", @@ -2089,7 +2089,7 @@ "url": "https://opencollective.com/typescript-eslint" }, "peerDependencies": { - "@typescript-eslint/parser": "^8.33.0", + "@typescript-eslint/parser": "^8.33.1", "eslint": "^8.57.0 || ^9.0.0", "typescript": ">=4.8.4 <5.9.0" } @@ -2105,16 +2105,16 @@ } }, "node_modules/@typescript-eslint/parser": { - "version": "8.33.0", - "resolved": "https://registry.npmmirror.com/@typescript-eslint/parser/-/parser-8.33.0.tgz", - "integrity": "sha512-JaehZvf6m0yqYp34+RVnihBAChkqeH+tqqhS0GuX1qgPpwLvmTPheKEs6OeCK6hVJgXZHJ2vbjnC9j119auStQ==", + "version": "8.33.1", + "resolved": "https://registry.npmmirror.com/@typescript-eslint/parser/-/parser-8.33.1.tgz", + "integrity": "sha512-qwxv6dq682yVvgKKp2qWwLgRbscDAYktPptK4JPojCwwi3R9cwrvIxS4lvBpzmcqzR4bdn54Z0IG1uHFskW4dA==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/scope-manager": "8.33.0", - "@typescript-eslint/types": "8.33.0", - "@typescript-eslint/typescript-estree": "8.33.0", - "@typescript-eslint/visitor-keys": "8.33.0", + "@typescript-eslint/scope-manager": "8.33.1", + "@typescript-eslint/types": "8.33.1", + "@typescript-eslint/typescript-estree": "8.33.1", + "@typescript-eslint/visitor-keys": "8.33.1", "debug": "^4.3.4" }, "engines": { @@ -2130,14 +2130,14 @@ } }, "node_modules/@typescript-eslint/project-service": { - "version": "8.33.0", - "resolved": "https://registry.npmmirror.com/@typescript-eslint/project-service/-/project-service-8.33.0.tgz", - "integrity": "sha512-d1hz0u9l6N+u/gcrk6s6gYdl7/+pp8yHheRTqP6X5hVDKALEaTn8WfGiit7G511yueBEL3OpOEpD+3/MBdoN+A==", + "version": "8.33.1", + "resolved": "https://registry.npmmirror.com/@typescript-eslint/project-service/-/project-service-8.33.1.tgz", + "integrity": "sha512-DZR0efeNklDIHHGRpMpR5gJITQpu6tLr9lDJnKdONTC7vvzOlLAG/wcfxcdxEWrbiZApcoBCzXqU/Z458Za5Iw==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/tsconfig-utils": "^8.33.0", - "@typescript-eslint/types": "^8.33.0", + "@typescript-eslint/tsconfig-utils": "^8.33.1", + "@typescript-eslint/types": "^8.33.1", "debug": "^4.3.4" }, "engines": { @@ -2146,17 +2146,20 @@ "funding": { "type": "opencollective", "url": "https://opencollective.com/typescript-eslint" + }, + "peerDependencies": { + "typescript": ">=4.8.4 <5.9.0" } }, "node_modules/@typescript-eslint/scope-manager": { - "version": "8.33.0", - "resolved": "https://registry.npmmirror.com/@typescript-eslint/scope-manager/-/scope-manager-8.33.0.tgz", - "integrity": "sha512-LMi/oqrzpqxyO72ltP+dBSP6V0xiUb4saY7WLtxSfiNEBI8m321LLVFU9/QDJxjDQG9/tjSqKz/E3380TEqSTw==", + "version": "8.33.1", + "resolved": "https://registry.npmmirror.com/@typescript-eslint/scope-manager/-/scope-manager-8.33.1.tgz", + "integrity": "sha512-dM4UBtgmzHR9bS0Rv09JST0RcHYearoEoo3pG5B6GoTR9XcyeqX87FEhPo+5kTvVfKCvfHaHrcgeJQc6mrDKrA==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/types": "8.33.0", - "@typescript-eslint/visitor-keys": "8.33.0" + "@typescript-eslint/types": "8.33.1", + "@typescript-eslint/visitor-keys": "8.33.1" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -2167,9 +2170,9 @@ } }, "node_modules/@typescript-eslint/tsconfig-utils": { - "version": "8.33.0", - "resolved": "https://registry.npmmirror.com/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.33.0.tgz", - "integrity": "sha512-sTkETlbqhEoiFmGr1gsdq5HyVbSOF0145SYDJ/EQmXHtKViCaGvnyLqWFFHtEXoS0J1yU8Wyou2UGmgW88fEug==", + "version": "8.33.1", + "resolved": "https://registry.npmmirror.com/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.33.1.tgz", + "integrity": "sha512-STAQsGYbHCF0/e+ShUQ4EatXQ7ceh3fBCXkNU7/MZVKulrlq1usH7t2FhxvCpuCi5O5oi1vmVaAjrGeL71OK1g==", "dev": true, "license": "MIT", "engines": { @@ -2184,14 +2187,14 @@ } }, "node_modules/@typescript-eslint/type-utils": { - "version": "8.33.0", - "resolved": "https://registry.npmmirror.com/@typescript-eslint/type-utils/-/type-utils-8.33.0.tgz", - "integrity": "sha512-lScnHNCBqL1QayuSrWeqAL5GmqNdVUQAAMTaCwdYEdWfIrSrOGzyLGRCHXcCixa5NK6i5l0AfSO2oBSjCjf4XQ==", + "version": "8.33.1", + "resolved": "https://registry.npmmirror.com/@typescript-eslint/type-utils/-/type-utils-8.33.1.tgz", + "integrity": "sha512-1cG37d9xOkhlykom55WVwG2QRNC7YXlxMaMzqw2uPeJixBFfKWZgaP/hjAObqMN/u3fr5BrTwTnc31/L9jQ2ww==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/typescript-estree": "8.33.0", - "@typescript-eslint/utils": "8.33.0", + "@typescript-eslint/typescript-estree": "8.33.1", + "@typescript-eslint/utils": "8.33.1", "debug": "^4.3.4", "ts-api-utils": "^2.1.0" }, @@ -2208,9 +2211,9 @@ } }, "node_modules/@typescript-eslint/types": { - "version": "8.33.0", - "resolved": "https://registry.npmmirror.com/@typescript-eslint/types/-/types-8.33.0.tgz", - "integrity": "sha512-DKuXOKpM5IDT1FA2g9x9x1Ug81YuKrzf4mYX8FAVSNu5Wo/LELHWQyM1pQaDkI42bX15PWl0vNPt1uGiIFUOpg==", + "version": "8.33.1", + "resolved": "https://registry.npmmirror.com/@typescript-eslint/types/-/types-8.33.1.tgz", + "integrity": "sha512-xid1WfizGhy/TKMTwhtVOgalHwPtV8T32MS9MaH50Cwvz6x6YqRIPdD2WvW0XaqOzTV9p5xdLY0h/ZusU5Lokg==", "dev": true, "license": "MIT", "engines": { @@ -2222,16 +2225,16 @@ } }, "node_modules/@typescript-eslint/typescript-estree": { - "version": "8.33.0", - "resolved": "https://registry.npmmirror.com/@typescript-eslint/typescript-estree/-/typescript-estree-8.33.0.tgz", - "integrity": "sha512-vegY4FQoB6jL97Tu/lWRsAiUUp8qJTqzAmENH2k59SJhw0Th1oszb9Idq/FyyONLuNqT1OADJPXfyUNOR8SzAQ==", + "version": "8.33.1", + "resolved": "https://registry.npmmirror.com/@typescript-eslint/typescript-estree/-/typescript-estree-8.33.1.tgz", + "integrity": "sha512-+s9LYcT8LWjdYWu7IWs7FvUxpQ/DGkdjZeE/GGulHvv8rvYwQvVaUZ6DE+j5x/prADUgSbbCWZ2nPI3usuVeOA==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/project-service": "8.33.0", - "@typescript-eslint/tsconfig-utils": "8.33.0", - "@typescript-eslint/types": "8.33.0", - "@typescript-eslint/visitor-keys": "8.33.0", + "@typescript-eslint/project-service": "8.33.1", + "@typescript-eslint/tsconfig-utils": "8.33.1", + "@typescript-eslint/types": "8.33.1", + "@typescript-eslint/visitor-keys": "8.33.1", "debug": "^4.3.4", "fast-glob": "^3.3.2", "is-glob": "^4.0.3", @@ -2277,16 +2280,16 @@ } }, "node_modules/@typescript-eslint/utils": { - "version": "8.33.0", - "resolved": "https://registry.npmmirror.com/@typescript-eslint/utils/-/utils-8.33.0.tgz", - "integrity": "sha512-lPFuQaLA9aSNa7D5u2EpRiqdAUhzShwGg/nhpBlc4GR6kcTABttCuyjFs8BcEZ8VWrjCBof/bePhP3Q3fS+Yrw==", + "version": "8.33.1", + "resolved": "https://registry.npmmirror.com/@typescript-eslint/utils/-/utils-8.33.1.tgz", + "integrity": "sha512-52HaBiEQUaRYqAXpfzWSR2U3gxk92Kw006+xZpElaPMg3C4PgM+A5LqwoQI1f9E5aZ/qlxAZxzm42WX+vn92SQ==", "dev": true, "license": "MIT", "dependencies": { "@eslint-community/eslint-utils": "^4.7.0", - "@typescript-eslint/scope-manager": "8.33.0", - "@typescript-eslint/types": "8.33.0", - "@typescript-eslint/typescript-estree": "8.33.0" + "@typescript-eslint/scope-manager": "8.33.1", + "@typescript-eslint/types": "8.33.1", + "@typescript-eslint/typescript-estree": "8.33.1" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -2301,13 +2304,13 @@ } }, "node_modules/@typescript-eslint/visitor-keys": { - "version": "8.33.0", - "resolved": "https://registry.npmmirror.com/@typescript-eslint/visitor-keys/-/visitor-keys-8.33.0.tgz", - "integrity": "sha512-7RW7CMYoskiz5OOGAWjJFxgb7c5UNjTG292gYhWeOAcFmYCtVCSqjqSBj5zMhxbXo2JOW95YYrUWJfU0zrpaGQ==", + "version": "8.33.1", + "resolved": "https://registry.npmmirror.com/@typescript-eslint/visitor-keys/-/visitor-keys-8.33.1.tgz", + "integrity": "sha512-3i8NrFcZeeDHJ+7ZUuDkGT+UHq+XoFGsymNK2jZCOHcfEzRQ0BdpRtdpSx/Iyf3MHLWIcLS0COuOPibKQboIiQ==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/types": "8.33.0", + "@typescript-eslint/types": "8.33.1", "eslint-visitor-keys": "^4.2.0" }, "engines": { @@ -4544,15 +4547,15 @@ } }, "node_modules/typescript-eslint": { - "version": "8.33.0", - "resolved": "https://registry.npmmirror.com/typescript-eslint/-/typescript-eslint-8.33.0.tgz", - "integrity": "sha512-5YmNhF24ylCsvdNW2oJwMzTbaeO4bg90KeGtMjUw0AGtHksgEPLRTUil+coHwCfiu4QjVJFnjp94DmU6zV7DhQ==", + "version": "8.33.1", + "resolved": "https://registry.npmmirror.com/typescript-eslint/-/typescript-eslint-8.33.1.tgz", + "integrity": "sha512-AgRnV4sKkWOiZ0Kjbnf5ytTJXMUZQ0qhSVdQtDNYLPLnjsATEYhaO94GlRQwi4t4gO8FfjM6NnikHeKjUm8D7A==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/eslint-plugin": "8.33.0", - "@typescript-eslint/parser": "8.33.0", - "@typescript-eslint/utils": "8.33.0" + "@typescript-eslint/eslint-plugin": "8.33.1", + "@typescript-eslint/parser": "8.33.1", + "@typescript-eslint/utils": "8.33.1" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" diff --git a/frontend/package.json b/frontend/package.json index 5508394..b134cb0 100644 --- a/frontend/package.json +++ b/frontend/package.json @@ -34,7 +34,7 @@ "@codemirror/lang-wast": "^6.0.2", "@codemirror/lang-xml": "^6.1.0", "@codemirror/lang-yaml": "^6.1.2", - "@codemirror/language": "^6.11.0", + "@codemirror/language": "^6.11.1", "@codemirror/language-data": "^6.5.1", "@codemirror/legacy-modes": "^6.5.1", "@codemirror/lint": "^6.8.5", @@ -62,7 +62,7 @@ "eslint-plugin-vue": "^10.1.0", "globals": "^16.2.0", "typescript": "^5.8.3", - "typescript-eslint": "^8.33.0", + "typescript-eslint": "^8.33.1", "unplugin-vue-components": "^28.7.0", "vite": "^6.3.5", "vue-eslint-parser": "^10.1.3", diff --git a/frontend/src/i18n/locales/en-US.ts b/frontend/src/i18n/locales/en-US.ts index b1ee8af..eecc66f 100644 --- a/frontend/src/i18n/locales/en-US.ts +++ b/frontend/src/i18n/locales/en-US.ts @@ -27,6 +27,7 @@ export default { tabSizeFixed: 'Tab size ({value}) has been corrected to {fixed}', tabTypeFixed: 'Tab type ({value}) is invalid, corrected to spaces', alwaysOnTopFailed: 'Failed to set window always on top', + alwaysOnTopSuccess: 'Window always on top status updated', languageChanged: 'Language setting updated', languageChangeFailed: 'Failed to update language setting' }, @@ -67,9 +68,15 @@ export default { window: 'Window/Application', showInSystemTray: 'Show in System Tray', alwaysOnTop: 'Always on Top', + dataStorage: 'Data Storage', + useCustomDataPath: 'Use custom data storage path', + selectDirectory: 'Select Directory', + selectDataDirectory: 'Select Data Storage Directory', + defaultDataPath: 'Default data storage path', + enterCustomPath: 'Enter custom data storage path', + pathHint: 'Example: C:\\MyData or /home/user/data or relative path ./data', bufferFiles: 'Buffer Files Path', useCustomLocation: 'Use custom location for buffer files', - selectDirectory: 'Select Directory', fontSize: 'Font Size', fontSizeDescription: 'Editor font size', fontSettings: 'Font Settings', diff --git a/frontend/src/i18n/locales/zh-CN.ts b/frontend/src/i18n/locales/zh-CN.ts index 91dcdeb..0982365 100644 --- a/frontend/src/i18n/locales/zh-CN.ts +++ b/frontend/src/i18n/locales/zh-CN.ts @@ -27,6 +27,7 @@ export default { tabSizeFixed: 'Tab大小值({value})已被修正为{fixed}', tabTypeFixed: 'Tab类型({value})不合法,已修正为空格', alwaysOnTopFailed: '无法设置窗口置顶状态', + alwaysOnTopSuccess: '窗口置顶状态已更新', languageChanged: '语言设置已更新', languageChangeFailed: '语言设置更新失败' }, @@ -67,9 +68,15 @@ export default { window: '窗口/应用程序', showInSystemTray: '在系统托盘中显示', alwaysOnTop: '窗口始终置顶', + dataStorage: '数据存储', + useCustomDataPath: '使用自定义数据存储路径', + selectDirectory: '选择目录', + selectDataDirectory: '选择数据存储目录', + defaultDataPath: '默认数据存储路径', + enterCustomPath: '请输入自定义数据存储路径', + pathHint: '例如: C:\\MyData 或 /home/user/data 或相对路径 ./data', bufferFiles: '缓冲文件路径', useCustomLocation: '使用自定义位置存储缓冲文件', - selectDirectory: '选择目录', fontSize: '字体大小', fontSizeDescription: '编辑器字体大小', fontSettings: '字体设置', diff --git a/frontend/src/stores/configStore.ts b/frontend/src/stores/configStore.ts index f9496e8..5b3de69 100644 --- a/frontend/src/stores/configStore.ts +++ b/frontend/src/stores/configStore.ts @@ -13,6 +13,7 @@ import {useI18n} from 'vue-i18n'; import {useErrorHandler} from '@/utils/errorHandler'; import {ConfigUtils} from '@/utils/configUtils'; import {WindowController} from '@/utils/windowController'; +import * as runtime from '@wailsio/runtime'; // 国际化相关导入 export type SupportedLocaleType = 'zh-CN' | 'en-US'; @@ -46,7 +47,9 @@ type NumberConfigKey = 'fontSize' | 'tabSize' | 'lineHeight'; // 配置键映射 const GENERAL_CONFIG_KEY_MAP: GeneralConfigKeyMap = { alwaysOnTop: 'general.always_on_top', - dataPath: 'general.data_path', + defaultDataPath: 'general.default_data_path', + useCustomDataPath: 'general.use_custom_data_path', + customDataPath: 'general.custom_data_path', enableGlobalHotkey: 'general.enable_global_hotkey', globalHotkey: 'general.global_hotkey' } as const; @@ -114,7 +117,9 @@ const getBrowserLanguage = (): SupportedLocaleType => { const DEFAULT_CONFIG: AppConfig = { general: { alwaysOnTop: false, - dataPath: './data', + defaultDataPath: './data', + useCustomDataPath: false, + customDataPath: '', enableGlobalHotkey: false, globalHotkey: { ctrl: false, @@ -318,7 +323,13 @@ export const useConfigStore = defineStore('config', () => { // 创建切换器实例 const togglers = { tabIndent: createEditingToggler('enableTabIndent'), - alwaysOnTop: createGeneralToggler('alwaysOnTop'), + alwaysOnTop: async () => { + await safeCall(async () => { + await updateGeneralConfig('alwaysOnTop', !state.config.general.alwaysOnTop); + // 立即应用窗口置顶状态 + await runtime.Window.SetAlwaysOnTop(state.config.general.alwaysOnTop); + }, 'config.alwaysOnTopFailed', 'config.alwaysOnTopSuccess'); + }, tabType: createEnumToggler('tabType', CONFIG_LIMITS.tabType.values) }; @@ -326,7 +337,7 @@ export const useConfigStore = defineStore('config', () => { const setters = { fontFamily: (value: string) => safeCall(() => updateEditingConfig('fontFamily', value), 'config.saveFailed', 'config.saveSuccess'), fontWeight: (value: string) => safeCall(() => updateEditingConfig('fontWeight', value), 'config.saveFailed', 'config.saveSuccess'), - dataPath: (value: string) => safeCall(() => updateGeneralConfig('dataPath', value), 'config.saveFailed', 'config.saveSuccess'), + defaultDataPath: (value: string) => safeCall(() => updateGeneralConfig('defaultDataPath', value), 'config.saveFailed', 'config.saveSuccess'), autoSaveDelay: (value: number) => safeCall(() => updateEditingConfig('autoSaveDelay', value), 'config.saveFailed', 'config.saveSuccess'), changeThreshold: (value: number) => safeCall(() => updateEditingConfig('changeThreshold', value), 'config.saveFailed', 'config.saveSuccess'), minSaveInterval: (value: number) => safeCall(() => updateEditingConfig('minSaveInterval', value), 'config.saveFailed', 'config.saveSuccess') @@ -370,13 +381,16 @@ export const useConfigStore = defineStore('config', () => { // 窗口操作 toggleAlwaysOnTop: togglers.alwaysOnTop, + setAlwaysOnTop: (value: boolean) => safeCall(() => updateGeneralConfig('alwaysOnTop', value), 'config.saveFailed', 'config.saveSuccess'), // 字体操作 setFontFamily: setters.fontFamily, setFontWeight: setters.fontWeight, // 路径操作 - setDataPath: setters.dataPath, + setDefaultDataPath: setters.defaultDataPath, + setUseCustomDataPath: (value: boolean) => safeCall(() => updateGeneralConfig('useCustomDataPath', value), 'config.saveFailed', 'config.saveSuccess'), + setCustomDataPath: (value: string) => safeCall(() => updateGeneralConfig('customDataPath', value), 'config.saveFailed', 'config.saveSuccess'), // 保存配置相关方法 setAutoSaveDelay: setters.autoSaveDelay, diff --git a/frontend/src/views/settings/pages/GeneralPage.vue b/frontend/src/views/settings/pages/GeneralPage.vue index 6325b67..5213290 100644 --- a/frontend/src/views/settings/pages/GeneralPage.vue +++ b/frontend/src/views/settings/pages/GeneralPage.vue @@ -1,11 +1,12 @@