dsh-tide-theme 0.5.0 → 0.5.2

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 CHANGED
@@ -220,7 +220,7 @@ dsh plugin --profile desktop add git+https://github.com/zdt3476/dsh-tide-theme.g
220
220
  dsh plugin --profile desktop add link:"$PWD"
221
221
 
222
222
  # GitHub Release 预构建包
223
- dsh plugin --profile desktop add https://github.com/zdt3476/dsh-tide-theme/releases/download/v0.5.0/dsh-tide-theme-0.5.0.tgz
223
+ dsh plugin --profile desktop add https://github.com/zdt3476/dsh-tide-theme/releases/download/v0.5.2/dsh-tide-theme-0.5.2.tgz
224
224
  ```
225
225
 
226
226
  安装后在 **设置 → 插件** 中启用,并按下 `Cmd/Ctrl + R` 重载客户端。
@@ -235,7 +235,7 @@ pnpm test # TypeScript 类型检查 + Vitest 单元测试(110 tests)
235
235
  pnpm build # 编译产出 lib/index.js (Host) 与 lib/client.js (Client)
236
236
  pnpm check # test + build 全量流水线检查
237
237
 
238
- # 浏览器契约测试(真实 Chromium,54 项)
238
+ # 浏览器契约测试(真实 Chromium,56 项)
239
239
  # 注意:必须逐个列出测试文件。tests/client/ 下还有 dock-stats-fixture.mjs 等夹具,
240
240
  # 用 glob 会把夹具当成测试文件从而误报失败。
241
241
  PLAYWRIGHT_MODULE=<playwright/index.mjs> CHROMIUM_EXECUTABLE=<chromium> \
package/lib/client.js CHANGED
@@ -555,10 +555,20 @@ body[data-dsh-tide-theme] ::selection {
555
555
  display: inline-flex;
556
556
  align-items: center;
557
557
  min-width: 0;
558
+ /* 座位自身必须可收缩:只给内含 pill 设 min-width:0 不够——inline-flex 父级仍被
559
+ * 内容撑开,窄容器下会把 composer 行顶出横向滚动。 */
560
+ flex: 0 1 auto;
561
+ max-width: 100%;
558
562
  }
559
563
 
560
564
  /* 座位里的原生按钮与插件按钮同规格:28px 高、13px 字号、透明底。 */
561
- [data-dsh-tide-seat] > [data-dsh-tide-dock-root] { display: inline-flex; align-items: center; gap: 2px; }
565
+ [data-dsh-tide-seat] > [data-dsh-tide-dock-root] {
566
+ display: inline-flex;
567
+ align-items: center;
568
+ gap: 2px;
569
+ min-width: 0;
570
+ max-width: 100%;
571
+ }
562
572
 
563
573
  /* 两侧等分:中间统计簇才能以卡片中心对齐(不等分时会被宽的一侧挤偏) */
564
574
  [data-dsh-tide-dock-left] {
@@ -1145,7 +1155,8 @@ body[data-dsh-tide-theme] .dsh-tide-stats-detail-list {
1145
1155
  font-size: 13px;
1146
1156
  line-height: 20px;
1147
1157
  min-width: 0;
1148
- max-width: 260px;
1158
+ /* 与 [data-dsh-tide-control='model'] 的上限保持一致,避免两处规则互相打架。 */
1159
+ max-width: 280px;
1149
1160
  }
1150
1161
 
1151
1162
  [data-dsh-tide-pill]:hover:not(:disabled) {
@@ -2401,17 +2412,14 @@ body[data-dsh-tide-theme] [data-slot='sidebar.workspaces'] [data-row-key^='works
2401
2412
  gap: 2px;
2402
2413
  }
2403
2414
 
2404
- /* 模型与思考等级之间的分隔点:两侧留出呼吸间隙,避免贴住按钮描边 */
2405
- [data-dsh-tide-separator] {
2406
- flex: none;
2407
- padding: 0 4px;
2408
- color: var(--dsw-alias-label-tertiary);
2409
- font-size: 12px;
2410
- line-height: 16px;
2411
- user-select: none;
2412
- }
2415
+ /* 模型与思考等级两颗 pill 直接相邻,靠 [data-dsh-tide-seat] 的 gap 分隔,不再插『·』。
2416
+ * 两颗 pill 之间的间距由容器 gap 提供,保持与原生 seat 一致的节奏。 */
2413
2417
  [data-dsh-tide-control='effort'] { flex: none; }
2414
- [data-dsh-tide-control='model'] { max-width: 240px; }
2418
+ /* 「供应商 / 模型」常见组合(如 WorkBuddy / Deepseek-V4.1-Flash)自然宽约 244px,
2419
+ * 240px 的上限会差 4px 触发省略号,让唯一的截断控件显得与同行其他控件不协调。
2420
+ * 宽屏取 280px 覆盖常见标签;窄屏按视口收紧上限(见文件末尾的窄屏断点),
2421
+ * 超长名仍由 ellipsis 兜底,三种情况都不会撑破 composer 行。 */
2422
+ [data-dsh-tide-control='model'] { max-width: 280px; flex: 0 1 auto; }
2415
2423
 
2416
2424
  [data-dsh-tide-filter] {
2417
2425
  appearance: none;
@@ -3056,6 +3064,20 @@ body:not([data-ds-dark-theme]) [data-dsh-tide-pill][aria-expanded='true'],
3056
3064
  body:not([data-ds-dark-theme]) [data-dsh-tide-pill][aria-expanded='true']:hover:not(:disabled) {
3057
3065
  color: var(--dsw-alias-label-primary);
3058
3066
  }
3067
+
3068
+ /* —— 窄视口:模型 pill 上限随视口收紧,保证 composer 行不产生横向溢出 ——
3069
+ * 280px 只在宽屏需要(完整显示常见标签);窄屏继续沿用会挤掉权限与思考等级控件。 */
3070
+ @media (max-width: 640px) {
3071
+ [data-dsh-tide-control='model'] {
3072
+ max-width: 180px;
3073
+ }
3074
+ }
3075
+
3076
+ @media (max-width: 420px) {
3077
+ [data-dsh-tide-control='model'] {
3078
+ max-width: 140px;
3079
+ }
3080
+ }
3059
3081
  `;
