@topmindspace/tms-skills 0.1.13 → 0.1.14

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.
Files changed (44) hide show
  1. package/CHANGELOG.md +26 -0
  2. package/README.en.md +3 -3
  3. package/README.md +3 -3
  4. package/package.json +1 -1
  5. package/top-ppt-html/README.en.md +2 -2
  6. package/top-ppt-html/README.md +1 -1
  7. package/top-ppt-html/SKILL.md +3 -3
  8. package/top-ppt-html/assets/examples/2026-09-09-architecture-graphite-dark.html +59 -20
  9. package/top-ppt-html/assets/examples/2026-09-09-presentation-business-blue.html +64 -26
  10. package/top-ppt-html/assets/examples/2026-09-09-research-mckinsey.html +64 -42
  11. package/top-ppt-html/assets/examples/2026-09-26-topmind-tms-skills-showcase.html +85 -46
  12. package/top-ppt-html/assets/examples/2026-09-26-topmind-tms-skills-showcase.model.json +1 -1
  13. package/top-ppt-html/assets/pptx-export.js +40 -17
  14. package/top-ppt-html/assets/showcase/showcase-charts.png +0 -0
  15. package/top-ppt-html/assets/showcase/showcase-cover.png +0 -0
  16. package/top-ppt-html/assets/showcase/showcase-gates.png +0 -0
  17. package/top-ppt-html/assets/showcase/showcase-modes.png +0 -0
  18. package/top-ppt-html/assets/showcase/showcase-positioning.png +0 -0
  19. package/top-ppt-html/assets/showcase/showcase-split.png +0 -0
  20. package/top-ppt-html/assets/showcase/showcase-toolbar.png +0 -0
  21. package/top-ppt-html/assets/style-gallery.html +3 -3
  22. package/top-ppt-html/assets/templates/architecture.html +59 -20
  23. package/top-ppt-html/assets/templates/engine.css +17 -1
  24. package/top-ppt-html/assets/templates/presentation.html +59 -20
  25. package/top-ppt-html/assets/templates/research.html +60 -27
  26. package/top-ppt-html/assets/templates/ui.js +1 -1
  27. package/top-ppt-html/package-lock.json +2 -2
  28. package/top-ppt-html/package.json +1 -1
  29. package/top-ppt-html/references/components-atoms.md +14 -1
  30. package/top-ppt-html/references/content-rules.md +1 -1
  31. package/top-ppt-html/references/design-system.md +1 -1
  32. package/top-ppt-html/references/icons.md +19 -0
  33. package/top-ppt-html/references/layout-grammar.md +17 -0
  34. package/top-ppt-html/references/layouts-combo.md +2 -4
  35. package/top-ppt-html/references/modes.md +1 -1
  36. package/top-ppt-html/references/pptx-export.md +1 -1
  37. package/top-ppt-html/scripts/build_pptx.js +50 -22
  38. package/top-ppt-html/scripts/layout-constants.json +18 -6
  39. package/top-ppt-html/scripts/quality_gate.py +2 -2
  40. package/top-ppt-html/scripts/render_from_model.py +2 -4
  41. package/top-ppt-html/scripts/scaffold_report.py +4 -10
  42. package/top-ppt-html/scripts/test_feedback_gates.py +2 -2
  43. package/top-ppt-html/scripts/validate_pptx.py +27 -11
  44. package/top-ppt-html/scripts/validate_report.py +27 -5
@@ -264,7 +264,8 @@ section.band{scroll-snap-align:start}
264
264
  svh 兼容移动端浏览器工具栏;旧浏览器落到 100vh。 */
265
265
  .band{padding-block:var(--band-pad);min-height:var(--band-min);
266
266
  display:flex;flex-direction:column;justify-content:center}
267
- .band>.wrap{width:100%}
267
+ .band>.wrap{width:100%;min-height:0}
268
+ .band>.wrap>.grid,.band>.wrap>.stack,.band>.wrap>.fig,.band>.wrap>.cols-2,.band>.wrap>.cols-3,.band>.wrap>.exhibit{min-height:0}
268
269
  .band--top{justify-content:flex-start} /* 内容约六七成屏:贴顶 + 底部自然留白 */
269
270
  .band--fit{justify-content:center} /* 内容接近一屏:垂直居中(默认行为,保留以兼容旧报告) */
270
271
  .band--flow{min-height:0;justify-content:flex-start} /* 长内容页(附录/全量参考)显式退出固定页高 */
@@ -505,6 +506,21 @@ tbody tr:hover{background:var(--surface-1)}
505
506
  td strong{color:var(--text);font-weight:600}
506
507
  td.k{color:var(--text);font-weight:500;white-space:nowrap}
507
508
  td.num{font-variant-numeric:tabular-nums}
509
+ /* ── 结论条(MD3 tonal strip · 本页重点收口;默认不显示「So what」标签) ──
510
+ 与上方主内容呼吸间距 ≥ --sp-6;flex:none 防止被主内容挤压;一屏页不得压进注释带。 */
511
+ .band>.wrap:has(>.sowhat),.band>.wrap:has(>.note){display:flex;flex-direction:column}
512
+ .sowhat{display:flex;align-items:flex-start;gap:var(--sp-3);flex:none;
513
+ margin-top:clamp(28px,3.6vh,48px); /* ≥ --sp-6 量级,修「贴底」 */
514
+ padding:var(--sp-4) var(--sp-5);background:var(--accent-soft);border:1px solid var(--accent-soft-2);
515
+ border-left:4px solid var(--accent);border-radius:var(--r-md);max-width:100%}
516
+ .sowhat__k{display:none}
517
+ .sowhat--labeled .sowhat__k{display:inline;font-size:var(--fs-xs);font-weight:700;letter-spacing:.1em;
518
+ text-transform:uppercase;color:var(--accent-text);white-space:nowrap;flex:none;padding-top:.15em}
519
+ .sowhat__v,.sowhat>:not(.sowhat__k){font-size:var(--fs-h3);color:var(--text);font-weight:var(--fw-title);
520
+ line-height:1.55;flex:1;min-width:0}
521
+ .sowhat__v p,.sowhat__stack{margin:0}
522
+ .sowhat__stack{display:flex;flex-direction:column;gap:var(--sp-2)}
523
+
508
524
  .note{display:flex;gap:var(--sp-4);padding:clamp(20px,2vw,28px);border-radius:var(--r-lg);
509
525
  background:var(--accent-soft);border-left:3px solid var(--accent)}
