Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 9 additions & 2 deletions src/pages/components/CodeEditor/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -135,6 +135,8 @@ const CodeEditor: React.ForwardRefRenderFunction<{ editor: editor.IStandaloneCod
largeFileOptimizations: true,
colorDecorators: true,
} as const;
let originalModel: editor.ITextModel | undefined;
let modifiedModel: editor.ITextModel | undefined;
if (diffCode) {
edit = editor.createDiffEditor(inlineDiv, {
hideUnchangedRegions: {
Expand All @@ -146,9 +148,12 @@ const CodeEditor: React.ForwardRefRenderFunction<{ editor: editor.IStandaloneCod
diffWordWrap: "off",
...commonEditorOptions,
});
// standalone model 不会随 editor.dispose 自动清理,需手动跟踪并在 cleanup 释放
originalModel = editor.createModel(diffCode, "javascript");
modifiedModel = editor.createModel(code, "javascript");
edit.setModel({
original: editor.createModel(diffCode, "javascript"),
modified: editor.createModel(code, "javascript"),
original: originalModel,
modified: modifiedModel,
});
} else {
edit = editor.create(inlineDiv, {
Expand All @@ -165,6 +170,8 @@ const CodeEditor: React.ForwardRefRenderFunction<{ editor: editor.IStandaloneCod
// 目前会出现:Uncaught (in promise) Canceled: Canceled
// 问题追踪:https://github.com/microsoft/monaco-editor/issues/4702
edit?.dispose();
originalModel?.dispose();
modifiedModel?.dispose();
};
}, [div, code, diffCode, editable, id]);

Expand Down
55 changes: 37 additions & 18 deletions src/pages/options/routes/script/ScriptEditor.tsx
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import type { Script } from "@App/app/repo/scripts";
import { SCRIPT_TYPE_NORMAL, ScriptCodeDAO, ScriptDAO } from "@App/app/repo/scripts";
import CodeEditor from "@App/pages/components/CodeEditor";
import React, { useCallback, useEffect, useMemo, useState } from "react";
import React, { useCallback, useEffect, useMemo, useRef, useState } from "react";
import { useParams, useSearchParams } from "react-router-dom";
import type { editor } from "monaco-editor";
import type { editor, IDisposable } from "monaco-editor";
import { KeyCode, KeyMod } from "monaco-editor";
import { Button, Dropdown, Grid, Input, Menu, Message, Modal, Space, Tabs, Tooltip } from "@arco-design/web-react";
import TabPane from "@arco-design/web-react/es/Tabs/tab-pane";
Expand Down Expand Up @@ -53,32 +53,51 @@
},
[node]
);
// 用 ref 拿到最新的 hotKeys/onChange/callbackEditor,避免 stale closure
// 同时让 effect 仅在 editor 实例变化时重跑(不会因父组件重渲染重复 addAction)
const hotKeysRef = useRef(hotKeys);
const onChangeRef = useRef(onChange);
const callbackEditorRef = useRef(callbackEditor);
const scriptRef = useRef(script);
hotKeysRef.current = hotKeys;
onChangeRef.current = onChange;
callbackEditorRef.current = callbackEditor;
scriptRef.current = script;

useEffect(() => {
if (!node || !node.editor) {
return;
}
// @ts-ignore
if (!node.editor.uuid) {
// @ts-ignore
node.editor.uuid = script.uuid;
node.editor.uuid = scriptRef.current.uuid;
}
hotKeys.forEach((item) => {
node.editor.addAction({
id: item.id,
label: item.title,
keybindings: [item.hotKey],
run(editor) {
// @ts-ignore
item.action(script, editor);
},
});
});
node.editor.onKeyUp(() => {
onChange(node.editor.getValue() || "");
const disposables: IDisposable[] = [];
hotKeysRef.current.forEach((item) => {
disposables.push(
node.editor.addAction({
id: item.id,
label: item.title,
keybindings: [item.hotKey],
run(editor) {
// @ts-ignore
item.action(scriptRef.current, editor);
},
})
);
});
callbackEditor(node.editor);
return node.editor.dispose.bind(node.editor);
disposables.push(
node.editor.onKeyUp(() => {
onChangeRef.current(node.editor.getValue() || "");
})
);
callbackEditorRef.current(node.editor);
// editor 实例本身由 CodeEditor 自身负责 dispose,这里仅清理本 effect 注册的 listener/action
return () => {
disposables.forEach((d) => d.dispose());
};
}, [node?.editor]);

Check warning on line 100 in src/pages/options/routes/script/ScriptEditor.tsx

View workflow job for this annotation

GitHub Actions / Run tests

React Hook useEffect has a missing dependency: 'node'. Either include it or remove the dependency array

Check warning on line 100 in src/pages/options/routes/script/ScriptEditor.tsx

View workflow job for this annotation

GitHub Actions / Run tests

React Hook useEffect has a missing dependency: 'node'. Either include it or remove the dependency array

return <CodeEditor key={id} id={id} ref={ref} className={className} code={code} diffCode="" editable />;
};
Expand Down Expand Up @@ -468,7 +487,7 @@
return () => {
document.title = "Home - ScriptCat";
};
}, []);

