diff --git a/src-tauri/src/main.rs b/src-tauri/src/main.rs index 992a335..b692616 100644 --- a/src-tauri/src/main.rs +++ b/src-tauri/src/main.rs @@ -78,7 +78,7 @@ use process::ProcessRegistryState; use file_watcher::FileWatcherState; use std::sync::Mutex; use tauri::Manager; -use tauri::menu::{MenuBuilder, MenuItemBuilder}; +use tauri::menu::{MenuBuilder, MenuItemBuilder, SubmenuBuilder}; use tauri_plugin_log::{Target, TargetKind}; fn main() { @@ -95,14 +95,30 @@ fn main() { Target::new(TargetKind::Stdout), ]) .build()) - // Add an app menu with DevTools toggle for packaged builds + // App menu: include standard Edit actions so OS hotkeys (Undo/Redo/Cut/Copy/Paste/Select All) + // work across all pages, plus a DevTools toggle. .menu(|app| { let toggle_devtools = MenuItemBuilder::new("Toggle DevTools") .id("toggle-devtools") .accelerator("CmdOrCtrl+Alt+I") .build(app) .unwrap(); + // Create a proper "Edit" submenu (macOS expects standard edit actions under Edit) + let edit_menu = SubmenuBuilder::new(app, "Edit") + .undo() + .redo() + .separator() + .cut() + .copy() + .paste() + .select_all() + .build() + .unwrap(); + MenuBuilder::new(app) + .item(&edit_menu) + .separator() + // DevTools toggle .item(&toggle_devtools) .build() }) diff --git a/src/components/FileEditorEnhanced.tsx b/src/components/FileEditorEnhanced.tsx index 922e588..7fcb381 100644 --- a/src/components/FileEditorEnhanced.tsx +++ b/src/components/FileEditorEnhanced.tsx @@ -1,7 +1,6 @@ import React, { useState, useEffect, useCallback, useRef } from "react"; import { invoke } from "@tauri-apps/api/core"; import { listen, type UnlistenFn } from "@tauri-apps/api/event"; -import { writeText, readText } from "@tauri-apps/plugin-clipboard-manager"; import { X, Save, @@ -390,104 +389,11 @@ export const FileEditorEnhanced: React.FC = ({ }); }); - // 使用简单的复制处理,避免剪贴板权限问题 - editor.addAction({ - id: 'custom-copy', - label: 'Copy', - keybindings: [monaco.KeyMod.CtrlCmd | monaco.KeyCode.KeyC], - contextMenuGroupId: 'navigation', - contextMenuOrder: 1.5, - run: async (ed) => { - const selection = ed.getSelection(); - if (selection) { - const text = ed.getModel()?.getValueInRange(selection); - if (text) { - try { - // 尝试使用 Tauri 的剪贴板 API - await writeText(text).catch(() => { - // 如果失败,使用浏览器原生 API - if (navigator.clipboard && navigator.clipboard.writeText) { - navigator.clipboard.writeText(text).catch(console.error); - } - }); - console.log('[FileEditor] Text copied'); - } catch (err) { - console.error('[FileEditor] Copy failed:', err); - } - } - } - } - }); + // 使用系统默认的复制快捷键,避免拦截导致权限/聚焦问题 - editor.addAction({ - id: 'custom-paste', - label: 'Paste', - keybindings: [monaco.KeyMod.CtrlCmd | monaco.KeyCode.KeyV], - contextMenuGroupId: 'navigation', - contextMenuOrder: 1.6, - run: async (ed) => { - try { - let text = ''; - try { - // 尝试使用 Tauri API - text = await readText(); - } catch { - // 如果失败,使用浏览器原生 API - if (navigator.clipboard && navigator.clipboard.readText) { - text = await navigator.clipboard.readText().catch(() => ''); - } - } - - if (text) { - const selection = ed.getSelection(); - if (selection) { - ed.executeEdits('paste', [{ - range: selection, - text: text, - forceMoveMarkers: true - }]); - } - } - } catch (err) { - console.error('[FileEditor] Paste failed:', err); - } - } - }); + // 使用系统默认的粘贴快捷键(Cmd/Ctrl+V),避免拦截导致无法粘贴 - editor.addAction({ - id: 'custom-cut', - label: 'Cut', - keybindings: [monaco.KeyMod.CtrlCmd | monaco.KeyCode.KeyX], - contextMenuGroupId: 'navigation', - contextMenuOrder: 1.4, - run: async (ed) => { - const selection = ed.getSelection(); - if (selection) { - const text = ed.getModel()?.getValueInRange(selection); - if (text) { - try { - // 尝试复制到剪贴板 - await writeText(text).catch(() => { - if (navigator.clipboard && navigator.clipboard.writeText) { - navigator.clipboard.writeText(text).catch(console.error); - } - }); - - // 删除选中的文本 - ed.executeEdits('cut', [{ - range: selection, - text: '', - forceMoveMarkers: true - }]); - - console.log('[FileEditor] Text cut'); - } catch (err) { - console.error('[FileEditor] Cut failed:', err); - } - } - } - } - }); + // 使用系统默认的剪切快捷键,避免拦截导致不一致行为 // 初始化 Monaco 配置 initializeMonaco();