510
526
  .note__ico{width:26px;height:26px;flex:none;border-radius:50%;background:var(--accent);
@@ -1123,7 +1139,6 @@ transition:color .18s,background-color .18s}
1123
1139
  <p class="t-body"><strong>推论。</strong>平台化先行:统一编排与护栏到位后,场景再分层放量,顺序反了会被治理拖死。</p>
1124
1140
  </div>
1125
1141
  <div class="sowhat rv">
1126
- <span class="sowhat__k">So what</span>
1127
1142
  <span class="sowhat__v">先建平台与护栏,再放场景——顺序反了会被治理拖死。</span>
1128
1143
  </div>
1129
1144
  <div class="footnote">注:试点率 = 已进入试点及以上的企业占比;规模化 = 3 个以上场景稳定运行。来源见
@@ -1209,7 +1224,6 @@ transition:color .18s,background-color .18s}
1209
1224
  </li>
1210
1225
  </ul>
1211
1226
  <div class="sowhat rv">
1212
- <span class="sowhat__k">So what</span>
1213
1227
  <span class="sowhat__v">研发域渗透最浅但势能最大,工具链成熟后有望一年内反超客服域。</span>
1214
1228
  </div>
1215
1229
  </div>
@@ -1258,7 +1272,6 @@ transition:color .18s,background-color .18s}
1258
1272
  </div>
1259
1273
  </div>
1260
1274
  <div class="sowhat rv">
1261
- <span class="sowhat__k">So what</span>
1262
1275
  <span class="sowhat__v">增幅与基数负相关,研发域工具链补齐后将进入陡峭爬坡段。</span>
1263
1276
  </div>
1264
1277
  </div>
@@ -1273,7 +1286,7 @@ transition:color .18s,background-color .18s}
1273
1286
  </div>
1274
1287
  <div class="grid g-half rv">
1275
1288
  <div class="card">
1276
- <h3 class="t-h3">堆场景路径(n=23)</h3>
1289
+ <div class="card__hd"><div class="card__ico"><svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><path d="M10.3 3.9L1.8 18a2 2 0 0 0 1.7 3h17a2 2 0 0 0 1.7-3L13.7 3.9a2 2 0 0 0-3.4 0z"/><path d="M12 9v4M12 17h.01"/></svg></div><h3 class="t-h3">堆场景路径(n=23)</h3></div>
1277
1290
  <ul class="ul">
1278
1291
  <li><strong>接入慢。</strong>每场景重复对接,平均 11 周上线。</li>
1279
1292
  <li><strong>治理弱。</strong>事后审计,回退靠人工。</li>
@@ -1281,7 +1294,7 @@ transition:color .18s,background-color .18s}
1281
1294
  </ul>
1282
1295
  </div>
1283
1296
  <div class="card" style="background:var(--accent-soft);border-color:transparent">
1284
- <h3 class="t-h3" style="color:var(--accent)">平台化路径(n=9)</h3>
1297
+ <div class="card__hd"><div class="card__ico"><svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><path d="M20 6L9 17l-5-5"/></svg></div><h3 class="t-h3" style="color:var(--accent)">平台化路径(n=9)</h3></div>
1285
1298
  <ul class="ul">
1286
1299
  <li><strong>接入快。</strong>统一编排,平均 3 周上线。</li>
1287
1300
  <li><strong>治理内嵌。</strong>权限、审计、回退进平台层。</li>
@@ -1290,7 +1303,6 @@ transition:color .18s,background-color .18s}
1290
1303
  </div>
1291
1304
  </div>
1292
1305
  <div class="sowhat rv">
1293
- <span class="sowhat__k">So what</span>
1294
1306
  <span class="sowhat__v">平台化把场景接入周期从 11 周压到 3 周,是穿越分水岭的唯一共同路径。</span>
1295
1307
  </div>
1296
1308
  </div>
@@ -1401,7 +1413,6 @@ transition:color .18s,background-color .18s}
1401
1413
  </div>
1402
1414
  </div>
1403
1415
  <div class="sowhat rv">
1404
- <span class="sowhat__k">So what</span>
1405
1416
  <span class="sowhat__v">平台层的投入在四个季度内由采纳率爬坡兑回,不是纯成本。</span>
1406
1417
  </div>
1407
1418
  </div>
@@ -1497,7 +1508,6 @@ transition:color .18s,background-color .18s}
1497
1508
  </div>
1498
1509
  </div>
1499
1510
  <div class="sowhat rv">
1500
- <span class="sowhat__k">So what</span>
1501
1511
  <span class="sowhat__v">金融客服与互联网研发是两个可复制样板,制造研发域需先补工具链再谈放量。</span>
1502
1512
  </div>
1503
1513
  <div class="footnote">注:就绪度 = 场景 × 行业维度的能力自评加权得分(0–100),N=42 深度访谈 + 行业抽样<a class="cite" href="#ref-2">[2]</a>。</div>
@@ -1530,7 +1540,6 @@ transition:color .18s,background-color .18s}
1530
1540
  </div>
1531
1541
  </div>
1532
1542
  <div class="sowhat rv">
1533
- <span class="sowhat__k">So what</span>
1534
1543
  <span class="sowhat__v">当前主力仍在第二级:把副驾协同做厚,比抢跑自主决策更能兑现价值。</span>
1535
1544
  </div>
1536
1545
  <div class="footnote">注:台阶高度不代表难度,仅表示覆盖范围;accent 层为当前主力形态<a class="cite" href="#ref-1">[1]</a>。</div>