3060
3082
  //#endregion
3061
3083
  //#region src/client/legacy-migration.ts
@@ -3904,7 +3926,7 @@ body:not([data-ds-dark-theme]) [data-dsh-tide-pill][aria-expanded='true']:hover:
3904
3926
  startedAt.delete(sessionId);
3905
3927
  const elapsed = now() - start;
3906
3928
  if (elapsed < 100) return;
3907
- const text = `· ${options.locale("duration.took")} ${formatTurnDuration(elapsed, options.locale)}`;
3929
+ const text = `${options.locale("duration.took")} ${formatTurnDuration(elapsed, options.locale)}`;
3908
3930
  const pending = [...RETRY_DELAYS];
3909
3931
  const attempt = () => {
3910
3932
  if (paint(text) !== null) return;
@@ -4989,7 +5011,9 @@ body:not([data-ds-dark-theme]) [data-dsh-tide-pill][aria-expanded='true']:hover:
4989
5011
  const name = displayName(groups, selection);
4990
5012
  const group = selection === null ? void 0 : groups.find((candidate) => candidate.id === selection.provider);
4991
5013
  const providerLabel = group === void 0 ? selection?.provider ?? "" : providerName(group.id, group.name);
4992
- const modelLabel = name === "" ? t("model.placeholder") : `${providerLabel} / ${name}`;
5014
+ const duplicatedName = name !== "" && groups.filter((candidate) => candidate.models.some((model) => model.name === name)).length > 1;
5015
+ const fullLabel = name === "" ? t("model.placeholder") : `${providerLabel} / ${name}`;
5016
+ const modelLabel = name === "" ? t("model.placeholder") : duplicatedName ? fullLabel : name;
4993
5017
  const effort = effortLabel(groups, selection, t("effort.providerDefault"), state.retainedEffort);
4994
5018
  const busy = state.status === "selecting" || state.status === "loading";
4995
5019
  const close = () => {
@@ -5059,7 +5083,7 @@ body:not([data-ds-dark-theme]) [data-dsh-tide-pill][aria-expanded='true']:hover:
5059
5083
  "data-dsh-tide-pill": "",
5060
5084
  "data-dsh-tide-control": kind,
5061
5085
  "data-dsh-tide-emphasis": kind,
5062
- title: kind === "model" ? modelLabel : void 0,
5086
+ title: kind === "model" ? fullLabel : void 0,
5063
5087
  style: color === void 0 ? void 0 : { "--dsh-tide-provider-color": color },
5064
5088
  "aria-label": kind === "effort" ? `${t("effort.title")}:${effort ?? t("effort.unavailableShort")}` : void 0,
5065
5089
  "aria-haspopup": "dialog",
@@ -5084,10 +5108,6 @@ body:not([data-ds-dark-theme]) [data-dsh-tide-pill][aria-expanded='true']:hover:
5084
5108
  const orderedProviders = groups.filter((candidate) => candidate.models.length > 0);
5085
5109
  const providerIndex = group === void 0 ? -1 : orderedProviders.findIndex((candidate) => candidate.id === group.id);
5086
5110
  const children = [pill("model", h("span", { "data-dsh-tide-pill-label": "" }, modelLabel), providerIndex < 0 || group === void 0 ? void 0 : providerColor(group.id, providerIndex))];
5087
- children.push(h("span", {
5088
- "data-dsh-tide-separator": "",
5089
- "aria-hidden": "true"
5090
- }, "·"));
5091
5111
  children.push(pill("effort", h("span", { "data-dsh-tide-pill-label": "" }, effort ?? t("effort.unavailableShort"))));
5092
5112
  let popupNode = null;
5093
5113
  if (open === "model") {
@@ -5405,7 +5425,7 @@ body:not([data-ds-dark-theme]) [data-dsh-tide-pill][aria-expanded='true']:hover:
5405
5425
  label: `${compactUsed} / ${compactWindow} (${capacity.usedPercent}%)`,
5406
5426
  level: capacity.level,
5407
5427
  bucket: capacity.bucket,
5408
- tooltip: `上下文容量: 已用 ${capacity.usedTokens.toLocaleString()} / 上限 ${capacity.contextWindow.toLocaleString()} (剩余 ${capacity.remainingTokens.toLocaleString()} tokens)${lastInput || lastCache || lastOut ? `\n最新单轮: 输入 ${formatCompactTokens(lastInput)} · 缓存读 ${formatCompactTokens(lastCache)} · 输出 ${formatCompactTokens(lastOut)}` : ""}`,
5428
+ tooltip: `上下文容量: 已用 ${capacity.usedTokens.toLocaleString()} / 上限 ${capacity.contextWindow.toLocaleString()} (剩余 ${capacity.remainingTokens.toLocaleString()} tokens)${lastInput || lastCache || lastOut ? `\n最新单轮: 输入 ${formatCompactTokens(lastInput)} / 缓存读 ${formatCompactTokens(lastCache)} / 输出 ${formatCompactTokens(lastOut)}` : ""}`,
5409
5429
  breakdown: capacity.breakdown
5410
5430
  };
5411
5431
  }
@@ -5651,7 +5671,7 @@ body:not([data-ds-dark-theme]) [data-dsh-tide-pill][aria-expanded='true']:hover:
5651
5671
  }, value);