Check warning on line 490 in src/pages/options/routes/script/ScriptEditor.tsx

View workflow job for this annotation

GitHub Actions / Run tests

React Hook useEffect has missing dependencies: 'pageInit', 'pageUrlSearchParams', 'scriptDAO', and 'setPageUrlSearchParams'. Either include them or remove the dependency array

Check warning on line 490 in src/pages/options/routes/script/ScriptEditor.tsx

View workflow job for this annotation

GitHub Actions / Run tests

React Hook useEffect has missing dependencies: 'pageInit', 'pageUrlSearchParams', 'scriptDAO', and 'setPageUrlSearchParams'. Either include them or remove the dependency array

const memoUrlQueryString = useMemo(() => {
return `${pageUrlParams.uuid || ""}|${pageUrlSearchParams.get("template") || ""}|${pageUrlSearchParams.get("target") || ""}|${pageUrlSearchParams.get("d") || ""}`;
Expand Down
9 changes: 8 additions & 1 deletion src/pkg/utils/monaco-editor/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ const langs = {
quickfix: "修复 {0} 问题",
addEslintDisableNextLine: "添加 eslint-disable-next-line 注释",
addEslintDisable: "添加 eslint-disable 注释",
declareGlobal: "将 '{0}' 声明为全局变量 (/* global */)",
prompt: {
name: "脚本名称",
namespace: "脚本命名空间",
Expand Down Expand Up @@ -84,6 +85,7 @@ tracking:该脚本会追踪你的用户信息`.replace(/\n/g, "<br>"),
quickfix: "Fix {0} Issue",
addEslintDisableNextLine: "Add eslint-disable-next-line Comment",
addEslintDisable: "Add eslint-disable Comment",
declareGlobal: "Declare '{0}' as a global variable (/* global */)",
prompt: {
name: "Script name",
namespace: "Script namespace",
Expand Down Expand Up @@ -146,6 +148,7 @@ tracking:该脚本会追踪你的用户信息`.replace(/\n/g, "<br>"),
quickfix: "修復 {0} 問題",
addEslintDisableNextLine: "新增 eslint-disable-next-line 註解",
addEslintDisable: "新增 eslint-disable 註解",
declareGlobal: "將 '{0}' 宣告為全域變數 (/* global */)",
prompt: {
name: "腳本名稱",
namespace: "腳本命名空間",
Expand Down Expand Up @@ -208,6 +211,7 @@ tracking:该脚本会追踪你的用户信息`.replace(/\n/g, "<br>"),
quickfix: "{0} の問題を修正",
addEslintDisableNextLine: "eslint-disable-next-line コメントを追加",
addEslintDisable: "eslint-disable コメントを追加",
declareGlobal: "'{0}' をグローバル変数として宣言 (/* global */)",
prompt: {
name: "スクリプト名",
namespace: "スクリプトの名前空間",
Expand Down Expand Up @@ -270,6 +274,7 @@ tracking:该脚本会追踪你的用户信息`.replace(/\n/g, "<br>"),
quickfix: "{0}-Problem beheben",
addEslintDisableNextLine: "eslint-disable-next-line Kommentar hinzufügen",
addEslintDisable: "eslint-disable Kommentar hinzufügen",
declareGlobal: "'{0}' als globale Variable deklarieren (/* global */)",
prompt: {
name: "Skriptname",
namespace: "Skript-Namensraum",
Expand Down Expand Up @@ -332,6 +337,7 @@ tracking:该脚本会追踪你的用户信息`.replace(/\n/g, "<br>"),
quickfix: "Sửa lỗi {0}",
addEslintDisableNextLine: "Thêm chú thích eslint-disable-next-line",
addEslintDisable: "Thêm chú thích eslint-disable",
declareGlobal: "Khai báo '{0}' là biến toàn cục (/* global */)",
prompt: {
name: "Tên script",
namespace: "Namespace của script",
Expand Down Expand Up @@ -394,6 +400,7 @@ tracking:该脚本会追踪你的用户信息`.replace(/\n/g, "<br>"),
quickfix: "Исправить проблему {0}",
addEslintDisableNextLine: "Добавить комментарий eslint-disable-next-line",
addEslintDisable: "Добавить комментарий eslint-disable",
declareGlobal: "Объявить '{0}' как глобальную переменную (/* global */)",
prompt: {
name: "Имя скрипта",
namespace: "Пространство имён скрипта",
Expand Down Expand Up @@ -587,7 +594,7 @@ export default function registerEditor() {
}

actions.push(<languages.CodeAction>{
title: `将 '${globalName}' 声明为全局变量 (/* global */)`,
title: multiLang.declareGlobal.replace("{0}", globalName),
diagnostics: [val],
kind: "quickfix",
edit: {
Expand Down
Loading