@@ -1573,7 +1582,6 @@ transition:color .18s,background-color .18s}
1573
1582
  <div class="exhibit__src">来源:企业智能体发展调研,2026-08;单位为百分点(pt),按增量归因分解</div>
1574
1583
  </div>
1575
1584
  <div class="sowhat rv">
1576
- <span class="sowhat__k">So what</span>
1577
1585
  <span class="sowhat__v">九个百分点增量里工具链补齐贡献最大、治理不足拖累 3pt——补齐工具链的边际收益最高。</span>
1578
1586
  </div>
1579
1587
  <div class="footnote">注:归因分解基于 42 家访谈企业的自报增量与编码结果,合计等于两期试点率之差。</div>
@@ -1620,7 +1628,6 @@ transition:color .18s,background-color .18s}
1620
1628
  <div class="exhibit__src">来源:企业智能体发展调研,2026-08;单位:条,自然月去重线索</div>
1621
1629
  </div>
1622
1630
  <div class="sowhat rv">
1623
- <span class="sowhat__k">So what</span>
1624
1631
  <span class="sowhat__v">初筛环节流失 580 条、占全链路 58%——先修初筛判定规则,比加大线索投放更快见效。</span>
1625
1632
  </div>
1626
1633
  <div class="footnote">注:流带宽度按流量线性编码,明细数据随页附数据表(PPTX 演讲者备注或页内表格)。</div>
@@ -1651,7 +1658,6 @@ transition:color .18s,background-color .18s}
1651
1658
  <div class="exhibit__src">注:行业构成基于 9 家规模化成功企业(N=42 访谈样本),能源与医疗各 1 家合并显示</div>
1652
1659
  </div>
1653
1660
  <div class="sowhat rv">
1654
- <span class="sowhat__k">So what</span>
1655
1661
  <span class="sowhat__v">制造与金融合计 5 家、占 55%——共同点是流程标准、容错边界清晰,可直接复制。</span>
1656
1662
  </div>
1657
1663
  <div class="footnote">注:面积与家数严格成比例;小于 2 家的行业合并为「其他」以保证可读性。</div>
@@ -1700,7 +1706,6 @@ transition:color .18s,background-color .18s}
1700
1706
  <div class="exhibit__src">注:就绪度 = 场景 × 行业维度的能力自评加权得分(0–100),N=42 深度访谈</div>
1701
1707
  </div>
1702
1708
  <div class="sowhat rv">
1703
- <span class="sowhat__k">So what</span>
1704
1709
  <span class="sowhat__v">金融客服中位 81 分且四分位区间最窄——标准化程度高的场景,就绪度稳定且可复制。</span>
1705
1710
  </div>
1706
1711
  <div class="footnote">注:分布基于各场景 8–12 个样本点;能源财务组样本最少(n=8),区间仅供参考。</div>
@@ -1737,7 +1742,6 @@ transition:color .18s,background-color .18s}
1737
1742
  <div class="exhibit__src">注:依赖关系取自 9 家规模化企业的平台架构文档(2026-08)</div>
1738
1743
  </div>
1739
1744
  <div class="sowhat rv">
1740
- <span class="sowhat__k">So what</span>
1741
1745
  <span class="sowhat__v">编排层连接度最高——它一旦不可用,工具、记忆、权限三条链路同时中断,须优先做冗余。</span>
1742
1746
  </div>
1743
1747
  <div class="footnote">注:布局为确定性环形排布(同输入必同输出),不使用随机力导向。</div>
@@ -1780,7 +1784,6 @@ transition:color .18s,background-color .18s}
1780
1784
  <div class="exhibit__src">注:列宽 ∝ 当年总规模(2023 = 100),列高 = 渠道构成占比</div>
1781
1785
  </div>
1782
1786
  <div class="sowhat rv">
1783
- <span class="sowhat__k">So what</span>
1784
1787
  <span class="sowhat__v">总量三年增长 65%,线上占比从 40% 升到 61%——线上承载能力已成为规模化的前置条件。</span>
1785
1788
  </div>
1786
1789
  <div class="footnote">注:双重编码缺一不可——只画占比会丢掉规模差异,只画规模会丢掉结构变化。</div>
@@ -1814,7 +1817,6 @@ transition:color .18s,background-color .18s}
1814
1817
  <div class="exhibit__src">注:占比为各形态场景数占当年总量;带宽 ∝ 场景数,基线居中展开</div>
1815
1818
  </div>
1816
1819
  <div class="sowhat rv">
1817
- <span class="sowhat__k">So what</span>
1818
1820
  <span class="sowhat__v">问答检索的占比从 52% 降到 18%,价值重心持续向副驾协同与端到端交付迁移。</span>
1819
1821
  </div>
1820
1822
  <div class="footnote">注:带边界上下分别采样(≥24 点),不使用预设形状替代曲线语义。</div>
@@ -1854,7 +1856,6 @@ transition:color .18s,background-color .18s}
1854
1856
  <div class="exhibit__src">来源:项目排期基线,2026-08;时间轴跨度 = 各阶段「起点 + 时长」最大值(18 周)</div>
1855
1857
  </div>
1856
1858
  <div class="sowhat rv">
1857
- <span class="sowhat__k">So what</span>
1858
1859
  <span class="sowhat__v">开发阶段独占 8 周、占总工期 44%——压缩工期的杠杆在开发,不在调研与设计。</span>
1859
1860
  </div>
1860
1861
  <div class="footnote">注:条形长度按周线性编码,起点为阶段起始周;「起点 + 时长」最大值决定时间轴跨度。</div>
@@ -1887,7 +1888,6 @@ transition:color .18s,background-color .18s}
1887
1888
  <div class="exhibit__src">注:扇区半径按得分线性映射(0–100 分);每扇区 ≥16 段采样,不使用预设形状替代曲线语义</div>
1888
1889
  </div>
1889
1890
  <div class="sowhat rv">