5652
5672
  if (model.activity) items.push(block("activity", "is-activity", "会话规模", iconUser, [
5653
5673
  number(model.activity.turns),
5654
- unit(" 轮 · "),
5674
+ unit(" 轮 / "),
5655
5675
  number(model.activity.steps),
5656
5676
  unit(" 步")
5657
5677
  ]));
@@ -5727,7 +5747,7 @@ body:not([data-ds-dark-theme]) [data-dsh-tide-pill][aria-expanded='true']:hover:
5727
5747
  }, model.cache ? `${model.cache.percent}%` : "暂无数据"), h("div", { className: "dsh-tide-hud-mini-track" }, h("div", {
5728
5748
  className: "dsh-tide-hud-mini-fill is-cache",
5729
5749
  style: { width: `${model.cache?.percent ?? 0}%` }
5730
- })), h("span", { className: "dsh-tide-stats-card-hint" }, `读取: ${model.tokensDetail ? formatCompactTokens(model.tokensDetail.cacheReadTokens) : "暂无数据"}`)), h("div", { className: "dsh-tide-stats-card" }, h("span", { className: "dsh-tide-stats-card-k" }, "平均首字延迟 (TTFT)"), h("strong", { className: "dsh-tide-stats-card-v" }, model.tps?.avgTtft ?? "暂无数据"), h("span", { className: "dsh-tide-stats-card-hint" }, "含网络/推理思考耗时")), h("div", { className: "dsh-tide-stats-card" }, h("span", { className: "dsh-tide-stats-card-k" }, latestDuration ? "单轮最新总耗时" : "模型累计总耗时"), h("strong", { className: "dsh-tide-stats-card-v" }, latestDuration ?? (model.duration ? model.duration.label : "暂无数据")), h("span", { className: "dsh-tide-stats-card-hint" }, latestDuration ? "包含排队与流式等待" : stats?.turns ? `平均每轮 ${formatSimpleDuration((model.timingDetail?.llmMs ?? 0) / Math.max(1, stats.turns))}` : "模型总耗时"))), model.tokensDetail ? h("div", { className: "dsh-tide-stats-detail-list" }, h("div", { className: "dsh-tide-stats-detail-row" }, h("span", {}, "未缓存输入 Tokens"), h("strong", {}, model.tokensDetail.uncachedInputTokens.toLocaleString())), h("div", { className: "dsh-tide-stats-detail-row" }, h("span", {}, "缓存读取 Tokens (Cache Read)"), h("strong", {}, model.tokensDetail.cacheReadTokens.toLocaleString())), model.tokensDetail.cacheWriteTokens > 0 ? h("div", { className: "dsh-tide-stats-detail-row" }, h("span", {}, "缓存写入 Tokens (Cache Write)"), h("strong", {}, model.tokensDetail.cacheWriteTokens.toLocaleString())) : null, h("div", { className: "dsh-tide-stats-detail-row" }, h("span", {}, "模型输出 Tokens (含思考内容)"), h("strong", {}, model.tokensDetail.outputTokens.toLocaleString())), h("div", { className: "dsh-tide-stats-detail-row is-total" }, h("span", {}, "累计消耗总 Tokens"), h("strong", {}, model.tokensDetail.totalTokens.toLocaleString()))) : null, h("div", { className: "dsh-tide-stats-footer" }, model.activity ? h("div", {}, `会话累计活动: ${model.activity.turns} 轮 · ${model.activity.steps} 步`) : null, model.timingDetail ? h("div", {}, `模型总耗时 ${formatSimpleDuration(model.timingDetail.llmMs)}${model.timingDetail.toolMs > 0 ? ` · 工具耗时 ${formatSimpleDuration(model.timingDetail.toolMs)}` : ""}`) : null)) : null;
5750
+ })), h("span", { className: "dsh-tide-stats-card-hint" }, `读取: ${model.tokensDetail ? formatCompactTokens(model.tokensDetail.cacheReadTokens) : "暂无数据"}`)), h("div", { className: "dsh-tide-stats-card" }, h("span", { className: "dsh-tide-stats-card-k" }, "平均首字延迟 (TTFT)"), h("strong", { className: "dsh-tide-stats-card-v" }, model.tps?.avgTtft ?? "暂无数据"), h("span", { className: "dsh-tide-stats-card-hint" }, "含网络/推理思考耗时")), h("div", { className: "dsh-tide-stats-card" }, h("span", { className: "dsh-tide-stats-card-k" }, latestDuration ? "单轮最新总耗时" : "模型累计总耗时"), h("strong", { className: "dsh-tide-stats-card-v" }, latestDuration ?? (model.duration ? model.duration.label : "暂无数据")), h("span", { className: "dsh-tide-stats-card-hint" }, latestDuration ? "包含排队与流式等待" : stats?.turns ? `平均每轮 ${formatSimpleDuration((model.timingDetail?.llmMs ?? 0) / Math.max(1, stats.turns))}` : "模型总耗时"))), model.tokensDetail ? h("div", { className: "dsh-tide-stats-detail-list" }, h("div", { className: "dsh-tide-stats-detail-row" }, h("span", {}, "未缓存输入 Tokens"), h("strong", {}, model.tokensDetail.uncachedInputTokens.toLocaleString())), h("div", { className: "dsh-tide-stats-detail-row" }, h("span", {}, "缓存读取 Tokens (Cache Read)"), h("strong", {}, model.tokensDetail.cacheReadTokens.toLocaleString())), model.tokensDetail.cacheWriteTokens > 0 ? h("div", { className: "dsh-tide-stats-detail-row" }, h("span", {}, "缓存写入 Tokens (Cache Write)"), h("strong", {}, model.tokensDetail.cacheWriteTokens.toLocaleString())) : null, h("div", { className: "dsh-tide-stats-detail-row" }, h("span", {}, "模型输出 Tokens (含思考内容)"), h("strong", {}, model.tokensDetail.outputTokens.toLocaleString())), h("div", { className: "dsh-tide-stats-detail-row is-total" }, h("span", {}, "累计消耗总 Tokens"), h("strong", {}, model.tokensDetail.totalTokens.toLocaleString()))) : null, h("div", { className: "dsh-tide-stats-footer" }, model.activity ? h("div", {}, `会话累计活动: ${model.activity.turns} 轮 / ${model.activity.steps} 步`) : null, model.timingDetail ? h("div", {}, `模型总耗时 ${formatSimpleDuration(model.timingDetail.llmMs)}${model.timingDetail.toolMs > 0 ? ` / 工具耗时 ${formatSimpleDuration(model.timingDetail.toolMs)}` : ""}`) : null)) : null;
5731
5751
  const popoverContent = popoverNode && typeof document !== "undefined" ? (0, react_dom.createPortal)(popoverNode, document.body) : popoverNode;
