From d682b4d5662120a9c290cbfea7e8979f55934517 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E7=8E=8B=E4=B8=80=E4=B9=8B?= Date: Tue, 18 Mar 2025 15:40:39 +0800 Subject: [PATCH] =?UTF-8?q?=E7=BC=96=E8=BE=91=E5=99=A8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- rspack.config.ts | 5 +- src/app/service/service_worker/client.ts | 2 +- src/app/service/service_worker/script.ts | 2 +- src/locales/zh-CN/translation.json | 7 +- src/pages/components/CodeEditor/index.tsx | 4 +- src/pages/install/App.tsx | 6 +- .../options/routes/script/ScriptEditor.tsx | 141 ++++++++++-------- src/pkg/utils/script.ts | 27 ++-- 8 files changed, 111 insertions(+), 83 deletions(-) diff --git a/rspack.config.ts b/rspack.config.ts index 5d611bf..1166fae 100644 --- a/rspack.config.ts +++ b/rspack.config.ts @@ -2,13 +2,12 @@ import * as path from "path"; import { defineConfig } from "@rspack/cli"; import { rspack } from "@rspack/core"; import { version } from "./package.json"; -import CompressionPlugin from "compression-webpack-plugin"; +// eslint-disable-next-line @typescript-eslint/no-require-imports +const CompressionPlugin = require("compression-webpack-plugin"); const isDev = process.env.NODE_ENV === "development"; const isBeta = version.includes("-"); -console.log(CompressionPlugin); - // Target browsers, see: https://github.com/browserslist/browserslist const targets = ["chrome >= 87", "edge >= 88", "firefox >= 78", "safari >= 14"]; diff --git a/src/app/service/service_worker/client.ts b/src/app/service/service_worker/client.ts index 320d39f..a3e639c 100644 --- a/src/app/service/service_worker/client.ts +++ b/src/app/service/service_worker/client.ts @@ -25,7 +25,7 @@ export class ScriptClient extends Client { return this.do("getInstallInfo", uuid); } - install(script: Script, code: string, upsertBy: InstallSource = "user") { + install(script: Script, code: string, upsertBy: InstallSource = "user"): Promise<{ update: boolean }> { return this.do("install", { script, code, upsertBy }); } diff --git a/src/app/service/service_worker/script.ts b/src/app/service/service_worker/script.ts index e7d9c24..31e0caa 100644 --- a/src/app/service/service_worker/script.ts +++ b/src/app/service/service_worker/script.ts @@ -178,7 +178,7 @@ export class ScriptService { logger.info("install success"); // 广播一下 this.mq.publish("installScript", { script, update }); - return Promise.resolve(true); + return Promise.resolve({ update }); }) .catch((e: any) => { logger.error("install error", Logger.E(e)); diff --git a/src/locales/zh-CN/translation.json b/src/locales/zh-CN/translation.json index cd32cbf..ab07633 100644 --- a/src/locales/zh-CN/translation.json +++ b/src/locales/zh-CN/translation.json @@ -31,6 +31,10 @@ "sync_delete": "同步删除", "enable_script_sync_to": "启用脚本同步至", "save": "保存", + "save_as": "另存为", + "file": "文件", + "run": "运行", + "debug": "调试", "cloud_sync_account_verification": "云同步账号信息验证中...", "cloud_sync_verification_failed": "云同步账号信息验证失败", "save_success": "保存成功", @@ -358,5 +362,6 @@ "collapse": "收起", "expand": "展开", "menu_expand_num_before": "菜单项超过", - "menu_expand_num_after": "个时,自动隐藏" + "menu_expand_num_after": "个时,自动隐藏", + "script_name_cannot_be_set_to_empty": "脚本name不可以设置为空" } \ No newline at end of file diff --git a/src/pages/components/CodeEditor/index.tsx b/src/pages/components/CodeEditor/index.tsx index acb5072..ca935aa 100644 --- a/src/pages/components/CodeEditor/index.tsx +++ b/src/pages/components/CodeEditor/index.tsx @@ -12,12 +12,12 @@ type Props = { code?: string; }; -const CodeEditor: React.ForwardRefRenderFunction<{ editor: editor.ICodeEditor | undefined }, Props> = ( +const CodeEditor: React.ForwardRefRenderFunction<{ editor: editor.IStandaloneCodeEditor | undefined }, Props> = ( { id, className, code, diffCode, editable }, ref ) => { const settings = useAppSelector((state) => state.setting); - const [monacoEditor, setEditor] = useState(); + const [monacoEditor, setEditor] = useState(); const div = useRef(null); useImperativeHandle(ref, () => ({ editor: monacoEditor, diff --git a/src/pages/install/App.tsx b/src/pages/install/App.tsx index b882ff5..683387e 100644 --- a/src/pages/install/App.tsx +++ b/src/pages/install/App.tsx @@ -44,7 +44,7 @@ function App() { permission.push({ label: t("subscribe_install_label"), color: "#ff0000", - value: metadata.scripturl, + value: metadata.scripturl!, }); } if (metadata.match) { @@ -311,8 +311,8 @@ function App() {
{oldScript && ( - - {oldScript.metadata.version[0]} + + {oldScript.metadata.version![0]} )} {metadata.version && ( diff --git a/src/pages/options/routes/script/ScriptEditor.tsx b/src/pages/options/routes/script/ScriptEditor.tsx index 366cc3a..bae87fb 100644 --- a/src/pages/options/routes/script/ScriptEditor.tsx +++ b/src/pages/options/routes/script/ScriptEditor.tsx @@ -1,6 +1,6 @@ import { Script, ScriptAndCode, ScriptCodeDAO, ScriptDAO } from "@App/app/repo/scripts"; import CodeEditor from "@App/pages/components/CodeEditor"; -import React, { useEffect, useRef, useState } from "react"; +import React, { useCallback, useEffect, useRef, useState } from "react"; import { useNavigate, useParams, useSearchParams } from "react-router-dom"; import { editor, KeyCode, KeyMod } from "monaco-editor"; import { Button, Dropdown, Grid, Menu, Message, Tabs, Tooltip } from "@arco-design/web-react"; @@ -16,14 +16,15 @@ import { prepareScriptByCode } from "@App/pkg/utils/script"; import ScriptStorage from "@App/pages/components/ScriptStorage"; import ScriptResource from "@App/pages/components/ScriptResource"; import ScriptSetting from "@App/pages/components/ScriptSetting"; +import { scriptClient } from "@App/pages/store/features/script"; +import { useTranslation } from "react-i18next"; const { Row } = Grid; const { Col } = Grid; -// 声明一个Map存储Script -const ScriptMap = new Map(); - type HotKey = { + id: string; + title: string; hotKey: number; action: (script: Script, codeEditor: editor.IStandaloneCodeEditor) => void; }; @@ -35,51 +36,59 @@ const Editor: React.FC<{ callbackEditor: (e: editor.IStandaloneCodeEditor) => void; onChange: (code: string) => void; }> = ({ id, script, hotKeys, callbackEditor, onChange }) => { - const [init, setInit] = useState(false); - const codeEditor = useRef<{ editor: editor.IStandaloneCodeEditor }>(null); - // Script.uuid为key,Script为value,储存Script - ScriptMap.set(script.uuid, script); + const [node, setNode] = useState<{ editor: editor.IStandaloneCodeEditor }>(); + const ref = useCallback<(node: { editor: editor.IStandaloneCodeEditor }) => void>( + (inlineNode) => { + if (inlineNode && inlineNode.editor && !node) { + setNode(inlineNode); + } + }, + [node] + ); useEffect(() => { - if (!codeEditor.current || !codeEditor.current.editor) { - return () => {}; + if (!node || !node.editor) { + return; } - console.log(codeEditor); - // 初始化editor时将Script的uuid绑定到editor上 // @ts-ignore - if (!codeEditor.current.editor.uuid) { + if (!node.editor.uuid) { // @ts-ignore - codeEditor.current.editor.uuid = script.uuid; + node.editor.uuid = script.uuid; } + //@ts-ignore + console.log(node.editor.uuid); hotKeys.forEach((item) => { - codeEditor.current?.editor.addCommand(item.hotKey, () => { - // 获取当前激活的editor(通过editor._focusTracker._hasFocus判断editor激活状态 可能有更好的方法) - const activeEditor = editor - .getEditors() + node.editor.addAction({ + id: item.id, + label: item.title, + keybindings: [item.hotKey], + run(editor) { // @ts-ignore - .find((i) => i._focusTracker._hasFocus); - - // 仅在获取到激活的editor时,通过editor上绑定的uuid获取Script,并指定激活的editor执行快捷键action - if (activeEditor) { - // @ts-ignore - item.action(ScriptMap.get(activeEditor.uuid), activeEditor); - } + item.action(script, editor); + }, }); }); - codeEditor.current.editor.onKeyUp(() => { - onChange(codeEditor.current?.editor.getValue() || ""); + node.editor.onKeyUp(() => { + onChange(node.editor.getValue() || ""); }); - callbackEditor(codeEditor.current.editor); - return () => {}; - }, []); + callbackEditor(node.editor); + return () => { + node.editor.dispose(); + }; + }, [node?.editor]); - return ; + return ; }; +const WarpEditor = React.memo(Editor, (prev, next) => { + return prev.script.uuid === next.script.uuid; +}); + type EditorMenu = { title: string; tooltip?: string; action?: (script: Script, e: editor.IStandaloneCodeEditor) => void; items?: { + id: string; title: string; tooltip?: string; hotKey?: number; @@ -140,10 +149,6 @@ const popstate = () => { }; function ScriptEditor() { - const scriptDAO = new ScriptDAO(); - const scriptCodeDAO = new ScriptCodeDAO(); - const template = useSearchParams()[0].get("template") || ""; - const target = useSearchParams()[0].get("target") || ""; const navigate = useNavigate(); const [visible, setVisible] = useState<{ [key: string]: boolean }>({}); const [editors, setEditors] = useState< @@ -164,6 +169,11 @@ function ScriptEditor() { selectSciptButtonAndTab: string; }>(); const { uuid } = useParams(); + const { t } = useTranslation(); + const template = useSearchParams()[0].get("template") || ""; + const target = useSearchParams()[0].get("target") || ""; + const scriptDAO = new ScriptDAO(); + const scriptCodeDAO = new ScriptCodeDAO(); const setShow = (key: visibleItem, show: boolean) => { Object.keys(visible).forEach((k) => { @@ -175,17 +185,17 @@ function ScriptEditor() { const save = (script: Script, e: editor.IStandaloneCodeEditor): Promise