1890
- <span class="sowhat__k">So what</span>
1891
1891
  <span class="sowhat__v">技术可控 78 分领先 36 分,而经济可行 42 分垫底——能力建设的短板不在技术,在算得过来账。</span>
1892
1892
  </div>
1893
1893
  <div class="footnote">注:五维得分来自 42 家访谈企业的能力自评加权(0–100 分),维度定义见参考资料 [1]。</div>
@@ -1931,7 +1931,6 @@ transition:color .18s,background-color .18s}
1931
1931
  <div class="exhibit__src">来源:季度就绪度评分序列,2025Q1–2026Q4;单位:分(0–100)</div>
1932
1932
  </div>
1933
1933
  <div class="sowhat rv">
1934
- <span class="sowhat__k">So what</span>
1935
1934
  <span class="sowhat__v">八期振幅收窄后连拉两根阳线——就绪度进入温和上行段,治理投入开始显效。</span>
1936
1935
  </div>
1937
1936
  <div class="footnote">注:上涨用 accent 实体、下跌用中性色实体(不引入红绿第二色相);明细数据随页附数据表。</div>
@@ -1990,17 +1989,17 @@ transition:color .18s,background-color .18s}
1990
1989
  </div>
1991
1990
  <div class="grid g-3 rv">
1992
1991
  <div class="card">
1993
- <h3 class="t-h3" style="margin-bottom:var(--sp-2)">平台先行</h3>
1992
+ <div class="card__hd"><div class="card__ico"><svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><path d="M12 2l9 5-9 5-9-5 9-5z"/><path d="M3 12l9 5 9-5"/><path d="M3 17l9 5 9-5"/></svg></div><h3 class="t-h3" style="margin-bottom:var(--sp-2)">平台先行</h3></div>
1994
1993
  <p class="t-body">
1995
1994
  统一编排与护栏到位,场景再分层放量。</p>
1996
1995
  </div>
1997
1996
  <div class="card">
1998
- <h3 class="t-h3" style="margin-bottom:var(--sp-2)">场景分级</h3>
1997
+ <div class="card__hd"><div class="card__ico"><svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><path d="M8 6h13M8 12h13M8 18h13M3 6h.01M3 12h.01M3 18h.01"/></svg></div><h3 class="t-h3" style="margin-bottom:var(--sp-2)">场景分级</h3></div>
1999
1998
  <p class="t-body">
2000
1999
  三重门槛齐备的场景优先,不足两成。</p>
2001
2000
  </div>
2002
2001
  <div class="card">
2003
- <h3 class="t-h3" style="margin-bottom:var(--sp-2)">治理闭环</h3>
2002
+ <div class="card__hd"><div class="card__ico"><svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.8" stroke-linecap="round" stroke-linejoin="round"><path d="M12 3l8 3v6c0 5-3.5 8.5-8 10-4.5-1.5-8-5-8-10V6l8-3z"/></svg></div><h3 class="t-h3" style="margin-bottom:var(--sp-2)">治理闭环</h3></div>
2004
2003
  <p class="t-body">
2005
2004
  权限、审计、回退全链路内嵌平台层。</p>
2006
2005
  </div>