5732
5752
  return h("div", {
5733
5753
  className: "dsh-tide-dock-center-container",
@@ -5950,7 +5970,7 @@ body:not([data-ds-dark-theme]) [data-dsh-tide-pill][aria-expanded='true']:hover:
5950
5970
  * ModuleLoader 壳提供,这正是 tsdown client 构建保持 require 的原因。
5951
5971
  */
5952
5972
  const PLUGIN_ID = "dsh-tide-theme";
5953
- const BUILD = "0.5.0+2026-11-02T17:33:05.904Z";
5973
+ const BUILD = "0.5.1+2026-11-03T02:13:02.151Z";
5954
5974
  const name = PLUGIN_ID;
5955
5975
  const inject = [
5956
5976
  "slots",
package/lib/index.js CHANGED
@@ -1,4 +1,4 @@
1
- /** dsh-tide-theme v0.5.0 — 潮汐主题(Tide Theme)——给 DeepSeek Harness 的深海潮汐主题,遵循 workbuddy-design 现代克制设计规范,附带侧栏分页与筛选、输入框下方模型/权限控件、底栏性能 HUD、子代理委派图等界面增强。 */
1
+ /** dsh-tide-theme v0.5.1 — 潮汐主题(Tide Theme)——给 DeepSeek Harness 的深海潮汐主题,遵循 workbuddy-design 现代克制设计规范,附带侧栏分页与筛选、输入框下方模型/权限控件、底栏性能 HUD、子代理委派图等界面增强。 */
2
2
  //#region src/host/index.ts
3
3
  /**
4
4
  * 潮汐主题 —— Host 侧入口。
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "dsh-tide-theme",
3
- "version": "0.5.0",
3
+ "version": "0.5.2",
4
4
  "private": false,
5
5
  "publishConfig": {
6
6
  "access": "public"