dsh-sidenote 0.7.3 → 0.7.5
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/lib/client.js
CHANGED
|
@@ -308,6 +308,17 @@ window.__ModuleLoader__.load({
|
|
|
308
308
|
function conversationViewOf(node) {
|
|
309
309
|
return node.closest("[data-conversation-session], [data-sidenote-chat-session]") ?? document.body;
|
|
310
310
|
}
|
|
311
|
+
/** Find the last rendered member of an explicit history range, not the side-chat tail. */
|
|
312
|
+
function lastConversationEntry(root, keys) {
|
|
313
|
+
return [...root.querySelectorAll("[data-chat-flow-key]")].reverse().find((row) => keys.has(row.dataset.chatFlowKey ?? "") && row.getBoundingClientRect().height > 0);
|
|
314
|
+
}
|
|
315
|
+
/** Land above the native composer, without scrolling another pane or moving focus. */
|
|
316
|
+
function revealConversationEntryEnd(row) {
|
|
317
|
+
const scroller = row.closest("[data-conversation-scroll]");
|
|
318
|
+
if (!scroller) return;
|
|
319
|
+
const clip = quoteClipOf(row, conversationViewOf(row));
|
|
320
|
+
scroller.scrollTop += row.getBoundingClientRect().bottom - clip.bottom + 12;
|
|
321
|
+
}
|
|
311
322
|
function hasConversationMessages() {
|
|
312
323
|
return document.querySelector("[data-chat-flow-kind]") !== null;
|
|
313
324
|
}
|
|
@@ -611,7 +622,7 @@ window.__ModuleLoader__.load({
|
|
|
611
622
|
let dockRegistered = false;
|
|
612
623
|
let report = {
|
|
613
624
|
versions: {
|
|
614
|
-
sidenote: "0.7.
|
|
625
|
+
sidenote: "0.7.5",
|
|
615
626
|
dsh: "unknown",
|
|
616
627
|
betterSidebar: null
|
|
617
628
|
},
|
|
@@ -1262,15 +1273,15 @@ window.__ModuleLoader__.load({
|
|
|
1262
1273
|
document.head.appendChild(tag);
|
|
1263
1274
|
}
|
|
1264
1275
|
var diagnostics_module_css_default = {
|
|
1265
|
-
"
|
|
1276
|
+
"versions": "tGe0LW_versions",
|
|
1266
1277
|
"list": "tGe0LW_list",
|
|
1267
1278
|
"header": "tGe0LW_header",
|
|
1268
|
-
"
|
|
1279
|
+
"panel": "tGe0LW_panel",
|
|
1280
|
+
"description": "tGe0LW_description",
|
|
1269
1281
|
"actions": "tGe0LW_actions",
|
|
1270
1282
|
"trigger": "tGe0LW_trigger",
|
|
1271
1283
|
"settingTitle": "tGe0LW_settingTitle",
|
|
1272
|
-
"
|
|
1273
|
-
"description": "tGe0LW_description"
|
|
1284
|
+
"setting": "tGe0LW_setting"
|
|
1274
1285
|
};
|
|
1275
1286
|
//#endregion
|
|
1276
1287
|
//#region src/client/diagnostics/index.tsx
|
|
@@ -2323,7 +2334,7 @@ window.__ModuleLoader__.load({
|
|
|
2323
2334
|
}
|
|
2324
2335
|
//#endregion
|
|
2325
2336
|
//#region \0dsh-css:/home/runner/work/dsh-sidenote/dsh-sidenote/src/client/sidechat/sidechat.module.css.mjs
|
|
2326
|
-
const css$2 = "._5KEEsG_nativeHost,._5KEEsG_root,._5KEEsG_nativeConversation{flex-direction:column;min-height:0;display:flex}._5KEEsG_nativeHost,._5KEEsG_root{height:100%}._5KEEsG_root{color:var(--dsw-alias-label-primary)}._5KEEsG_nativeConversation{flex:1}._5KEEsG_chatView{flex-direction:column;flex:1 0 auto;min-width:0;display:flex}._5KEEsG_mainContext{flex:none;padding:12px 24px 4px}._5KEEsG_historyToggle{align-items:center;gap:6px;display:flex}._5KEEsG_contextHint{color:var(--dsw-alias-label-tertiary);font-size:12px}._5KEEsG_contextChevron{transform:rotate(-90deg)}._5KEEsG_contextChevron,._5KEEsG_contextChevronOpen{flex:none}._5KEEsG_progressEntries{max-height:240px;margin:8px 6px;overflow:auto}._5KEEsG_progressEntry{white-space:pre-wrap;overflow-wrap:anywhere;margin:10px 0;font-size:13px;line-height:1.6}._5KEEsG_root [data-sidenote-progress-snapshot],._5KEEsG_root[data-sidenote-context-pending] [data-submission-echo]{display:none}._5KEEsG_reflowAction{width:32px;height:32px;color:var(--dsw-alias-label-tertiary);cursor:pointer;background:0 0;border:0;border-radius:8px;flex:none;order:1;justify-content:center;align-items:center;margin-left:auto;padding:0;display:inline-flex}._5KEEsG_reflowAction:hover{color:var(--dsw-alias-label-secondary);background:var(--dsw-alias-interactive-bg-hover)}._5KEEsG_reflowAction:focus-visible{outline:2px solid var(--dsw-alias-state-business-primary);outline-offset:2px}._5KEEsG_reflowAction:disabled{cursor:default;color:var(--dsw-alias-state-business-primary);background:0 0}._5KEEsG_nativeToolbar{border-bottom:1px solid var(--dsw-alias-border-l1);justify-content:space-between;align-items:center;gap:8px;padding:8px 12px;display:flex}._5KEEsG_nativeToolbarActions{flex-wrap:wrap;align-items:center;gap:8px;display:flex}._5KEEsG_nativeAction,._5KEEsG_historyToggle{color:var(--dsw-alias-label-secondary);font:inherit;cursor:pointer;background:0 0;border:0;border-radius:6px;padding:4px 6px;font-size:13px}._5KEEsG_nativeAction:hover,._5KEEsG_nativeAction:focus-visible,._5KEEsG_historyToggle:hover,._5KEEsG_historyToggle:focus-visible{color:var(--dsw-alias-label-primary);background:var(--dsw-alias-interactive-bg-hover)}._5KEEsG_nativeAction:disabled{opacity:.5;cursor:default}._5KEEsG_historyToggle{text-align:left;margin:0}._5KEEsG_stateScreen{text-align:center;flex-direction:column;flex:1;justify-content:center;align-items:center;gap:8px;padding:24px 16px;display:flex}._5KEEsG_emptyIcon{color:var(--dsw-alias-label-tertiary)}._5KEEsG_emptyTitle{font-size:14px;font-weight:600}._5KEEsG_emptyText{color:var(--dsw-alias-label-secondary);max-width:280px;font-size:13px;line-height:1.6}._5KEEsG_stateDetail,._5KEEsG_errorRow{color:var(--dsw-alias-state-error-primary);overflow-wrap:anywhere;font-size:13px;line-height:1.6}._5KEEsG_errorRow{padding:8px 12px}._5KEEsG_headerSide{color:var(--dsw-alias-label-secondary);cursor:pointer;font:inherit;background:0 0;border:0;border-radius:6px;align-items:center;gap:4px;padding:4px 8px;display:inline-flex}._5KEEsG_headerSide:hover,._5KEEsG_headerSide:focus-visible{color:var(--dsw-alias-label-primary);background:var(--dsw-alias-interactive-bg-hover)}._5KEEsG_headerSide:disabled{opacity:.4;cursor:default}._5KEEsG_visibilitySetting{justify-content:space-between;align-items:center;gap:16px;padding:8px 0;display:flex}._5KEEsG_visibilitySetting p{color:var(--dsw-alias-label-secondary);margin:4px 0 0;font-size:13px}";
|
|
2337
|
+
const css$2 = "._5KEEsG_nativeHost,._5KEEsG_root,._5KEEsG_nativeConversation{flex-direction:column;min-height:0;display:flex}._5KEEsG_nativeHost,._5KEEsG_root{height:100%}._5KEEsG_root{color:var(--dsw-alias-label-primary)}._5KEEsG_nativeConversation{flex:1}._5KEEsG_chatView{flex-direction:column;flex:1 0 auto;min-width:0;display:flex}._5KEEsG_historyView{display:contents}._5KEEsG_mainContext{flex:none;padding:12px 24px 4px}._5KEEsG_historyToggle{align-items:center;gap:6px;display:flex}._5KEEsG_contextHint{color:var(--dsw-alias-label-tertiary);font-size:12px}._5KEEsG_contextChevron{transform:rotate(-90deg)}._5KEEsG_contextChevron,._5KEEsG_contextChevronOpen{flex:none}._5KEEsG_progressEntries{max-height:240px;margin:8px 6px;overflow:auto}._5KEEsG_progressEntry{white-space:pre-wrap;overflow-wrap:anywhere;margin:10px 0;font-size:13px;line-height:1.6}._5KEEsG_root [data-sidenote-progress-snapshot],._5KEEsG_root[data-sidenote-context-pending] [data-submission-echo]{display:none}._5KEEsG_reflowAction{width:32px;height:32px;color:var(--dsw-alias-label-tertiary);cursor:pointer;background:0 0;border:0;border-radius:8px;flex:none;order:1;justify-content:center;align-items:center;margin-left:auto;padding:0;display:inline-flex}._5KEEsG_reflowAction:hover{color:var(--dsw-alias-label-secondary);background:var(--dsw-alias-interactive-bg-hover)}._5KEEsG_reflowAction:focus-visible{outline:2px solid var(--dsw-alias-state-business-primary);outline-offset:2px}._5KEEsG_reflowAction:disabled{cursor:default;color:var(--dsw-alias-state-business-primary);background:0 0}._5KEEsG_nativeToolbar{border-bottom:1px solid var(--dsw-alias-border-l1);justify-content:space-between;align-items:center;gap:8px;padding:8px 12px;display:flex}._5KEEsG_nativeToolbarActions{flex-wrap:wrap;align-items:center;gap:8px;display:flex}._5KEEsG_nativeAction,._5KEEsG_historyToggle{color:var(--dsw-alias-label-secondary);font:inherit;cursor:pointer;background:0 0;border:0;border-radius:6px;padding:4px 6px;font-size:13px}._5KEEsG_nativeAction:hover,._5KEEsG_nativeAction:focus-visible,._5KEEsG_historyToggle:hover,._5KEEsG_historyToggle:focus-visible{color:var(--dsw-alias-label-primary);background:var(--dsw-alias-interactive-bg-hover)}._5KEEsG_nativeAction:disabled{opacity:.5;cursor:default}._5KEEsG_historyToggle{text-align:left;margin:0}._5KEEsG_stateScreen{text-align:center;flex-direction:column;flex:1;justify-content:center;align-items:center;gap:8px;padding:24px 16px;display:flex}._5KEEsG_emptyIcon{color:var(--dsw-alias-label-tertiary)}._5KEEsG_emptyTitle{font-size:14px;font-weight:600}._5KEEsG_emptyText{color:var(--dsw-alias-label-secondary);max-width:280px;font-size:13px;line-height:1.6}._5KEEsG_stateDetail,._5KEEsG_errorRow{color:var(--dsw-alias-state-error-primary);overflow-wrap:anywhere;font-size:13px;line-height:1.6}._5KEEsG_errorRow{padding:8px 12px}._5KEEsG_headerSide{color:var(--dsw-alias-label-secondary);cursor:pointer;font:inherit;background:0 0;border:0;border-radius:6px;align-items:center;gap:4px;padding:4px 8px;display:inline-flex}._5KEEsG_headerSide:hover,._5KEEsG_headerSide:focus-visible{color:var(--dsw-alias-label-primary);background:var(--dsw-alias-interactive-bg-hover)}._5KEEsG_headerSide:disabled{opacity:.4;cursor:default}._5KEEsG_visibilitySetting{justify-content:space-between;align-items:center;gap:16px;padding:8px 0;display:flex}._5KEEsG_visibilitySetting p{color:var(--dsw-alias-label-secondary);margin:4px 0 0;font-size:13px}";
|
|
2327
2338
|
const tagId$2 = "dsh-sidenote/sidechat.module.css";
|
|
2328
2339
|
if (typeof document !== "undefined" && document.querySelector("style[data-plugin-css=" + JSON.stringify(tagId$2) + "]") === null) {
|
|
2329
2340
|
const tag = document.createElement("style");
|
|
@@ -2333,29 +2344,30 @@ window.__ModuleLoader__.load({
|
|
|
2333
2344
|
document.head.appendChild(tag);
|
|
2334
2345
|
}
|
|
2335
2346
|
var sidechat_module_css_default = {
|
|
2336
|
-
"
|
|
2337
|
-
"nativeAction": "_5KEEsG_nativeAction",
|
|
2338
|
-
"stateScreen": "_5KEEsG_stateScreen",
|
|
2339
|
-
"nativeHost": "_5KEEsG_nativeHost",
|
|
2347
|
+
"emptyTitle": "_5KEEsG_emptyTitle",
|
|
2340
2348
|
"root": "_5KEEsG_root",
|
|
2341
|
-
"
|
|
2342
|
-
"
|
|
2343
|
-
"
|
|
2349
|
+
"historyView": "_5KEEsG_historyView",
|
|
2350
|
+
"contextHint": "_5KEEsG_contextHint",
|
|
2351
|
+
"contextChevronOpen": "_5KEEsG_contextChevronOpen",
|
|
2352
|
+
"progressEntries": "_5KEEsG_progressEntries",
|
|
2353
|
+
"stateScreen": "_5KEEsG_stateScreen",
|
|
2354
|
+
"headerSide": "_5KEEsG_headerSide",
|
|
2344
2355
|
"visibilitySetting": "_5KEEsG_visibilitySetting",
|
|
2345
|
-
"
|
|
2356
|
+
"stateDetail": "_5KEEsG_stateDetail",
|
|
2357
|
+
"errorRow": "_5KEEsG_errorRow",
|
|
2358
|
+
"progressEntry": "_5KEEsG_progressEntry",
|
|
2359
|
+
"nativeToolbar": "_5KEEsG_nativeToolbar",
|
|
2360
|
+
"nativeAction": "_5KEEsG_nativeAction",
|
|
2361
|
+
"nativeHost": "_5KEEsG_nativeHost",
|
|
2346
2362
|
"chatView": "_5KEEsG_chatView",
|
|
2363
|
+
"mainContext": "_5KEEsG_mainContext",
|
|
2347
2364
|
"historyToggle": "_5KEEsG_historyToggle",
|
|
2365
|
+
"nativeToolbarActions": "_5KEEsG_nativeToolbarActions",
|
|
2366
|
+
"emptyIcon": "_5KEEsG_emptyIcon",
|
|
2348
2367
|
"contextChevron": "_5KEEsG_contextChevron",
|
|
2349
|
-
"
|
|
2350
|
-
"nativeToolbar": "_5KEEsG_nativeToolbar",
|
|
2351
|
-
"emptyTitle": "_5KEEsG_emptyTitle",
|
|
2352
|
-
"progressEntry": "_5KEEsG_progressEntry",
|
|
2353
|
-
"contextHint": "_5KEEsG_contextHint",
|
|
2368
|
+
"nativeConversation": "_5KEEsG_nativeConversation",
|
|
2354
2369
|
"reflowAction": "_5KEEsG_reflowAction",
|
|
2355
|
-
"
|
|
2356
|
-
"emptyText": "_5KEEsG_emptyText",
|
|
2357
|
-
"errorRow": "_5KEEsG_errorRow",
|
|
2358
|
-
"headerSide": "_5KEEsG_headerSide"
|
|
2370
|
+
"emptyText": "_5KEEsG_emptyText"
|
|
2359
2371
|
};
|
|
2360
2372
|
//#endregion
|
|
2361
2373
|
//#region src/client/sidechat/NativeConversation.tsx
|
|
@@ -2397,8 +2409,9 @@ window.__ModuleLoader__.load({
|
|
|
2397
2409
|
children: side.contextPending ? t("contextAtSend") : side.progress?.takenAt ? t("contextAsOf", { time: side.progress.takenAt }) : t("contextInherited")
|
|
2398
2410
|
})
|
|
2399
2411
|
]
|
|
2400
|
-
}), expanded && side.progress && /* @__PURE__ */ (0, react_jsx_runtime.jsx)("div", {
|
|
2412
|
+
}), expanded && side.progress && side.progress.entries.length > 0 && /* @__PURE__ */ (0, react_jsx_runtime.jsx)("div", {
|
|
2401
2413
|
className: sidechat_module_css_default.progressEntries,
|
|
2414
|
+
"data-sidenote-context-progress": true,
|
|
2402
2415
|
children: side.progress.entries.map((entry, index) => /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
2403
2416
|
className: sidechat_module_css_default.progressEntry,
|
|
2404
2417
|
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
@@ -2494,6 +2507,8 @@ window.__ModuleLoader__.load({
|
|
|
2494
2507
|
});
|
|
2495
2508
|
}
|
|
2496
2509
|
function HistoryView({ Original, props, side }) {
|
|
2510
|
+
const root = (0, react.useRef)(null);
|
|
2511
|
+
const wasExpanded = (0, react.useRef)(side.contextExpanded);
|
|
2497
2512
|
const nodes = props.useChat((state) => state.nodes);
|
|
2498
2513
|
const snapshot = props.useConversation((state) => state);
|
|
2499
2514
|
const groups = snapshot.views.grouped("chat");
|
|
@@ -2519,9 +2534,31 @@ window.__ModuleLoader__.load({
|
|
|
2519
2534
|
}
|
|
2520
2535
|
};
|
|
2521
2536
|
const useProjected = (0, react.useCallback)((selector) => selector(projected), [projected]);
|
|
2522
|
-
|
|
2523
|
-
|
|
2524
|
-
|
|
2537
|
+
(0, react.useLayoutEffect)(() => {
|
|
2538
|
+
const opening = side.contextExpanded && !wasExpanded.current;
|
|
2539
|
+
wasExpanded.current = side.contextExpanded;
|
|
2540
|
+
if (!opening) return;
|
|
2541
|
+
const keys = new Set(entries.filter(isInherited).map((entry) => entry.key));
|
|
2542
|
+
let frame = requestAnimationFrame(() => {
|
|
2543
|
+
frame = requestAnimationFrame(() => {
|
|
2544
|
+
if (!root.current) return;
|
|
2545
|
+
const progress = root.current.closest("[data-sidenote-transcript]")?.querySelector("[data-sidenote-context-progress]");
|
|
2546
|
+
if (progress) progress.scrollTop = progress.scrollHeight;
|
|
2547
|
+
const target = progress ?? lastConversationEntry(root.current, keys);
|
|
2548
|
+
if (target) revealConversationEntryEnd(target);
|
|
2549
|
+
});
|
|
2550
|
+
});
|
|
2551
|
+
return () => {
|
|
2552
|
+
cancelAnimationFrame(frame);
|
|
2553
|
+
};
|
|
2554
|
+
}, [side.contextExpanded]);
|
|
2555
|
+
return /* @__PURE__ */ (0, react_jsx_runtime.jsx)("div", {
|
|
2556
|
+
ref: root,
|
|
2557
|
+
className: sidechat_module_css_default.historyView,
|
|
2558
|
+
children: (0, react.createElement)(Original, {
|
|
2559
|
+
...props,
|
|
2560
|
+
useConversation: useProjected
|
|
2561
|
+
})
|
|
2525
2562
|
});
|
|
2526
2563
|
}
|
|
2527
2564
|
/** Both admitted hosts publish the native chat View; only 0.2.1 adds a Flow slot. */
|
|
@@ -5555,34 +5592,34 @@ ${entries.map((entry) => {
|
|
|
5555
5592
|
document.head.appendChild(tag);
|
|
5556
5593
|
}
|
|
5557
5594
|
var annotate_module_css_default = {
|
|
5558
|
-
"
|
|
5595
|
+
"sentChip": "_SVViG_sentChip",
|
|
5596
|
+
"sentCardTitle": "_SVViG_sentCardTitle",
|
|
5559
5597
|
"editorSpacer": "_SVViG_editorSpacer",
|
|
5560
|
-
"
|
|
5598
|
+
"toolbarButton": "_SVViG_toolbarButton",
|
|
5599
|
+
"editorInput": "_SVViG_editorInput",
|
|
5600
|
+
"editorTextarea": "_SVViG_editorTextarea",
|
|
5561
5601
|
"confirmButton": "_SVViG_confirmButton",
|
|
5602
|
+
"saveButton": "_SVViG_saveButton",
|
|
5603
|
+
"sentCardQuote": "_SVViG_sentCardQuote",
|
|
5604
|
+
"sentCardNote": "_SVViG_sentCardNote",
|
|
5605
|
+
"badgeSent": "_SVViG_badgeSent",
|
|
5562
5606
|
"hint": "_SVViG_hint",
|
|
5607
|
+
"dshSidenoteHintIn": "_SVViG_dshSidenoteHintIn",
|
|
5608
|
+
"badge": "_SVViG_badge",
|
|
5609
|
+
"editorFooter": "_SVViG_editorFooter",
|
|
5610
|
+
"editorError": "_SVViG_editorError",
|
|
5611
|
+
"editorAskRow": "_SVViG_editorAskRow",
|
|
5612
|
+
"highlight": "_SVViG_highlight",
|
|
5613
|
+
"toolbarBelow": "_SVViG_toolbarBelow",
|
|
5563
5614
|
"sentChipRow": "_SVViG_sentChipRow",
|
|
5564
|
-
"hintClose": "_SVViG_hintClose",
|
|
5565
|
-
"sentCardTitle": "_SVViG_sentCardTitle",
|
|
5566
|
-
"editorTextarea": "_SVViG_editorTextarea",
|
|
5567
|
-
"editorNew": "_SVViG_editorNew",
|
|
5568
5615
|
"editorTarget": "_SVViG_editorTarget",
|
|
5569
|
-
"
|
|
5616
|
+
"hintClose": "_SVViG_hintClose",
|
|
5570
5617
|
"cancelButton": "_SVViG_cancelButton",
|
|
5571
|
-
"dshSidenoteHintIn": "_SVViG_dshSidenoteHintIn",
|
|
5572
|
-
"sentChip": "_SVViG_sentChip",
|
|
5573
|
-
"editorInput": "_SVViG_editorInput",
|
|
5574
|
-
"highlight": "_SVViG_highlight",
|
|
5575
|
-
"toolbarButton": "_SVViG_toolbarButton",
|
|
5576
|
-
"toolbar": "_SVViG_toolbar",
|
|
5577
5618
|
"deleteButton": "_SVViG_deleteButton",
|
|
5619
|
+
"editorNew": "_SVViG_editorNew",
|
|
5578
5620
|
"editorAsk": "_SVViG_editorAsk",
|
|
5579
|
-
"
|
|
5580
|
-
"
|
|
5581
|
-
"sentCardNote": "_SVViG_sentCardNote",
|
|
5582
|
-
"saveButton": "_SVViG_saveButton",
|
|
5583
|
-
"editorAskRow": "_SVViG_editorAskRow",
|
|
5584
|
-
"toolbarBelow": "_SVViG_toolbarBelow",
|
|
5585
|
-
"editorEdit": "_SVViG_editorEdit"
|
|
5621
|
+
"editorEdit": "_SVViG_editorEdit",
|
|
5622
|
+
"toolbar": "_SVViG_toolbar"
|
|
5586
5623
|
};
|
|
5587
5624
|
//#endregion
|
|
5588
5625
|
//#region src/client/annotate/hint.tsx
|
|
@@ -6395,34 +6432,34 @@ ${entries.map((entry) => {
|
|
|
6395
6432
|
document.head.appendChild(tag);
|
|
6396
6433
|
}
|
|
6397
6434
|
var annotations_module_css_default = {
|
|
6398
|
-
"chipClearAll": "SVnebq_chipClearAll",
|
|
6399
|
-
"sentChips": "SVnebq_sentChips",
|
|
6400
|
-
"chipDismissShade": "SVnebq_chipDismissShade",
|
|
6401
|
-
"storageNotice": "SVnebq_storageNotice",
|
|
6402
|
-
"contextText": "SVnebq_contextText",
|
|
6403
|
-
"contextAppear": "SVnebq_contextAppear",
|
|
6404
|
-
"chip": "SVnebq_chip",
|
|
6405
|
-
"contextList": "SVnebq_contextList",
|
|
6406
|
-
"contextActions": "SVnebq_contextActions",
|
|
6407
6435
|
"contextLabel": "SVnebq_contextLabel",
|
|
6436
|
+
"contextPanel": "SVnebq_contextPanel",
|
|
6408
6437
|
"contextAction": "SVnebq_contextAction",
|
|
6438
|
+
"chipMain": "SVnebq_chipMain",
|
|
6439
|
+
"contextEditor": "SVnebq_contextEditor",
|
|
6409
6440
|
"sentChipGroup": "SVnebq_sentChipGroup",
|
|
6410
|
-
"
|
|
6411
|
-
"sentChip": "SVnebq_sentChip",
|
|
6412
|
-
"contextItem": "SVnebq_contextItem",
|
|
6441
|
+
"sentChevron": "SVnebq_sentChevron",
|
|
6413
6442
|
"sentChevronOpen": "SVnebq_sentChevronOpen",
|
|
6414
|
-
"
|
|
6415
|
-
"contextSource": "SVnebq_contextSource",
|
|
6443
|
+
"contextItem": "SVnebq_contextItem",
|
|
6416
6444
|
"sentPreview": "SVnebq_sentPreview",
|
|
6445
|
+
"chip": "SVnebq_chip",
|
|
6446
|
+
"userContextHost": "SVnebq_userContextHost",
|
|
6417
6447
|
"contextNumber": "SVnebq_contextNumber",
|
|
6418
|
-
"
|
|
6419
|
-
"
|
|
6420
|
-
"
|
|
6421
|
-
"
|
|
6422
|
-
"chipDismiss": "SVnebq_chipDismiss",
|
|
6423
|
-
"contextPanel": "SVnebq_contextPanel",
|
|
6448
|
+
"contextSource": "SVnebq_contextSource",
|
|
6449
|
+
"sentChips": "SVnebq_sentChips",
|
|
6450
|
+
"contextList": "SVnebq_contextList",
|
|
6451
|
+
"contextText": "SVnebq_contextText",
|
|
6424
6452
|
"contextContent": "SVnebq_contextContent",
|
|
6425
|
-
"
|
|
6453
|
+
"contextActions": "SVnebq_contextActions",
|
|
6454
|
+
"chipClearAll": "SVnebq_chipClearAll",
|
|
6455
|
+
"chipDismiss": "SVnebq_chipDismiss",
|
|
6456
|
+
"storageNotice": "SVnebq_storageNotice",
|
|
6457
|
+
"sentContext": "SVnebq_sentContext",
|
|
6458
|
+
"sentChip": "SVnebq_sentChip",
|
|
6459
|
+
"chipDismissShade": "SVnebq_chipDismissShade",
|
|
6460
|
+
"contextFooter": "SVnebq_contextFooter",
|
|
6461
|
+
"chipWrap": "SVnebq_chipWrap",
|
|
6462
|
+
"contextAppear": "SVnebq_contextAppear"
|
|
6426
6463
|
};
|
|
6427
6464
|
//#endregion
|
|
6428
6465
|
//#region src/client/annotations/chip.tsx
|
|
@@ -32,6 +32,10 @@ export declare function findSendButtonInCard(root?: ParentNode): HTMLButtonEleme
|
|
|
32
32
|
export declare function composerSessionId(seat: HTMLElement, fallback: string): string;
|
|
33
33
|
/** Bound message hover details to their native conversation pane. */
|
|
34
34
|
export declare function conversationViewOf(node: Element): HTMLElement;
|
|
35
|
+
/** Find the last rendered member of an explicit history range, not the side-chat tail. */
|
|
36
|
+
export declare function lastConversationEntry(root: HTMLElement, keys: ReadonlySet<string>): HTMLElement | undefined;
|
|
37
|
+
/** Land above the native composer, without scrolling another pane or moving focus. */
|
|
38
|
+
export declare function revealConversationEntryEnd(row: HTMLElement): void;
|
|
35
39
|
export declare function isMainComposerInput(target: EventTarget | null): boolean;
|
|
36
40
|
export declare function composerHasMenu(seat: HTMLElement): boolean;
|
|
37
41
|
export declare function hasConversationMessages(): boolean;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "dsh-sidenote",
|
|
3
|
-
"version": "0.7.
|
|
3
|
+
"version": "0.7.5",
|
|
4
4
|
"description": "Follow the tangent. Keep the thread. Annotate, explore on the side, and bring answers back to DeepSeek Harness. / 思路可以分岔,主线始终向前。划选注释、侧边追问,再把结论带回正在推进的任务。",
|
|
5
5
|
"icon": "docs/assets/logo.svg",
|
|
6
6
|
"type": "module",
|
package/src/client/host/dom.ts
CHANGED
|
@@ -89,6 +89,20 @@ export function conversationViewOf(node: Element): HTMLElement {
|
|
|
89
89
|
return node.closest<HTMLElement>('[data-conversation-session], [data-sidenote-chat-session]') ?? document.body
|
|
90
90
|
}
|
|
91
91
|
|
|
92
|
+
/** Find the last rendered member of an explicit history range, not the side-chat tail. */
|
|
93
|
+
export function lastConversationEntry(root: HTMLElement, keys: ReadonlySet<string>): HTMLElement | undefined {
|
|
94
|
+
return [...root.querySelectorAll<HTMLElement>('[data-chat-flow-key]')].reverse()
|
|
95
|
+
.find(row => keys.has(row.dataset.chatFlowKey ?? '') && row.getBoundingClientRect().height > 0)
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
/** Land above the native composer, without scrolling another pane or moving focus. */
|
|
99
|
+
export function revealConversationEntryEnd(row: HTMLElement): void {
|
|
100
|
+
const scroller = row.closest<HTMLElement>('[data-conversation-scroll]')
|
|
101
|
+
if (!scroller) return
|
|
102
|
+
const clip = quoteClipOf(row, conversationViewOf(row))
|
|
103
|
+
scroller.scrollTop += row.getBoundingClientRect().bottom - clip.bottom + 12
|
|
104
|
+
}
|
|
105
|
+
|
|
92
106
|
|
|
93
107
|
export function isMainComposerInput(target: EventTarget | null): boolean {
|
|
94
108
|
return target instanceof HTMLElement
|
|
@@ -1,8 +1,9 @@
|
|
|
1
|
-
import { createContext, createElement, useCallback, useContext, useMemo, useSyncExternalStore, type ComponentType, type ReactNode } from 'react'
|
|
1
|
+
import { createContext, createElement, useCallback, useContext, useLayoutEffect, useMemo, useRef, useSyncExternalStore, type ComponentType, type ReactNode } from 'react'
|
|
2
2
|
import type { Context, SessionReference } from '../host/contracts.ts'
|
|
3
3
|
import { transcriptOf, type ChatMessage } from '../chat/transcript.ts'
|
|
4
4
|
import { createFoldStore } from '../chat/viewState.ts'
|
|
5
5
|
import { completedReplySeqsOf, type ChatReplySnapshot } from '../host/chat.ts'
|
|
6
|
+
import { lastConversationEntry, revealConversationEntryEnd } from '../host/dom.ts'
|
|
6
7
|
import { IconCheckOutline16, IconChevronDownOutline14 } from '../host/icons.ts'
|
|
7
8
|
import type { SnapshotEntry } from './snapshot.ts'
|
|
8
9
|
import { Tooltip } from '@deepseek-ai/dsh-client-ui-primitives'
|
|
@@ -45,7 +46,7 @@ function ChatView(props: { renderSlot(name: 'conversation.session', owner: { vie
|
|
|
45
46
|
<IconChevronDownOutline14 size={12} className={expanded ? css.contextChevronOpen : css.contextChevron} />
|
|
46
47
|
<span>{t('mainContext')}</span><span className={css.contextHint}>{side.contextPending ? t('contextAtSend') : side.progress?.takenAt ? t('contextAsOf', { time: side.progress.takenAt }) : t('contextInherited')}</span>
|
|
47
48
|
</button>
|
|
48
|
-
{expanded && side.progress && <div className={css.progressEntries}>{side.progress.entries.map((entry, index) => <div key={index} className={css.progressEntry}><span className={css.contextHint}>{entry.kind === 'tool' ? entry.toolName : t(`context${entry.kind}`)}</span><div>{entry.text}</div></div>)}</div>}
|
|
49
|
+
{expanded && side.progress && side.progress.entries.length > 0 && <div className={css.progressEntries} data-sidenote-context-progress>{side.progress.entries.map((entry, index) => <div key={index} className={css.progressEntry}><span className={css.contextHint}>{entry.kind === 'tool' ? entry.toolName : t(`context${entry.kind}`)}</span><div>{entry.text}</div></div>)}</div>}
|
|
49
50
|
</div>
|
|
50
51
|
<SideContext.Provider value={{ ...side, contextExpanded: expanded }}>{props.renderSlot('conversation.session', { view: 'chat' })}</SideContext.Provider>
|
|
51
52
|
</div>
|
|
@@ -107,6 +108,8 @@ interface ViewProps {
|
|
|
107
108
|
useConversation<T>(select: (state: ViewSnapshot) => T): T
|
|
108
109
|
}
|
|
109
110
|
function HistoryView({ Original, props, side }: { Original: ComponentType<ViewProps>; props: ViewProps; side: SideConversation }) {
|
|
111
|
+
const root = useRef<HTMLDivElement>(null)
|
|
112
|
+
const wasExpanded = useRef(side.contextExpanded)
|
|
110
113
|
const nodes = props.useChat(state => state.nodes)
|
|
111
114
|
const snapshot = props.useConversation(state => state)
|
|
112
115
|
const groups = snapshot.views.grouped('chat')
|
|
@@ -125,7 +128,27 @@ function HistoryView({ Original, props, side }: { Original: ComponentType<ViewPr
|
|
|
125
128
|
const visible = side.contextExpanded ? entries : entries.filter(entry => !isInherited(entry))
|
|
126
129
|
const projected = { ...snapshot, views: { ...snapshot.views, grouped: (name: string) => name === 'chat' && groups ? { ...groups, entries: visible } : snapshot.views.grouped(name) } }
|
|
127
130
|
const useProjected = useCallback(<T,>(selector: (state: ViewSnapshot) => T): T => selector(projected), [projected])
|
|
128
|
-
|
|
131
|
+
// Only an explicit expansion navigates. Later stream/layout updates and
|
|
132
|
+
// restored fold state leave the host's reader-position policy in charge.
|
|
133
|
+
useLayoutEffect(() => {
|
|
134
|
+
const opening = side.contextExpanded && !wasExpanded.current
|
|
135
|
+
wasExpanded.current = side.contextExpanded
|
|
136
|
+
if (!opening) return
|
|
137
|
+
const keys = new Set(entries.filter(isInherited).map(entry => entry.key))
|
|
138
|
+
// Native Chat settles its content resize first; navigate in the next frame
|
|
139
|
+
// so its initial tail restoration cannot overwrite this explicit action.
|
|
140
|
+
let frame = requestAnimationFrame(() => {
|
|
141
|
+
frame = requestAnimationFrame(() => {
|
|
142
|
+
if (!root.current) return
|
|
143
|
+
const progress = root.current.closest('[data-sidenote-transcript]')?.querySelector<HTMLElement>('[data-sidenote-context-progress]')
|
|
144
|
+
if (progress) progress.scrollTop = progress.scrollHeight
|
|
145
|
+
const target = progress ?? lastConversationEntry(root.current, keys)
|
|
146
|
+
if (target) revealConversationEntryEnd(target)
|
|
147
|
+
})
|
|
148
|
+
})
|
|
149
|
+
return () => { cancelAnimationFrame(frame) }
|
|
150
|
+
}, [side.contextExpanded])
|
|
151
|
+
return <div ref={root} className={css.historyView}>{createElement(Original, { ...props, useConversation: useProjected })}</div>
|
|
129
152
|
}
|
|
130
153
|
|
|
131
154
|
/** Both admitted hosts publish the native chat View; only 0.2.1 adds a Flow slot. */
|
|
@@ -8,6 +8,7 @@
|
|
|
8
8
|
.root { color: var(--dsw-alias-label-primary); }
|
|
9
9
|
.nativeConversation { flex: 1; }
|
|
10
10
|
.chatView { display: flex; flex-direction: column; flex: 1 0 auto; min-width: 0; }
|
|
11
|
+
.historyView { display: contents; }
|
|
11
12
|
.mainContext { flex: none; padding: 12px 24px 4px; }
|
|
12
13
|
.historyToggle { display: flex; align-items: center; gap: 6px; }
|
|
13
14
|
.contextHint { color: var(--dsw-alias-label-tertiary); font-size: 12px; }
|