@@ -2397,7 +2396,7 @@ if(e.isIntersecting){e.target.classList.add('in');o.unobserve(e.target)}})},
2397
2396
  var PROMPT=[
2398
2397
  '请为这份 HTML 报告生成可编辑 PPTX 并交付:',
2399
2398
  '1) 阅读 references/pptx-export.md 与 references/modes.md(三模式独立规则);',
2400
- '2) 核对/补全 window.REPORT_MODEL 为与正文严格一致的内容(含 mode/style/theme/title/agenda/sections/closing;theme 为 light 或 dark、与页面 data-theme 一致——PPTX 按此导出亮色版或深色版;29 种页型字段与 30 类 chart.type 见 scripts/model-schema.json;research 关键图表页用 type:"exhibit" 并填 exhibitNo/soWhat/footnote);',
2399
+ '2) 核对/补全 window.REPORT_MODEL 为与正文严格一致的内容(含 mode/style/theme/title/agenda/sections/closing;theme 为 light 或 dark、与页面 data-theme 一致——PPTX 按此导出亮色版或深色版;29 种页型字段与 30 类 chart.type 见 scripts/model-schema.json;research 关键图表页用 type:"exhibit" 并填 exhibitNo/soWhat(结论条)/footnote);',
2401
2400
  '3) 运行 python scripts/validate_report.py <报告.html> 直到全 PASS(含模型一致性检查);',
2402
2401
  '4) 智能体精导并质检(0/0 才交付):python scripts/extract_model.py <报告.html> → NODE_PATH=<pptxgenjs 所在 node_modules> node scripts/build_pptx.js <报告.pptx> --model=<报告.model.json>(如需覆盖模型主题可加 --theme=light|dark) → python scripts/validate_pptx.py <报告.pptx> --strict --model=<报告.model.json>。',
2403
2402
  '报告文件:<请填写报告.html 的路径>'
@@ -3577,7 +3576,7 @@ window.REPORT_MODEL = {
3577
3576
 
3578
3577
  /* __TOPPPT_RUNTIME_START__ */
3579
3578
  /* ══ PPTX 导出运行时(assets/pptx-export.js 的内联副本 · 由 scripts/sync_runtime.py 注入,禁止手改) ══ */
3580
- /* __TOPPPT_RUNTIME_SHA__:77ca318e7a510e01 */
3579
+ /* __TOPPPT_RUNTIME_SHA__:f4dc2ab366ea79c4 */
3581
3580
  /* ═══════════════════════════════════════════════════════════════════════════
3582
3581
  * TopPPT HTML· 浏览器端 PPTX 预览运行时
3583
3582
  * 零依赖、随报告单文件分发;OOXML 序列化器(仅供预览,页面不导出文件)。
@@ -3658,7 +3657,7 @@ var PRESETS_DARK = {
3658
3657
  var STYLE_DATA_COLORS = {"business-blue":["1a73e8","3526bb","21a199","b77148","99983d"],"apple-mono":["1d1d1f","0071e3","0f7b6c","c2410c","7c3aed"],"mckinsey":["003a70","2826bb","21a18e","b76848","99903d"],"brand-red":["d0021b","bb6326","d634ae","40a182","438aa8"],"warm-sand":["96681f","839324","cf3b3e","4d88b2","4a47a4"],"deep-teal":["0f6b5c","2683bb","22aa3e","b74870","a85c43"],"graphite-dark":["0369a1","2637bb","1f9977","b75948","a18a40"],"indigo-violet":["5b5bd6","7432ae","4197c8","a08f4b","7ca04b"],"spectrum":["4563ef","5b26bb","269ebb","af8746","83993d"]};
3659
3658
  var STYLE_DATA_COLORS_DARK = {"business-blue":["8ab4f8","7966e0","88e7e5","d4ad91","cbce83"],"apple-mono":["f5f5f7","2997ff","2dd4bf","ff9f0a","bf5af2"],"mckinsey":["7fb2e5","6f6bdb","8ce3d8","d1a694","cbc586"],"brand-red":["ff5a66","e09e66","e788cb","91d4c2","83b4ce"],"warm-sand":["d9b36a","c2d571","df9391","97b5ce","8e89c7"],"deep-teal":["4fc3b0","7aaecd","97d8a4","c99cac","c29c8f"],"graphite-dark":["4da3ff","6c66e0","88e7dc","d4a691","cec983"],"indigo-violet":["a5a4f0","a967e0","89c3e7","d3c792","aece83"],"spectrum":["8ba0f8","9066e0","88d6e7","d4ba91","bdce83"]};
3660
3659
  var GRID = {"columns":12,"gutter":0.16,"colW":0.8644,"x":[0.6,1.6244,2.6488,3.6732,4.6976,5.722,6.7464,7.7708,8.7952,9.8196,10.844,11.8684,12.733],"y":[2.35,3.27,4.19,5.11,6.03,6.9],"safe":{"top":0.4,"bottom":0.4,"left":0.6,"right":0.6}};
3661
- var TYPO = {"levels":[{"id":"C0","name":"封面/章节幕标题","role":"coverTitle","usage":"封面主标题、章节幕标题"},{"id":"T1","name":"页码/章节徽章","role":"caption","usage":"页码徽章、章节编号"},{"id":"T2","name":"页面主标题/结论标题","role":"h1","usage":"每页顶部结论句(research 行动标题)"},{"id":"T3","name":"副标题/语境说明","role":"lead","usage":"主标题下方导语"},{"id":"T4","name":"模块标题/图表标题","role":"h2","usage":"卡片标题、图表标题、面板标题"},{"id":"T5","name":"证据编号/轻量标签","role":"micro","usage":"Exhibit 编号、状态标签"},{"id":"T6","name":"证据块标题/小节标题","role":"h2","usage":"分栏小标题、证据块标题"},{"id":"T7","name":"正文解释段落","role":"body","usage":"证据解释、管理解读正文、表格正文"},{"id":"T8","name":"结论条文字","role":"body","usage":"so-what 结论条、核心结论框"},{"id":"T9","name":"SO WHAT 标签","role":"caption","usage":"so-what 标签行"},{"id":"T10","name":"SO WHAT 正文/业务含义","role":"body","usage":"so-what 正文、行动含义、表格行动项"},{"id":"T11","name":"图表轴/图例/刻度/微标签","role":"micro","usage":"坐标轴、图例、刻度、单位(禁用于表格正文与完整短句)"},{"id":"T12","name":"图表数据标签","role":"caption","usage":"折线点值、柱形标签、百分比标注"},{"id":"T13","name":"关键 KPI 大数字","role":"h1","usage":"KPI 大数字、hero 数值"},{"id":"T14","name":"注释/口径/来源/页脚","role":"micro","usage":"footnote、来源行、页脚、小页码"}],"tableSemanticRule":{"body":["T7","T10"],"microAllowed":["T11"],"microForbiddenFor":["表格正文","行动项","风险项","解释句","建议句","长项目符号","完整短句"]}};
3660
+ var TYPO = {"levels":[{"id":"C0","name":"封面/章节幕标题","role":"coverTitle","usage":"封面主标题、章节幕标题"},{"id":"T1","name":"页码/章节徽章","role":"caption","usage":"页码徽章、章节编号"},{"id":"T2","name":"页面主标题/结论标题","role":"h1","usage":"每页顶部结论句(research 行动标题)"},{"id":"T3","name":"副标题/语境说明","role":"lead","usage":"主标题下方导语"},{"id":"T4","name":"模块标题/图表标题","role":"h2","usage":"卡片标题、图表标题、面板标题"},{"id":"T5","name":"证据编号/轻量标签","role":"micro","usage":"Exhibit 编号、状态标签"},{"id":"T6","name":"证据块标题/小节标题","role":"h2","usage":"分栏小标题、证据块标题"},{"id":"T7","name":"正文解释段落","role":"body","usage":"证据解释、管理解读正文、表格正文"},{"id":"T8","name":"结论条文字","role":"body","usage":"结论条、核心结论框"},{"id":"T9","name":"结论条标签(可选·默认隐藏)","role":"caption","usage":"结论条可选标签(默认不显示)"},{"id":"T10","name":"结论条正文/业务含义","role":"body","usage":"结论条正文、行动含义、表格行动项"},{"id":"T11","name":"图表轴/图例/刻度/微标签","role":"micro","usage":"坐标轴、图例、刻度、单位(禁用于表格正文与完整短句)"},{"id":"T12","name":"图表数据标签","role":"caption","usage":"折线点值、柱形标签、百分比标注"},{"id":"T13","name":"关键 KPI 大数字","role":"h1","usage":"KPI 大数字、hero 数值"},{"id":"T14","name":"注释/口径/来源/页脚","role":"micro","usage":"footnote、来源行、页脚、小页码"}],"tableSemanticRule":{"body":["T7","T10"],"microAllowed":["T11"],"microForbiddenFor":["表格正文","行动项","风险项","解释句","建议句","长项目符号","完整短句"]}};
3662
3661
  var CONT = {"pad":{"card":0.18,"panel":0.2,"cell":0.08,"band":0.16,"soWhat":0.16,"kpi":0.18,"chart":0.1,"head":0.05,"footer":0.05,"node":0.06},"minPad":0.06,"textMetrics":{"lineFactor":1.45,"emAsciiRatio":0.52},"overflowRule":"溢出处置优先级(禁静默截断):① 重构承载(列表/卡片/表/图/组合版式)→ ② 拆页/分章(议程→主张→证据卡→明细;01a/01b;信息须完整)→ ③ 换布局形态(V1–V4/多列/卡栅格)→ ④ 有限 fontShrink(阶梯内、模式 floor 以上、最多 4 档)→ ⑤ 禁止:静默截断、砍 so-what/证据/口径、为审美稀疏删决策必需信息。单页字数预算是预警不是删字许可证。","fontShrink":{"ladder":[15,14,13.5,13,12.5,12,11.5,11,10.5,10,9.5,9,8.5],"maxShrinkSteps":4,"floorPt":{"presentation":10,"research":9,"architecture":10},"preferContentFirst":true,"warnBelow":9.5},"continuousTextRule":"语义连续的一句话 / so-what 主句 / 结论句 / 表格单元格正文不得拆成多个独立文本框(避免异常空格、断句、基线漂移);局部加粗高亮必须用同一文本框内富文本。"};
3663
3662
  var REG = {"bar":{"html":"svg-bars","pptx":"native","nativeType":"bar","dataTable":"notes","min":{"vbHeightMin":160}},"hbar":{"html":"svg-hbars","pptx":"native","nativeType":"bar","dataTable":"notes","min":{"vbHeightMin":100}},"stack":{"html":"svg-stack","pptx":"native","nativeType":"bar","dataTable":"notes","min":{"vbHeightMin":160},"nativeOpt":{"barGrouping":"stacked"}},"stackline":{"html":"svg-stackline","pptx":"native","nativeType":"bar","dataTable":"notes","min":{"vbHeightMin":40},"nativeOpt":{"barGrouping":"percentStacked"}},"line":{"html":"svg-line","pptx":"native","nativeType":"line","dataTable":"notes","min":{"vbHeightMin":160}},"dualline":{"html":"svg-dualline","pptx":"native","nativeType":"line","dataTable":"notes","min":{"vbHeightMin":160}},"area":{"html":"svg-area","pptx":"native","nativeType":"area","dataTable":"notes","min":{"vbHeightMin":160}},"donut":{"html":"svg-donut","pptx":"native","nativeType":"doughnut","dataTable":"notes","min":{"pxWidthMin":140}},"multidonut":{"html":"svg-mdonut","pptx":"native","nativeType":"doughnut","dataTable":"notes","min":{"pxWidthMin":140}},"pie":{"html":"svg-pie","pptx":"native","nativeType":"pie","dataTable":"notes","min":{"pxWidthMin":140}},"radar":{"html":"svg-radar","pptx":"native","nativeType":"radar","dataTable":"notes","min":{"pxWidthMin":220}},"scatter":{"html":"svg-scatter","pptx":"native","nativeType":"scatter","dataTable":"notes","min":{"vbHeightMin":180}},"bubble":{"html":"svg-bubble","pptx":"native","nativeType":"bubble","dataTable":"notes","min":{"vbHeightMin":180}},"waterfall":{"html":"svg-wf","pptx":"native","nativeType":"bar","dataTable":"notes","min":{"vbHeightMin":170},"nativeTrick":"stacked+hiddenBase+connector"},"gauge":{"html":"svg-gauge","pptx":"native","nativeType":"doughnut","dataTable":"notes","min":{"pxWidthMin":180},"nativeTrick":"doughnut+firstSliceAng+hiddenRemainder"},"pareto":{"html":"svg-pareto","pptx":"native","nativeType":"bar","dataTable":"notes","min":{"vbHeightMin":180},"nativeTrick":"multiType+bar+line"},"gantt":{"html":"svg-gantt","pptx":"shape","dataTable":"notes","min":{"vbHeightMin":130},"path":{"forbidPresetShapes":true}},"vsbar":{"html":"svg-vsbar","pptx":"shape","dataTable":"notes","min":{"vbHeightMin":100},"path":{"forbidPresetShapes":true}},"progress":{"html":"svg-progress","pptx":"shape","dataTable":"notes","min":{"vbHeightMin":100},"path":{"forbidPresetShapes":true}},"sparkline":{"html":"svg-spark","pptx":"shape","dataTable":"off","min":{"vbHeightMin":20},"path":{"forbidPresetShapes":true}},"funnel":{"html":"svg-funnel","pptx":"shape","dataTable":"notes","min":{"vbHeightMin":160},"path":{"minSamplePoints":8,"forbidPresetShapes":true}},"treemap":{"html":"svg-treemap","pptx":"shape","dataTable":"appendix","min":{"vbHeightMin":170},"path":{"forbidPresetShapes":true}},"marimekko":{"html":"svg-marimekko","pptx":"shape","dataTable":"appendix","min":{"vbHeightMin":160},"path":{"forbidPresetShapes":true}},"boxplot":{"html":"svg-boxplot","pptx":"shape","dataTable":"appendix","min":{"vbHeightMin":180},"path":{"forbidPresetShapes":true}},"network":{"html":"svg-network","pptx":"shape","dataTable":"appendix","min":{"vbHeightMin":200},"path":{"forbidPresetShapes":true}},"sankey":{"html":"svg-sankey","pptx":"shape","dataTable":"appendix","min":{"vbHeightMin":200},"path":{"minSamplePoints":16,"trackBothEdges":true,"forbidPresetShapes":true}},"streamgraph":{"html":"svg-stream","pptx":"shape","dataTable":"appendix","min":{"vbHeightMin":160},"path":{"minSamplePoints":24,"trackBothEdges":true,"forbidPresetShapes":true}},"slope":{"html":"svg-slope","pptx":"shape","dataTable":"notes","min":{"vbHeightMin":180},"path":{"forbidPresetShapes":true}},"dumbbell":{"html":"svg-dumbbell","pptx":"shape","dataTable":"notes","min":{"vbHeightMin":160},"path":{"forbidPresetShapes":true}},"lollipop":{"html":"svg-lollipop","pptx":"shape","dataTable":"notes","min":{"vbHeightMin":140},"path":{"forbidPresetShapes":true}},"dotplot":{"html":"svg-dotplot","pptx":"shape","dataTable":"notes","min":{"vbHeightMin":120},"path":{"forbidPresetShapes":true}},"bulletchart":{"html":"svg-bullet","pptx":"shape","dataTable":"notes","min":{"vbHeightMin":140},"path":{"forbidPresetShapes":true}},"waffle":{"html":"svg-waffle","pptx":"shape","dataTable":"notes","min":{"vbHeightMin":160},"path":{"forbidPresetShapes":true}},"radialbar":{"html":"svg-radialbar","pptx":"shape","dataTable":"notes","min":{"pxWidthMin":200},"path":{"minSamplePoints":16,"forbidPresetShapes":true}},"rose":{"html":"svg-rose","pptx":"shape","dataTable":"notes","min":{"pxWidthMin":180},"path":{"minSamplePoints":16,"forbidPresetShapes":true}},"candlestick":{"html":"svg-candle","pptx":"shape","dataTable":"appendix","min":{"vbHeightMin":180},"path":{"forbidPresetShapes":true}}};
3664
3663
  var DEEP = {"triggers":["高保真","1:1","一比一","精确还原","按图还原","正式交付","不能偏移","像素级","严格对照","逐页验收"],"complexCharts":["sankey","streamgraph","treemap","marimekko","boxplot","network","rose","radialbar","candlestick","funnel"],"checks":{"anchors":true,"containerOverflow":true,"renderCompare":true,"manifest":true},"renderCompare":{"engine":"soffice","fallback":"powerpoint-com","skipIfMissing":true,"dpi":96}};
@@ -3909,7 +3908,7 @@ function fitRowH(avail, n, pref, floor) {
3909
3908
  function chartBottom(hasSoWhat, hasFootnote) {
3910
3909
  /* D8: tightest of soWhat/footnote/contentBottomWithNote — no short-circuit */
3911
3910
  var bot = CONTENT_BOTTOM;
3912
- if (hasSoWhat) bot = Math.min(bot, PT.exhibit.soWhatY - 0.12);
3911
+ if (hasSoWhat) bot = Math.min(bot, PT.exhibit.soWhatY - 0.20);
3913
3912
  if (hasFootnote) bot = Math.min(bot, PT.exhibit.footnoteY - 0.12);
3914
3913
  if (hasSoWhat || hasFootnote) bot = Math.min(bot, CONTENT_BOTTOM_NOTE);
3915
3914
  return bot;
@@ -3993,24 +3992,31 @@ function donutWedges(labels, values) {
3993
3992
  });
3994
3993
  return segs;
3995
3994
  }
