dsh-live2dwaifu 1.3.1 → 2.0.0
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 +16 -0
- package/assets/corpus.html +4 -5
- package/assets/mobile.html +1 -0
- package/assets/tone.html +19 -12
- package/assets/viewer.js +0 -1
- package/lib/client.js +11 -1
- package/lib/index.js +12 -2
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -380,6 +380,20 @@ curl -X POST http://127.0.0.1:<端口>/dsh-live2d/api/push \
|
|
|
380
380
|
|
|
381
381
|
版本号怎么走:动了功能和结构就抬第二位(1.2.0),只补洞和小修就抬第三位(1.2.1)。
|
|
382
382
|
|
|
383
|
+
### 2.0.0
|
|
384
|
+
|
|
385
|
+
- 修:`ISOLATION` 这个变量在 1.3.0 被误删,`/api/chat` 全部返回 500——那之后她其实一句都说不出来。这是这版最主要的问题。
|
|
386
|
+
- 修:补回 1.3.1 里漏掉的语料接口(之前保存语料会 404)。
|
|
387
|
+
- 修:调音页的下拉框改成只试听,不再顺手把正在显示的模型换掉;要换模型另点「切到这只模型」。
|
|
388
|
+
- 修:卡片位置存在本机,窗口缩小后可能跑到屏幕外,现在重开时自动收回可见范围。
|
|
389
|
+
- 修:页面切到后台时暂停轮询,不再空跑请求。
|
|
390
|
+
- 修:所有接受模型 id 的接口加了字符校验,避免拼出奇怪路径。
|
|
391
|
+
- 改:对话要求补一条——不要每句都反问,不要用「哈哈」「嗯嗯」凑字数。
|
|
392
|
+
- 清:删掉几个没用到的常量、开关和恒真判断。
|
|
393
|
+
|
|
394
|
+
<details>
|
|
395
|
+
<summary>2.0.0 之前的记录(黑历史,留着自嘲)</summary>
|
|
396
|
+
|
|
383
397
|
### 1.3.1
|
|
384
398
|
|
|
385
399
|
- 修:语料接口整个漏掉了(页面打得开,存不进去,返回 404)。补回来。
|
|
@@ -457,6 +471,8 @@ curl -X POST http://127.0.0.1:<端口>/dsh-live2d/api/push \
|
|
|
457
471
|
- 人设卡编辑页、音色调色页。
|
|
458
472
|
- 对外接口:`/api/chat`、`/api/push`、`/api/poll`。
|
|
459
473
|
|
|
474
|
+
</details>
|
|
475
|
+
|
|
460
476
|
## 反馈
|
|
461
477
|
|
|
462
478
|
遇到问题、想要新功能、觉得哪句话还是像 AI,都可以写信到 **FujiwaraReisen@outlook.com**。
|
package/assets/corpus.html
CHANGED
|
@@ -147,11 +147,10 @@
|
|
|
147
147
|
var said = unquote(m[2]);
|
|
148
148
|
if (!said) continue;
|
|
149
149
|
if (USERS.test(who)) { pending = said; continue; }
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
}
|
|
150
|
+
// 不是「他/我/用户」的说话人,一律当角色
|
|
151
|
+
pairs.push({ user: pending || '', assistant: said });
|
|
152
|
+
pending = null;
|
|
153
|
+
continue;
|
|
155
154
|
}
|
|
156
155
|
var t = unquote(line);
|
|
157
156
|
if (t) lines.push(t);
|
package/assets/mobile.html
CHANGED
package/assets/tone.html
CHANGED
|
@@ -91,6 +91,7 @@
|
|
|
91
91
|
|
|
92
92
|
<div class="foot">
|
|
93
93
|
<button class="act primary" id="save">保存</button>
|
|
94
|
+
<button class="act" id="useModel">切到这只模型</button>
|
|
94
95
|
<button class="act" id="reset">恢复默认</button>
|
|
95
96
|
<span class="state" id="state"></span>
|
|
96
97
|
</div>
|
|
@@ -205,21 +206,27 @@
|
|
|
205
206
|
|
|
206
207
|
sel.addEventListener('change', function () {
|
|
207
208
|
modelId = sel.value;
|
|
208
|
-
loadVoice(
|
|
209
|
+
loadVoice();
|
|
209
210
|
});
|
|
210
211
|
|
|
211
|
-
function
|
|
212
|
+
$('useModel').addEventListener('click', function () {
|
|
212
213
|
if (!modelId) return;
|
|
213
|
-
state.textContent = '
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
214
|
+
state.textContent = '切换中';
|
|
215
|
+
fetch('/dsh-live2d/api/select', {
|
|
216
|
+
method: 'POST',
|
|
217
|
+
headers: { 'content-type': 'application/json' },
|
|
218
|
+
body: JSON.stringify({ id: modelId })
|
|
219
|
+
})
|
|
220
|
+
.then(function () {
|
|
220
221
|
frame.src = '/dsh-live2d/viewer?embed=1&t=' + Date.now();
|
|
221
|
-
|
|
222
|
-
|
|
222
|
+
state.textContent = '已切换';
|
|
223
|
+
})
|
|
224
|
+
.catch(function (e) { state.textContent = '切换失败:' + e.message; });
|
|
225
|
+
});
|
|
226
|
+
|
|
227
|
+
function loadVoice() {
|
|
228
|
+
if (!modelId) return;
|
|
229
|
+
state.textContent = '读取中';
|
|
223
230
|
fetch('/dsh-live2d/api/voice?id=' + encodeURIComponent(modelId))
|
|
224
231
|
.then(function (r) { return r.json(); })
|
|
225
232
|
.then(function (d) {
|
|
@@ -249,7 +256,7 @@
|
|
|
249
256
|
state.textContent = '尚未导入模型';
|
|
250
257
|
return;
|
|
251
258
|
}
|
|
252
|
-
loadVoice(
|
|
259
|
+
loadVoice();
|
|
253
260
|
})
|
|
254
261
|
.catch(function (e) { state.textContent = '读取模型列表失败:' + e.message; });
|
|
255
262
|
|
package/assets/viewer.js
CHANGED
|
@@ -44358,7 +44358,6 @@ void main(void)\r
|
|
|
44358
44358
|
follow: "\u804A\u5929\u7A97\u53E3\u51FA\u73B0\u65B0\u56DE\u590D\u65F6\uFF0C\u7531\u89D2\u8272\u5FF5\u51FA\u6765"
|
|
44359
44359
|
};
|
|
44360
44360
|
var SERVER_HINT = {
|
|
44361
|
-
proactive: "\u4E00\u6BB5\u65F6\u95F4\u6CA1\u4EBA\u8BF4\u8BDD\uFF0C\u89D2\u8272\u81EA\u5DF1\u5F00\u4E00\u53E5",
|
|
44362
44361
|
choices: "\u89D2\u8272\u89C9\u5F97\u9700\u8981\u9009\u62E9\u65F6\uFF0C\u6C14\u6CE1\u4E0A\u65B9\u51FA\u73B0\u53EF\u70B9\u7684\u6309\u94AE",
|
|
44363
44362
|
memory: "\u4FDD\u7559\u804A\u8FC7\u7684\u5185\u5BB9\uFF0C\u4E0B\u6B21\u63A5\u7740\u804A\uFF08\u5360\u66F4\u591A\u6A21\u578B\u989D\u5EA6\uFF09"
|
|
44364
44363
|
};
|
package/lib/client.js
CHANGED
|
@@ -121,6 +121,16 @@
|
|
|
121
121
|
react.useEffect(() => localStorage.setItem('dsh-l2d-bg', bg), [bg]);
|
|
122
122
|
react.useEffect(() => localStorage.setItem('dsh-l2d-size', JSON.stringify(size)), [size]);
|
|
123
123
|
react.useEffect(() => localStorage.setItem('dsh-l2d-pos', JSON.stringify(pos)), [pos]);
|
|
124
|
+
react.useEffect(() => {
|
|
125
|
+
setPos((p) => {
|
|
126
|
+
const w = size.w;
|
|
127
|
+
const h = open ? size.h : 38;
|
|
128
|
+
const x = Math.max(-w + 90, Math.min(window.innerWidth - 90, p.x));
|
|
129
|
+
const y = Math.max(-h + 50, Math.min(window.innerHeight - 50, p.y));
|
|
130
|
+
return x === p.x && y === p.y ? p : { x, y };
|
|
131
|
+
});
|
|
132
|
+
// eslint-disable-next-line react-hooks/exhaustive-deps
|
|
133
|
+
}, []);
|
|
124
134
|
react.useEffect(() => {
|
|
125
135
|
frameWin = (ref.current && ref.current.contentWindow) || null;
|
|
126
136
|
}, [nonce, open]);
|
|
@@ -128,7 +138,7 @@
|
|
|
128
138
|
let seq = null;
|
|
129
139
|
let stop = false;
|
|
130
140
|
const tick = () => {
|
|
131
|
-
if (stop) return;
|
|
141
|
+
if (stop || document.hidden) return;
|
|
132
142
|
fetch(BASE + '/api/poll?since=' + (seq === null ? 0 : seq))
|
|
133
143
|
.then((r) => r.json())
|
|
134
144
|
.then((d) => {
|
package/lib/index.js
CHANGED
|
@@ -24,7 +24,6 @@ const MEME_TAGS = {
|
|
|
24
24
|
};
|
|
25
25
|
|
|
26
26
|
const DEFAULT_SETTINGS = {
|
|
27
|
-
proactive: true,
|
|
28
27
|
/** 多久没人说话才自己开口,单位分钟;0 = 关闭 */
|
|
29
28
|
proactiveInterval: 30,
|
|
30
29
|
/** off | own | both | external —— 测试功能,默认关 */
|
|
@@ -175,6 +174,13 @@ const TALK_SAMPLES = [
|
|
|
175
174
|
'他:明天要早起 —— 你:那我今晚早点关灯。',
|
|
176
175
|
].join('\n');
|
|
177
176
|
|
|
177
|
+
/** 世界隔离:不说破自己在哪儿 */
|
|
178
|
+
const ISOLATION = [
|
|
179
|
+
'【世界隔离】你不知道什么是程序、界面、插件、模型、参数。',
|
|
180
|
+
'有人问起,你就当他就站在你身边。不要提“系统”“设置”“网页”“token”这些词。',
|
|
181
|
+
'你不知道他那边什么样,得他讲给你听。',
|
|
182
|
+
].join('\n');
|
|
183
|
+
|
|
178
184
|
/** 语料:lines = 她的台词,pairs = 一问一答 */
|
|
179
185
|
function readCorpus(id) {
|
|
180
186
|
try {
|
|
@@ -404,7 +410,6 @@ async function generate(slot, prompt, limit = 900) {
|
|
|
404
410
|
}
|
|
405
411
|
|
|
406
412
|
/* ── 主动开口:没人说话,她自己开一句 ─────────────────────── */
|
|
407
|
-
const IDLE_MS = 12 * 60 * 1000;
|
|
408
413
|
let lastAutoAt = 0;
|
|
409
414
|
|
|
410
415
|
async function maybeTalk(ctx) {
|
|
@@ -523,7 +528,12 @@ function findModel3(dir) {
|
|
|
523
528
|
return out[0];
|
|
524
529
|
}
|
|
525
530
|
|
|
531
|
+
function validId(id) {
|
|
532
|
+
return /^[\w.-]+$/.test(String(id || ''));
|
|
533
|
+
}
|
|
534
|
+
|
|
526
535
|
function readMeta(id) {
|
|
536
|
+
if (!validId(id)) return null;
|
|
527
537
|
try {
|
|
528
538
|
return JSON.parse(readFileSync(join(MODELS, id, 'meta.json'), 'utf8'));
|
|
529
539
|
} catch {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "dsh-live2dwaifu",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "2.0.0",
|
|
4
4
|
"description": "给 DSH 网页右下角请一个 Live2D 角色:会眨眼、会呼吸、视线跟着鼠标、点她有反应、说话时嘴动、心情变了眉毛跟着动。模型不用内置——谁装谁放自己的文件夹;支持自定义 .exp3.json 表情和 .motion3.json 动作,卡片能拖能缩,背景可换。",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "lib/index.js",
|