dsh-plugins-jizuo-creator-writing 0.3.29 → 0.3.31
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -1
- package/node_modules/@jizuo/writing-plugin/README.md +3 -3
- package/node_modules/@jizuo/writing-plugin/lib/client.js +182 -98
- package/node_modules/@jizuo/writing-plugin/lib/index.js +413 -413
- package/node_modules/@jizuo/writing-plugin/node_modules/@jizuo/plugin/README.md +3 -3
- package/node_modules/@jizuo/writing-plugin/node_modules/@jizuo/plugin/lib/client.js +719 -222
- package/node_modules/@jizuo/writing-plugin/node_modules/@jizuo/plugin/lib/dream-worker.js +610 -460
- package/node_modules/@jizuo/writing-plugin/node_modules/@jizuo/plugin/lib/index.js +1165 -1016
- package/node_modules/@jizuo/writing-plugin/node_modules/@jizuo/plugin/lib/typert.host.js +17 -17
- package/node_modules/@jizuo/writing-plugin/node_modules/@jizuo/plugin/lib/workflow-verifier.js +17 -17
- package/node_modules/@jizuo/writing-plugin/node_modules/@jizuo/plugin/package.json +1 -1
- package/node_modules/@jizuo/writing-plugin/package.json +2 -2
- package/package.json +2 -2
package/README.md
CHANGED
|
@@ -12,7 +12,7 @@ dsh-plugins-jizuo-creator-writing
|
|
|
12
12
|
dsh plugin --profile desktop add dsh-plugins-jizuo-creator-writing
|
|
13
13
|
```
|
|
14
14
|
|
|
15
|
-
这是已验证 v0.3.
|
|
15
|
+
这是已验证 v0.3.31 插件包的 npm 安装入口,内含原始插件及共享核心,无需额外安装依赖。
|
|
16
16
|
|
|
17
17
|
已有 GitHub 安装版本时,请先卸载对应的旧安装项,再安装此 npm 包,完成后重启 DSH;卸载插件不会删除作品或对话。不要同时安装同一功能的 GitHub 包与 npm 包。
|
|
18
18
|
|
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
支持 **DeepSeek Harness Desktop 0.2.0-rc.2**。在左侧「插件」→「添加插件」粘贴下面这一行,确认来源后安装:
|
|
8
8
|
|
|
9
9
|
```text
|
|
10
|
-
https://github.com/ShikangPang/jizuo-creator-writing/releases/download/v0.3.
|
|
10
|
+
https://github.com/ShikangPang/jizuo-creator-writing/releases/download/v0.3.31/jizuo-writing-plugin-0.3.31.tgz
|
|
11
11
|
```
|
|
12
12
|
|
|
13
13
|
只填安装包地址,不要填整个安装命令。安装完成后「已安装」中显示「即作写作」,可分别启用、关闭、配置或卸载。共享核心已包含在安装包中,自动加载,不需要另装即作桌面端或手动安装核心插件。保留 Harness 原有新会话、插件与工作区入口;创作项目统一显示在工作区区域,小说和视频以前置图标区分,不再提供独立的创作面板。
|
|
@@ -17,7 +17,7 @@ https://github.com/ShikangPang/jizuo-creator-writing/releases/download/v0.3.29/j
|
|
|
17
17
|
也可使用 Desktop 菜单安装的 dsh 命令:
|
|
18
18
|
|
|
19
19
|
```sh
|
|
20
|
-
dsh plugin --profile desktop add https://github.com/ShikangPang/jizuo-creator-writing/releases/download/v0.3.
|
|
20
|
+
dsh plugin --profile desktop add https://github.com/ShikangPang/jizuo-creator-writing/releases/download/v0.3.31/jizuo-writing-plugin-0.3.31.tgz
|
|
21
21
|
```
|
|
22
22
|
|
|
23
23
|
源码克隆后运行 `node scripts/install.mjs --all` 一次安装五个插件,默认 desktop;Web 用户显式传 `--profile web`。脚本严格检查宿主版本。不要用旧版全局 dsh 命令安装到新版 Desktop,也不要绕过兼容检查。
|
|
@@ -26,7 +26,7 @@ dsh plugin --profile desktop add https://github.com/ShikangPang/jizuo-creator-wr
|
|
|
26
26
|
|
|
27
27
|
启用即作写作插件后,点击工作区列表顶部的“导入小说”。支持 TXT、Markdown 和 DOCX,单文件最大 10 MB。选择文件后预览章节、修改作品名称,确认后创建新的小说项目,展开“正文”即可编辑。取消预览不会创建作品;首章前的内容保留为前言。TXT 支持 UTF-8 和 GB18030 编码。
|
|
28
28
|
|
|
29
|
-
已安装多个即作插件时,请将它们一并更新到 0.3.
|
|
29
|
+
已安装多个即作插件时,请将它们一并更新到 0.3.31,并重启 Harness,使共享核心版本一致。
|
|
30
30
|
|
|
31
31
|
## 项目与数据
|
|
32
32
|
|
|
@@ -114,7 +114,7 @@ window.__ModuleLoader__.load({
|
|
|
114
114
|
}).message;
|
|
115
115
|
}
|
|
116
116
|
//#endregion
|
|
117
|
-
//#region
|
|
117
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/core/core.js
|
|
118
118
|
var _a$1;
|
|
119
119
|
function $constructor(name, initializer, params) {
|
|
120
120
|
function init(inst, def) {
|
|
@@ -173,7 +173,7 @@ window.__ModuleLoader__.load({
|
|
|
173
173
|
return globalConfig;
|
|
174
174
|
}
|
|
175
175
|
//#endregion
|
|
176
|
-
//#region
|
|
176
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/core/util.js
|
|
177
177
|
function getEnumValues(entries) {
|
|
178
178
|
const numericValues = Object.values(entries).filter((v) => typeof v === "number");
|
|
179
179
|
return Object.entries(entries).filter(([k, _]) => numericValues.indexOf(+k) === -1).map(([_, v]) => v);
|
|
@@ -487,7 +487,7 @@ window.__ModuleLoader__.load({
|
|
|
487
487
|
return { ...iss };
|
|
488
488
|
}
|
|
489
489
|
//#endregion
|
|
490
|
-
//#region
|
|
490
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/core/errors.js
|
|
491
491
|
const initializer$1 = (inst, def) => {
|
|
492
492
|
inst.name = "$ZodError";
|
|
493
493
|
Object.defineProperty(inst, "_zod", {
|
|
@@ -547,7 +547,7 @@ window.__ModuleLoader__.load({
|
|
|
547
547
|
return fieldErrors;
|
|
548
548
|
}
|
|
549
549
|
//#endregion
|
|
550
|
-
//#region
|
|
550
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/core/parse.js
|
|
551
551
|
const _parse = (_Err) => (schema, value, _ctx, _params) => {
|
|
552
552
|
const ctx = _ctx ? {
|
|
553
553
|
..._ctx,
|
|
@@ -661,7 +661,7 @@ window.__ModuleLoader__.load({
|
|
|
661
661
|
return _safeParseAsync(_Err)(schema, value, _ctx);
|
|
662
662
|
};
|
|
663
663
|
//#endregion
|
|
664
|
-
//#region
|
|
664
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/core/regexes.js
|
|
665
665
|
/**
|
|
666
666
|
* @deprecated CUID v1 is deprecated by its authors due to information leakage
|
|
667
667
|
* (timestamps embedded in the id). Use {@link cuid2} instead.
|
|
@@ -726,7 +726,7 @@ window.__ModuleLoader__.load({
|
|
|
726
726
|
const lowercase = /^[^A-Z]*$/;
|
|
727
727
|
const uppercase = /^[^a-z]*$/;
|
|
728
728
|
//#endregion
|
|
729
|
-
//#region
|
|
729
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/core/checks.js
|
|
730
730
|
const $ZodCheck = /*@__PURE__*/ $constructor("$ZodCheck", (inst, def) => {
|
|
731
731
|
var _a;
|
|
732
732
|
inst._zod ?? (inst._zod = {});
|
|
@@ -1088,7 +1088,7 @@ window.__ModuleLoader__.load({
|
|
|
1088
1088
|
};
|
|
1089
1089
|
});
|
|
1090
1090
|
//#endregion
|
|
1091
|
-
//#region
|
|
1091
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/core/doc.js
|
|
1092
1092
|
var Doc = class {
|
|
1093
1093
|
constructor(args = []) {
|
|
1094
1094
|
this.content = [];
|
|
@@ -1119,14 +1119,14 @@ window.__ModuleLoader__.load({
|
|
|
1119
1119
|
}
|
|
1120
1120
|
};
|
|
1121
1121
|
//#endregion
|
|
1122
|
-
//#region
|
|
1122
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/core/versions.js
|
|
1123
1123
|
const version = {
|
|
1124
1124
|
major: 4,
|
|
1125
1125
|
minor: 4,
|
|
1126
1126
|
patch: 3
|
|
1127
1127
|
};
|
|
1128
1128
|
//#endregion
|
|
1129
|
-
//#region
|
|
1129
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/core/schemas.js
|
|
1130
1130
|
const $ZodType = /*@__PURE__*/ $constructor("$ZodType", (inst, def) => {
|
|
1131
1131
|
var _a;
|
|
1132
1132
|
inst ?? (inst = {});
|
|
@@ -2443,7 +2443,7 @@ window.__ModuleLoader__.load({
|
|
|
2443
2443
|
}
|
|
2444
2444
|
}
|
|
2445
2445
|
//#endregion
|
|
2446
|
-
//#region
|
|
2446
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/core/registries.js
|
|
2447
2447
|
var _a;
|
|
2448
2448
|
var $ZodRegistry = class {
|
|
2449
2449
|
constructor() {
|
|
@@ -2490,7 +2490,7 @@ window.__ModuleLoader__.load({
|
|
|
2490
2490
|
(_a = globalThis).__zod_globalRegistry ?? (_a.__zod_globalRegistry = registry());
|
|
2491
2491
|
const globalRegistry = globalThis.__zod_globalRegistry;
|
|
2492
2492
|
//#endregion
|
|
2493
|
-
//#region
|
|
2493
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/core/api.js
|
|
2494
2494
|
// @__NO_SIDE_EFFECTS__
|
|
2495
2495
|
function _string(Class, params) {
|
|
2496
2496
|
return new Class({
|
|
@@ -3002,7 +3002,7 @@ window.__ModuleLoader__.load({
|
|
|
3002
3002
|
return ch;
|
|
3003
3003
|
}
|
|
3004
3004
|
//#endregion
|
|
3005
|
-
//#region
|
|
3005
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/core/to-json-schema.js
|
|
3006
3006
|
function initializeContext(params) {
|
|
3007
3007
|
let target = params?.target ?? "draft-2020-12";
|
|
3008
3008
|
if (target === "draft-4") target = "draft-04";
|
|
@@ -3297,7 +3297,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
3297
3297
|
return finalize(ctx, schema);
|
|
3298
3298
|
};
|
|
3299
3299
|
//#endregion
|
|
3300
|
-
//#region
|
|
3300
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/core/json-schema-processors.js
|
|
3301
3301
|
const formatMap = {
|
|
3302
3302
|
guid: "uuid",
|
|
3303
3303
|
url: "uri",
|
|
@@ -3575,7 +3575,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
3575
3575
|
seen.ref = innerType;
|
|
3576
3576
|
};
|
|
3577
3577
|
//#endregion
|
|
3578
|
-
//#region
|
|
3578
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/classic/iso.js
|
|
3579
3579
|
const ZodISODateTime = /*@__PURE__*/ $constructor("ZodISODateTime", (inst, def) => {
|
|
3580
3580
|
$ZodISODateTime.init(inst, def);
|
|
3581
3581
|
ZodStringFormat.init(inst, def);
|
|
@@ -3605,7 +3605,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
3605
3605
|
return /* @__PURE__ */ _isoDuration(ZodISODuration, params);
|
|
3606
3606
|
}
|
|
3607
3607
|
//#endregion
|
|
3608
|
-
//#region
|
|
3608
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/classic/errors.js
|
|
3609
3609
|
const initializer = (inst, issues) => {
|
|
3610
3610
|
$ZodError.init(inst, issues);
|
|
3611
3611
|
inst.name = "ZodError";
|
|
@@ -3627,7 +3627,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
3627
3627
|
};
|
|
3628
3628
|
const ZodRealError = /*@__PURE__*/ $constructor("ZodError", initializer, { Parent: Error });
|
|
3629
3629
|
//#endregion
|
|
3630
|
-
//#region
|
|
3630
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/classic/parse.js
|
|
3631
3631
|
const parse = /* @__PURE__ */ _parse(ZodRealError);
|
|
3632
3632
|
const parseAsync = /* @__PURE__ */ _parseAsync(ZodRealError);
|
|
3633
3633
|
const safeParse = /* @__PURE__ */ _safeParse(ZodRealError);
|
|
@@ -3641,7 +3641,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
3641
3641
|
const safeEncodeAsync = /* @__PURE__ */ _safeEncodeAsync(ZodRealError);
|
|
3642
3642
|
const safeDecodeAsync = /* @__PURE__ */ _safeDecodeAsync(ZodRealError);
|
|
3643
3643
|
//#endregion
|
|
3644
|
-
//#region
|
|
3644
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/zod/v4/classic/schemas.js
|
|
3645
3645
|
const _installedGroups = /* @__PURE__ */ new WeakMap();
|
|
3646
3646
|
function _installLazyMethods(inst, group, methods) {
|
|
3647
3647
|
const proto = Object.getPrototypeOf(inst);
|
|
@@ -7016,7 +7016,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
7016
7016
|
};
|
|
7017
7017
|
}
|
|
7018
7018
|
//#endregion
|
|
7019
|
-
//#region
|
|
7019
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/diff/libesm/diff/base.js
|
|
7020
7020
|
var Diff = class {
|
|
7021
7021
|
diff(oldStr, newStr, options = {}) {
|
|
7022
7022
|
let callback;
|
|
@@ -7194,11 +7194,11 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
7194
7194
|
}
|
|
7195
7195
|
};
|
|
7196
7196
|
//#endregion
|
|
7197
|
-
//#region
|
|
7197
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/diff/libesm/diff/character.js
|
|
7198
7198
|
var CharacterDiff = class extends Diff {};
|
|
7199
7199
|
new CharacterDiff();
|
|
7200
7200
|
//#endregion
|
|
7201
|
-
//#region
|
|
7201
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/diff/libesm/util/string.js
|
|
7202
7202
|
function longestCommonPrefix(str1, str2) {
|
|
7203
7203
|
let i = 0;
|
|
7204
7204
|
for (; i < str1.length && i < str2.length; i++) if (str1[i] != str2[i]) return str1.slice(0, i);
|
|
@@ -7288,7 +7288,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
7288
7288
|
return [/\s/.test(firstSeg) ? firstSeg : "", /\s/.test(lastSeg) ? lastSeg : ""];
|
|
7289
7289
|
}
|
|
7290
7290
|
//#endregion
|
|
7291
|
-
//#region
|
|
7291
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/diff/libesm/diff/word.js
|
|
7292
7292
|
const extendedWordChars = "a-zA-Z0-9_\\u{AD}\\u{C0}-\\u{D6}\\u{D8}-\\u{F6}\\u{F8}-\\u{2C6}\\u{2C8}-\\u{2D7}\\u{2DE}-\\u{2FF}\\u{1E00}-\\u{1EFF}";
|
|
7293
7293
|
const tokenizeIncludingWhitespace = new RegExp(`[${extendedWordChars}]+|\\s+|[^${extendedWordChars}]`, "ug");
|
|
7294
7294
|
var WordDiff = class extends Diff {
|
|
@@ -7396,7 +7396,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
7396
7396
|
};
|
|
7397
7397
|
new WordsWithSpaceDiff();
|
|
7398
7398
|
//#endregion
|
|
7399
|
-
//#region
|
|
7399
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/diff/libesm/diff/line.js
|
|
7400
7400
|
var LineDiff = class extends Diff {
|
|
7401
7401
|
constructor() {
|
|
7402
7402
|
super(...arguments);
|
|
@@ -7429,7 +7429,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
7429
7429
|
return retLines;
|
|
7430
7430
|
}
|
|
7431
7431
|
//#endregion
|
|
7432
|
-
//#region
|
|
7432
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/diff/libesm/diff/sentence.js
|
|
7433
7433
|
function isSentenceEndPunct(char) {
|
|
7434
7434
|
return char == "." || char == "!" || char == "?";
|
|
7435
7435
|
}
|
|
@@ -7456,7 +7456,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
7456
7456
|
};
|
|
7457
7457
|
new SentenceDiff();
|
|
7458
7458
|
//#endregion
|
|
7459
|
-
//#region
|
|
7459
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/diff/libesm/diff/css.js
|
|
7460
7460
|
var CssDiff = class extends Diff {
|
|
7461
7461
|
tokenize(value) {
|
|
7462
7462
|
return value.split(/([{}:;,]|\s+)/);
|
|
@@ -7464,7 +7464,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
7464
7464
|
};
|
|
7465
7465
|
new CssDiff();
|
|
7466
7466
|
//#endregion
|
|
7467
|
-
//#region
|
|
7467
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/diff/libesm/diff/json.js
|
|
7468
7468
|
var JsonDiff = class extends Diff {
|
|
7469
7469
|
constructor() {
|
|
7470
7470
|
super(...arguments);
|
|
@@ -7519,7 +7519,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
7519
7519
|
return canonicalizedObj;
|
|
7520
7520
|
}
|
|
7521
7521
|
//#endregion
|
|
7522
|
-
//#region
|
|
7522
|
+
//#region ../../../../../../stability-release-0.3.30/jizuo-creator-writing/.build/workspace/node_modules/diff/libesm/diff/array.js
|
|
7523
7523
|
var ArrayDiff = class extends Diff {
|
|
7524
7524
|
tokenize(value) {
|
|
7525
7525
|
return value.slice();
|
|
@@ -8029,21 +8029,40 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8029
8029
|
function useAutosave(options) {
|
|
8030
8030
|
const [state, setState] = (0, react.useState)("idle");
|
|
8031
8031
|
const blocked = (0, react.useRef)(false);
|
|
8032
|
+
const saving = (0, react.useRef)(false);
|
|
8033
|
+
const generation = (0, react.useRef)(0);
|
|
8034
|
+
const mounted = (0, react.useRef)(false);
|
|
8035
|
+
const [resume, setResume] = (0, react.useState)(0);
|
|
8032
8036
|
const optionsRef = (0, react.useRef)(options);
|
|
8033
8037
|
optionsRef.current = options;
|
|
8034
8038
|
(0, react.useEffect)(() => {
|
|
8039
|
+
mounted.current = true;
|
|
8040
|
+
return () => {
|
|
8041
|
+
mounted.current = false;
|
|
8042
|
+
generation.current += 1;
|
|
8043
|
+
};
|
|
8044
|
+
}, []);
|
|
8045
|
+
(0, react.useEffect)(() => {
|
|
8046
|
+
generation.current += 1;
|
|
8035
8047
|
blocked.current = false;
|
|
8036
8048
|
setState("idle");
|
|
8037
8049
|
}, [options.resetKey]);
|
|
8038
8050
|
const performSave = (0, react.useCallback)(async (content) => {
|
|
8039
8051
|
const current = optionsRef.current;
|
|
8040
|
-
if (!current.enabled || blocked.current || content === current.savedContent) return;
|
|
8052
|
+
if (!current.enabled || blocked.current || saving.current || content === current.savedContent) return;
|
|
8053
|
+
const savedGeneration = generation.current;
|
|
8054
|
+
const isCurrent = () => mounted.current && generation.current === savedGeneration && optionsRef.current.resetKey === current.resetKey;
|
|
8055
|
+
saving.current = true;
|
|
8056
|
+
let succeeded = false;
|
|
8041
8057
|
setState("saving");
|
|
8042
8058
|
try {
|
|
8043
8059
|
const saved = await current.save(content);
|
|
8060
|
+
if (!isCurrent()) return;
|
|
8061
|
+
succeeded = true;
|
|
8044
8062
|
setState("saved");
|
|
8045
|
-
current.onSaved(saved);
|
|
8063
|
+
optionsRef.current.onSaved(saved, content);
|
|
8046
8064
|
} catch (error) {
|
|
8065
|
+
if (!isCurrent()) return;
|
|
8047
8066
|
if (current.isConflict(error)) {
|
|
8048
8067
|
blocked.current = true;
|
|
8049
8068
|
setState("conflict");
|
|
@@ -8052,10 +8071,13 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8052
8071
|
setState("error");
|
|
8053
8072
|
current.onError(error);
|
|
8054
8073
|
}
|
|
8074
|
+
} finally {
|
|
8075
|
+
saving.current = false;
|
|
8076
|
+
if (mounted.current && (!isCurrent() || succeeded && optionsRef.current.content !== content)) setResume((value) => value + 1);
|
|
8055
8077
|
}
|
|
8056
8078
|
}, []);
|
|
8057
8079
|
(0, react.useEffect)(() => {
|
|
8058
|
-
if (!options.enabled || blocked.current || options.content === options.savedContent) return;
|
|
8080
|
+
if (!options.enabled || blocked.current || saving.current || options.content === options.savedContent) return;
|
|
8059
8081
|
setState("pending");
|
|
8060
8082
|
const timeout = globalThis.setTimeout(() => {
|
|
8061
8083
|
performSave(options.content);
|
|
@@ -8068,6 +8090,8 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8068
8090
|
options.delay,
|
|
8069
8091
|
options.enabled,
|
|
8070
8092
|
options.savedContent,
|
|
8093
|
+
options.resetKey,
|
|
8094
|
+
resume,
|
|
8071
8095
|
performSave
|
|
8072
8096
|
]);
|
|
8073
8097
|
return {
|
|
@@ -8104,12 +8128,20 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8104
8128
|
function hasCode(error, code) {
|
|
8105
8129
|
return typeof error === "object" && error !== null && "code" in error && error.code === code;
|
|
8106
8130
|
}
|
|
8131
|
+
function isSelectionGesture(event) {
|
|
8132
|
+
return event.key.startsWith("Arrow") || [
|
|
8133
|
+
"Home",
|
|
8134
|
+
"End",
|
|
8135
|
+
"PageUp",
|
|
8136
|
+
"PageDown"
|
|
8137
|
+
].includes(event.key) || event.key.toLocaleLowerCase() === "a" && (event.metaKey || event.ctrlKey);
|
|
8138
|
+
}
|
|
8107
8139
|
const BACKGROUND_REFRESH_INTERVAL_MS = 1500;
|
|
8108
8140
|
const HISTORY_READ_TIMEOUT_MS = 15e3;
|
|
8109
8141
|
function createEditSessionId() {
|
|
8110
8142
|
return `edit_${typeof globalThis.crypto?.randomUUID === "function" ? globalThis.crypto.randomUUID().replaceAll("-", "") : `${Date.now().toString(36)}${Math.random().toString(36).slice(2)}`}`;
|
|
8111
8143
|
}
|
|
8112
|
-
function ChapterInspector({ remote, persistence, close,
|
|
8144
|
+
function ChapterInspector({ remote, persistence, close, onSelectionExcerpt, subscribeWorksChanges }) {
|
|
8113
8145
|
const selection = useSelection();
|
|
8114
8146
|
const editorRef = (0, react.useRef)(null);
|
|
8115
8147
|
const draftPersistence = (0, react.useMemo)(() => persistence ?? createDraftPersistence(), [persistence]);
|
|
@@ -8130,7 +8162,17 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8130
8162
|
const [outlineDraft, setOutlineDraft] = (0, react.useState)("");
|
|
8131
8163
|
const [detailedOutlineDraft, setDetailedOutlineDraft] = (0, react.useState)("");
|
|
8132
8164
|
const [activeTab, setActiveTab] = (0, react.useState)("content");
|
|
8133
|
-
const
|
|
8165
|
+
const selectionExcerptCallback = (0, react.useRef)(onSelectionExcerpt);
|
|
8166
|
+
selectionExcerptCallback.current = onSelectionExcerpt;
|
|
8167
|
+
const searchHighlight = (0, react.useRef)(null);
|
|
8168
|
+
const clearAutomaticExcerpt = (0, react.useCallback)(() => {
|
|
8169
|
+
try {
|
|
8170
|
+
if (selectionExcerptCallback.current?.(null) === false) return false;
|
|
8171
|
+
return true;
|
|
8172
|
+
} catch {
|
|
8173
|
+
return false;
|
|
8174
|
+
}
|
|
8175
|
+
}, []);
|
|
8134
8176
|
const [outlineSaveState, setOutlineSaveState] = (0, react.useState)("idle");
|
|
8135
8177
|
const [loading, setLoading] = (0, react.useState)(false);
|
|
8136
8178
|
const [loadError, setLoadError] = (0, react.useState)(null);
|
|
@@ -8149,6 +8191,41 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8149
8191
|
const resizeDragRef = (0, react.useRef)(null);
|
|
8150
8192
|
const visibleDraft = chapter?.liveDraft ?? draft;
|
|
8151
8193
|
const targetKey = target === null ? null : `${target.workId}:${target.volumeId}:${target.chapterId}`;
|
|
8194
|
+
const fullChapterQuote = (0, react.useMemo)(() => {
|
|
8195
|
+
if (target === null || chapter === null || loading || loadError !== null || chapter.id !== target.chapterId || chapter.volumeId !== target.volumeId || chapter.workId !== target.workId || selection.overlay !== "chapter" || activeTab !== "content" || historyOpen || proposals[0] !== void 0 || visibleDraft.trim() === "") return null;
|
|
8196
|
+
return {
|
|
8197
|
+
target,
|
|
8198
|
+
chapterTitle: chapter.title,
|
|
8199
|
+
text: visibleDraft,
|
|
8200
|
+
kind: "chapter"
|
|
8201
|
+
};
|
|
8202
|
+
}, [
|
|
8203
|
+
target,
|
|
8204
|
+
chapter?.id,
|
|
8205
|
+
chapter?.volumeId,
|
|
8206
|
+
chapter?.workId,
|
|
8207
|
+
chapter?.title,
|
|
8208
|
+
visibleDraft,
|
|
8209
|
+
loading,
|
|
8210
|
+
loadError,
|
|
8211
|
+
selection.overlay,
|
|
8212
|
+
activeTab,
|
|
8213
|
+
historyOpen,
|
|
8214
|
+
proposals[0]?.id
|
|
8215
|
+
]);
|
|
8216
|
+
(0, react.useEffect)(() => {
|
|
8217
|
+
searchHighlight.current = null;
|
|
8218
|
+
if (fullChapterQuote === null) {
|
|
8219
|
+
clearAutomaticExcerpt();
|
|
8220
|
+
return;
|
|
8221
|
+
}
|
|
8222
|
+
try {
|
|
8223
|
+
selectionExcerptCallback.current?.(fullChapterQuote);
|
|
8224
|
+
} catch {}
|
|
8225
|
+
}, [fullChapterQuote, clearAutomaticExcerpt]);
|
|
8226
|
+
(0, react.useEffect)(() => () => {
|
|
8227
|
+
clearAutomaticExcerpt();
|
|
8228
|
+
}, [clearAutomaticExcerpt]);
|
|
8152
8229
|
const revisionReader = (0, react.useMemo)(() => {
|
|
8153
8230
|
let active = false;
|
|
8154
8231
|
let pending;
|
|
@@ -8235,12 +8312,20 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8235
8312
|
if (!selection.searchMatch || !chapter || chapter.id !== selection.chapterId || loading) return;
|
|
8236
8313
|
setActiveTab("content");
|
|
8237
8314
|
setHistoryOpen(false);
|
|
8315
|
+
if (fullChapterQuote !== null) try {
|
|
8316
|
+
selectionExcerptCallback.current?.(fullChapterQuote);
|
|
8317
|
+
} catch {}
|
|
8238
8318
|
const frame = requestAnimationFrame(() => {
|
|
8239
8319
|
const editor = editorRef.current;
|
|
8240
8320
|
const match = selection.searchMatch;
|
|
8241
8321
|
if (!editor || !match) return;
|
|
8242
8322
|
const start = chapter.revisionToken === match.revisionToken && visibleDraft === chapter.content ? match.start : visibleDraft.toLocaleLowerCase().indexOf(match.query.toLocaleLowerCase());
|
|
8243
8323
|
if (start >= 0) {
|
|
8324
|
+
searchHighlight.current = {
|
|
8325
|
+
start,
|
|
8326
|
+
end: start + match.query.length,
|
|
8327
|
+
content: visibleDraft
|
|
8328
|
+
};
|
|
8244
8329
|
editor.focus();
|
|
8245
8330
|
editor.setSelectionRange(start, start + match.query.length);
|
|
8246
8331
|
const lineHeight = parseFloat(getComputedStyle(editor).lineHeight) || 24;
|
|
@@ -8256,7 +8341,8 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8256
8341
|
selection.chapterId,
|
|
8257
8342
|
chapter,
|
|
8258
8343
|
loading,
|
|
8259
|
-
visibleDraft
|
|
8344
|
+
visibleDraft,
|
|
8345
|
+
fullChapterQuote
|
|
8260
8346
|
]);
|
|
8261
8347
|
(0, react.useEffect)(() => {
|
|
8262
8348
|
if (!target || !remote.touchDreamActivity) return;
|
|
@@ -8298,7 +8384,6 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8298
8384
|
setDraft("");
|
|
8299
8385
|
setOutlineDraft("");
|
|
8300
8386
|
setDetailedOutlineDraft("");
|
|
8301
|
-
setSelectedExcerpt("");
|
|
8302
8387
|
setLoadError(null);
|
|
8303
8388
|
setActionNotice(null);
|
|
8304
8389
|
return;
|
|
@@ -8317,7 +8402,6 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8317
8402
|
setDraft(matchingDraft?.content ?? next.content);
|
|
8318
8403
|
setOutlineDraft(next.outline);
|
|
8319
8404
|
setDetailedOutlineDraft(next.detailedOutline);
|
|
8320
|
-
setSelectedExcerpt("");
|
|
8321
8405
|
setOutlineSaveState("idle");
|
|
8322
8406
|
}).catch((cause) => {
|
|
8323
8407
|
if (active) setLoadError(messageOf$1(cause));
|
|
@@ -8453,7 +8537,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8453
8537
|
resetKey: target === null || chapter === null ? null : `${target.workId}:${target.volumeId}:${target.chapterId}:${chapter.revisionToken}`,
|
|
8454
8538
|
content: draft,
|
|
8455
8539
|
savedContent: chapter?.content ?? "",
|
|
8456
|
-
enabled: target !== null && chapter !== null && chapter.liveDraft === void 0,
|
|
8540
|
+
enabled: target !== null && chapter !== null && chapter.liveDraft === void 0 && chapter.id === target.chapterId && chapter.volumeId === target.volumeId && chapter.workId === target.workId,
|
|
8457
8541
|
delay: 800,
|
|
8458
8542
|
save: async (content) => {
|
|
8459
8543
|
if (target === null || chapter === null) throw new Error("没有选中的章节");
|
|
@@ -8470,8 +8554,14 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8470
8554
|
});
|
|
8471
8555
|
},
|
|
8472
8556
|
isConflict: (cause) => hasCode(cause, "revision_conflict"),
|
|
8473
|
-
onSaved: (next) => {
|
|
8474
|
-
|
|
8557
|
+
onSaved: (next, submittedContent) => {
|
|
8558
|
+
const content = draft === submittedContent ? next.content : draft;
|
|
8559
|
+
setChapter(next);
|
|
8560
|
+
setDraft(content);
|
|
8561
|
+
if (target !== null) draftPersistence.save(target, {
|
|
8562
|
+
content,
|
|
8563
|
+
revisionToken: next.revisionToken
|
|
8564
|
+
});
|
|
8475
8565
|
refreshRevisions();
|
|
8476
8566
|
},
|
|
8477
8567
|
onConflict: () => {
|
|
@@ -8489,7 +8579,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8489
8579
|
};
|
|
8490
8580
|
else editSessionRef.current.lastChangedAt = now;
|
|
8491
8581
|
setDraft(content);
|
|
8492
|
-
|
|
8582
|
+
searchHighlight.current = null;
|
|
8493
8583
|
setActionNotice(null);
|
|
8494
8584
|
if (target !== null && chapter !== null) draftPersistence.save(target, {
|
|
8495
8585
|
content,
|
|
@@ -8497,32 +8587,25 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8497
8587
|
});
|
|
8498
8588
|
};
|
|
8499
8589
|
const captureExcerpt = (editor) => {
|
|
8590
|
+
if (onSelectionExcerpt === void 0 || fullChapterQuote === null || selection.searchMatch !== void 0 || document.activeElement !== editor) return;
|
|
8591
|
+
const highlighted = searchHighlight.current;
|
|
8592
|
+
if (highlighted !== null && highlighted.content === editor.value && highlighted.start === editor.selectionStart && highlighted.end === editor.selectionEnd) return;
|
|
8593
|
+
searchHighlight.current = null;
|
|
8500
8594
|
const text = editor.value.slice(editor.selectionStart, editor.selectionEnd).trim();
|
|
8501
|
-
setSelectedExcerpt(text.slice(0, 6e3));
|
|
8502
|
-
};
|
|
8503
|
-
const quoteSelectedExcerpt = () => {
|
|
8504
|
-
if (target === null || chapter === null || onQuoteExcerpt === void 0) return;
|
|
8505
|
-
const quoteText = selectedExcerpt === "" ? visibleDraft.trim() : selectedExcerpt;
|
|
8506
|
-
if (quoteText === "") return;
|
|
8507
|
-
setActionError(null);
|
|
8508
|
-
setActionNotice(null);
|
|
8509
|
-
let inserted = false;
|
|
8510
8595
|
try {
|
|
8511
|
-
|
|
8512
|
-
target,
|
|
8513
|
-
chapterTitle:
|
|
8514
|
-
text
|
|
8515
|
-
})
|
|
8596
|
+
if (!onSelectionExcerpt(text === "" ? fullChapterQuote : {
|
|
8597
|
+
target: fullChapterQuote.target,
|
|
8598
|
+
chapterTitle: fullChapterQuote.chapterTitle,
|
|
8599
|
+
text
|
|
8600
|
+
})) {
|
|
8601
|
+
if (text !== "") setActionError("当前对话正在发送或暂不可用,请稍后重新选择。");
|
|
8602
|
+
return;
|
|
8603
|
+
}
|
|
8604
|
+
setActionError(null);
|
|
8605
|
+
setActionNotice(null);
|
|
8516
8606
|
} catch (cause) {
|
|
8517
|
-
setActionError(`引用失败:${messageOf$1(cause)}`);
|
|
8518
|
-
return;
|
|
8519
|
-
}
|
|
8520
|
-
if (!inserted) {
|
|
8521
|
-
setActionError("当前对话不可用,请先打开该作品的对话后重试。");
|
|
8522
|
-
return;
|
|
8607
|
+
if (text !== "") setActionError(`引用失败:${messageOf$1(cause)}`);
|
|
8523
8608
|
}
|
|
8524
|
-
setActionNotice(selectedExcerpt === "" ? "已将整章引用到当前对话" : "已将选段引用到当前对话");
|
|
8525
|
-
setSelectedExcerpt("");
|
|
8526
8609
|
};
|
|
8527
8610
|
const applyProposal = async (proposal) => {
|
|
8528
8611
|
if (remote.authorizeProposal === void 0 || remote.applyProposal === void 0) return;
|
|
@@ -8709,44 +8792,33 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8709
8792
|
]
|
|
8710
8793
|
}), activeTab === "content" ? /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
8711
8794
|
className: "jz-inspector-save-actions",
|
|
8712
|
-
children: [
|
|
8713
|
-
|
|
8714
|
-
|
|
8715
|
-
|
|
8716
|
-
|
|
8717
|
-
|
|
8718
|
-
|
|
8719
|
-
|
|
8720
|
-
|
|
8721
|
-
|
|
8722
|
-
|
|
8723
|
-
|
|
8724
|
-
|
|
8725
|
-
|
|
8726
|
-
|
|
8727
|
-
|
|
8728
|
-
|
|
8729
|
-
|
|
8730
|
-
|
|
8731
|
-
|
|
8732
|
-
|
|
8733
|
-
|
|
8734
|
-
proposals[0] === void 0 && /* @__PURE__ */ (0, react_jsx_runtime.jsx)(IconButton, {
|
|
8735
|
-
icon: "save",
|
|
8736
|
-
label: "保存正文",
|
|
8737
|
-
type: "button",
|
|
8738
|
-
disabled: chapter.liveDraft !== void 0 || autosave.state === "saving" || autosave.state === "conflict",
|
|
8739
|
-
onClick: () => {
|
|
8740
|
-
setActionError(null);
|
|
8741
|
-
if (draft === chapter.content) {
|
|
8742
|
-
setActionNotice("正文已经保存");
|
|
8743
|
-
return;
|
|
8744
|
-
}
|
|
8745
|
-
setActionNotice(null);
|
|
8746
|
-
autosave.saveNow();
|
|
8795
|
+
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)(IconButton, {
|
|
8796
|
+
icon: "history",
|
|
8797
|
+
label: revisions.length > 0 ? `历史版本(${revisions.length})` : "历史版本",
|
|
8798
|
+
type: "button",
|
|
8799
|
+
"aria-controls": "jz-chapter-history",
|
|
8800
|
+
"aria-expanded": historyOpen,
|
|
8801
|
+
onClick: () => {
|
|
8802
|
+
setHistoryOpen((open) => {
|
|
8803
|
+
if (!open) refreshRevisions(true);
|
|
8804
|
+
return !open;
|
|
8805
|
+
});
|
|
8806
|
+
}
|
|
8807
|
+
}), proposals[0] === void 0 && /* @__PURE__ */ (0, react_jsx_runtime.jsx)(IconButton, {
|
|
8808
|
+
icon: "save",
|
|
8809
|
+
label: "保存正文",
|
|
8810
|
+
type: "button",
|
|
8811
|
+
disabled: chapter.liveDraft !== void 0 || autosave.state === "saving" || autosave.state === "conflict",
|
|
8812
|
+
onClick: () => {
|
|
8813
|
+
setActionError(null);
|
|
8814
|
+
if (draft === chapter.content) {
|
|
8815
|
+
setActionNotice("正文已经保存");
|
|
8816
|
+
return;
|
|
8747
8817
|
}
|
|
8748
|
-
|
|
8749
|
-
|
|
8818
|
+
setActionNotice(null);
|
|
8819
|
+
autosave.saveNow();
|
|
8820
|
+
}
|
|
8821
|
+
})]
|
|
8750
8822
|
}) : activeTab === "workflow" ? null : /* @__PURE__ */ (0, react_jsx_runtime.jsx)(IconButton, {
|
|
8751
8823
|
icon: "save",
|
|
8752
8824
|
label: activeTab === "outline" ? "保存大纲" : "保存细纲",
|
|
@@ -8821,6 +8893,18 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
8821
8893
|
},
|
|
8822
8894
|
onSelect: (event) => {
|
|
8823
8895
|
captureExcerpt(event.currentTarget);
|
|
8896
|
+
},
|
|
8897
|
+
onPointerDown: () => {
|
|
8898
|
+
searchHighlight.current = null;
|
|
8899
|
+
},
|
|
8900
|
+
onPointerUp: (event) => {
|
|
8901
|
+
captureExcerpt(event.currentTarget);
|
|
8902
|
+
},
|
|
8903
|
+
onKeyDown: (event) => {
|
|
8904
|
+
if (isSelectionGesture(event)) searchHighlight.current = null;
|
|
8905
|
+
},
|
|
8906
|
+
onKeyUp: (event) => {
|
|
8907
|
+
if (isSelectionGesture(event)) captureExcerpt(event.currentTarget);
|
|
8824
8908
|
}
|
|
8825
8909
|
})]
|
|
8826
8910
|
}),
|
|
@@ -9080,7 +9164,7 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
|
|
|
9080
9164
|
remote,
|
|
9081
9165
|
subscribeWorksChanges: changes,
|
|
9082
9166
|
close,
|
|
9083
|
-
|
|
9167
|
+
onSelectionExcerpt: host.conversation?.syncChapterSelection ? (quote) => host.conversation.syncChapterSelection(quote) : void 0
|
|
9084
9168
|
})
|
|
9085
9169
|
}, ChapterInspector),
|
|
9086
9170
|
volume: () => host.slots.register({
|