3996
- function donutChart(sh, ec, S, dcols) {
3995
+ function donutChart(sh, ec, S, dcols, bottomY) {
3997
3996
  var d = PT.donut, labels = ec.labels || [], values = ec.values || [];
3998
3997
  var segs = donutWedges(labels, values);
3999
- var bx = d.centerX - d.r, by = d.centerY - d.r, bw = d.r * 2;
3998
+ var r = d.r;
3999
+ if (bottomY != null && d.centerY + r > bottomY) {
4000
+ r = Math.max(0.9, bottomY - d.centerY - 0.04);
4001
+ }
4002
+ var holeR = d.holeR * (r / d.r);
4003
+ var bx = d.centerX - r, by = d.centerY - r, bw = r * 2;
4000
4004
  segs.forEach(function (sg) {
4001
4005
  sh.push(shape('pie', bx, by, bw, bw, dcols[sg[2] % dcols.length], { av: pieAv(sg[0], sg[1]) }));
4002
4006
  });
4003
- var hb = d.holeR * 2;
4004
- sh.push(shape('ellipse', d.centerX - d.holeR, d.centerY - d.holeR, hb, hb, S.bg));
4007
+ var hb = holeR * 2;
4008
+ sh.push(shape('ellipse', d.centerX - holeR, d.centerY - holeR, hb, hb, S.bg));
4005
4009
  var total = 0; values.forEach(function (v) { total += Math.max(0, v); });
4006
4010
  var totalStr = (Math.round(total * 10) / 10) + (ec.unit || '');
4007
- sh.push(txSp(d.centerX - d.holeR, d.centerY - 0.42, hb, 0.5,
4011
+ sh.push(txSp(d.centerX - holeR, d.centerY - 0.42, hb, 0.5,
4008
4012
  [[{ t: totalStr, sz: 20, b: 1, col: S.ink, font: S.fontDisplay }]], { align: 'ctr', anchor: 'ctr' }));
4009
- sh.push(txSp(d.centerX - d.holeR, d.centerY + 0.08, hb, 0.35,
4013
+ sh.push(txSp(d.centerX - holeR, d.centerY + 0.08, hb, 0.35,
4010
4014
  [[{ t: ec.centerLabel || '合计', sz: 9.5, col: S.faint, font: S.font }]], { align: 'ctr', anchor: 'ctr' }));
4011
4015
  var n = Math.max(1, labels.length);
4012
- var rowH = Math.min(d.legendRowH, 3.4 / n);
4016
+ var maxLegH = (bottomY != null) ? Math.max(1.2, bottomY - (d.centerY - 1.7)) : 3.4;
4017
+ var rowH = Math.min(d.legendRowH, maxLegH / n, 3.4 / n);
4013
4018
  var ly0 = d.centerY - (n * rowH) / 2 + 0.1;
4019
+ if (bottomY != null) ly0 = Math.min(ly0, bottomY - n * rowH - 0.04);
4014
4020
  var sum2 = total || 1;
4015
4021
  labels.forEach(function (lb, i) {
4016
4022
  var v = values[i] || 0;
@@ -4067,14 +4073,13 @@ function table(x, y, w, colW, rows, S, opts) {
4067
4073
  function soWhatBar(sh, text, S) {
4068
4074
  var R = (typeof regionOf === 'function') ? regionOf('exhibit', 'annotation')
4069
4075
  : { x: MX, y: PT.exhibit.soWhatY, w: CW, h: 0.62 };
4070
- /* 与 B 通道同算法:长结论条有限缩字号,优先保容器不溢出 */
4071
- var bodyW = Math.max(2.5, R.w - 0.44 - 1.35);
4072
- var fzB = fitFont([String(text || '')], bodyW, R.h - 0.14, { max: 12.5, gapFactor: 0.2, maxShrinkSteps: 3 });
4076
+ /* MD3 结论条:衬底 + 左 accent 轨 + 正文(不绘制「SO WHAT」标签字样) */
4077
+ var bodyW = Math.max(2.5, R.w - 0.44);
4078
+ var fzB = fitFont([String(text || '')], bodyW, R.h - 0.14, { max: 14, gapFactor: 0.2, maxShrinkSteps: 3 });
4073
4079
  sh.push(shape('rect', R.x, R.y, R.w, R.h, S.soft));
4074
4080
  sh.push(shape('rect', R.x, R.y, 0.06, R.h, S.accent));
4075
4081
  sh.push(txSp(R.x + 0.22, R.y + 0.06, R.w - 0.44, R.h - 0.12,
4076
- [[{ t: 'SO WHAT ', sz: 11, b: 1, col: S.accent, font: S.font, spc: 150 },
4077
- { t: text, sz: fzB, col: S.ink, font: S.font }]], { anchor: 'ctr' }));
4082
+ [[{ t: String(text || ''), sz: fzB, b: 1, col: S.ink, font: S.font }]], { anchor: 'ctr' }));
4078
4083
  }
4079
4084
  function footnoteLine(sh, text, S) {
4080
4085
  var R = (typeof regionOf === 'function') ? regionOf('exhibit', 'footnote')
@@ -4934,7 +4939,7 @@ function slidesOf(model, S) {
4934
4939
  if (img.caption) sh.push(txSp(MX, capYImg + 0.04, CW, capH2, [[{ t: img.caption, sz: 10.5, col: S.faint, font: S.font }]]));
4935
4940
  } else if (type === 'donut') {
4936
4941
  var dcn = sec.chart || {};
4937
- if (dcn.labels && dcn.values) donutChart(sh, dcn, S, dcn.colors || donutColors(model.style, S, model.theme));
4942
+ if (dcn.labels && dcn.values) donutChart(sh, dcn, S, dcn.colors || donutColors(model.style, S, model.theme), bodyBottom);
4938
4943
  if (sec.note) sh.push(txSp(MX, PT.note.y, CW, PT.note.h, [[{ t: sec.note, sz: 11, col: S.faint, font: S.font }]]));
4939
4944
  } else if (type === 'heatmap') {
4940
4945
  var H = PT.heatmap;
@@ -5087,10 +5092,27 @@ function slidesOf(model, S) {
5087
5092
  var bRR = regOf('bar', isHBar ? 'hbar' : 'primary', { bottom: botY }) ||
5088
5093
  { x: isHBar ? MX : MX + PT.bar.chartX, y: isHBar ? PT.bar.hbarY0 : PT.bar.chartY,
5089
5094
  w: isHBar ? CW : CW - PT.bar.chartW, h: 3 };
5095
+ var ptsB = (sec.points || []).filter(Boolean);
5096
+ var bx = bRR.x, bw = bRR.w;
5097
+ if (ptsB.length && !isHBar) {
5098
+ var sideW = Math.min(3.6, Math.max(2.6, bRR.w * 0.30));
5099
+ bw = Math.max(3.2, bRR.w - sideW - 0.28);
5100
+ var sx = bRR.x + bw + 0.28;
5101
+ var rowHb = Math.min(0.72, (bRR.h - 0.1) / Math.max(1, ptsB.length));
5102
+ ptsB.slice(0, 6).forEach(function (p, i) {
5103
+ var k = Array.isArray(p) ? String(p[0] || '') : String((p && p.t) || '');
5104
+ var v = Array.isArray(p) ? String(p[1] || '') : String((p && p.d) || '');
5105
+ var y = bRR.y + i * rowHb;
5106
+ sh.push(shape('rect', sx, y + 0.12, 0.08, 0.08, S.accent));
5107
+ sh.push(txSp(sx + 0.2, y, sideW - 0.25, rowHb,
5108
+ [[{ t: k + (v ? ' ' : ''), sz: 12, b: 1, col: S.ink, font: S.font },
5109
+ { t: v, sz: 11, col: S.body, font: S.font }]], { anchor: 'ctr' }));
5110
+ });
5111
+ }
5090
5112
  if (isHBar) {
5091
- chartBlockShapes(sh, ch, S, bRR.x, bRR.y, bRR.w, bRR.h, dcols2);
5113
+ chartBlockShapes(sh, ch, S, bx, bRR.y, bw, bRR.h, dcols2);
5092
5114
  } else {
5093
- chartBlockShapes(sh, ch, S, bRR.x, bRR.y, bRR.w, Math.max(1.5, bRR.h), dcols2);
5115
+ chartBlockShapes(sh, ch, S, bx, bRR.y, bw, Math.max(1.5, bRR.h), dcols2);
5094
5116
  }
5095
5117
  if (sec.note) sh.push(txSp(MX, PT.note.y, CW, PT.note.h, [[{ t: sec.note, sz: 11, col: S.faint, font: S.font }]]));
5096
5118
  } else if (type === 'twocol' || type === 'threecol') {