Add section badges to strategy TOC/headings and fill cards to viewport height.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
dekun
2026-07-18 17:41:04 +08:00
parent 023bf6a814
commit 2f7e6355a1
3 changed files with 150 additions and 32 deletions
+115 -24
View File
@@ -9704,26 +9704,39 @@ body:not(.hub-phone) #page-calculator .calc-layout[data-calc-tab="roll"] [data-c
color: var(--text);
}
.strategy-doc-panel {
padding: 18px 20px 20px;
min-width: 0;
}
.strategy-blog-layout {
display: grid;
grid-template-columns: minmax(0, 1fr) minmax(200px, 260px);
gap: 18px;
align-items: start;
}
.strategy-blog-main {
padding: 16px 18px 18px;
min-width: 0;
display: flex;
flex-direction: column;
height: calc(100dvh - 168px);
min-height: 420px;
max-height: calc(100dvh - 140px);
}
.strategy-blog-layout {
display: grid;
grid-template-columns: minmax(0, 1fr) minmax(220px, 280px);
gap: 16px;
align-items: stretch;
flex: 1 1 auto;
min-height: 0;
}
.strategy-blog-main {
min-width: 0;
min-height: 0;
display: flex;
flex-direction: column;
height: 100%;
}
.strategy-toc-card {
padding: 14px 12px 16px;
position: sticky;
top: 72px;
max-height: calc(100vh - 96px);
top: 0;
align-self: stretch;
height: 100%;
max-height: none;
overflow: auto;
display: flex;
flex-direction: column;
}
.strategy-toc-title {
margin: 0 0 12px;
@@ -9736,17 +9749,20 @@ body:not(.hub-phone) #page-calculator .calc-layout[data-calc-tab="roll"] [data-c
.strategy-toc-nav {
display: flex;
flex-direction: column;
gap: 2px;
gap: 4px;
border-left: 2px solid var(--border-soft);
padding-left: 2px;
flex: 1 1 auto;
min-height: 0;
}
.strategy-toc-item {
display: flex;
align-items: flex-start;
display: grid;
grid-template-columns: auto auto minmax(0, 1fr);
align-items: start;
gap: 8px;
width: 100%;
text-align: left;
padding: 7px 10px;
padding: 8px 10px;
border: none;
border-radius: 0 8px 8px 0;
background: transparent;
@@ -9774,9 +9790,34 @@ body:not(.hub-phone) #page-calculator .calc-layout[data-calc-tab="roll"] [data-c
}
.strategy-toc-num {
flex: 0 0 auto;
min-width: 1.6em;
opacity: 0.85;
min-width: 1.7em;
height: 1.7em;
padding: 0 5px;
border-radius: 999px;
display: inline-flex;
align-items: center;
justify-content: center;
font-size: 0.72rem;
font-weight: 700;
font-variant-numeric: tabular-nums;
color: var(--accent);
background: rgba(0, 212, 255, 0.12);
border: 1px solid rgba(0, 212, 255, 0.35);
}
.strategy-toc-tag {
flex: 0 0 auto;
padding: 1px 6px;
border-radius: 4px;
font-size: 0.68rem;
line-height: 1.4;
color: var(--muted);
background: var(--inset-surface, rgba(0, 0, 0, 0.28));
border: 1px solid var(--border-soft);
white-space: nowrap;
}
.strategy-toc-item.is-active .strategy-toc-tag {
color: var(--accent);
border-color: rgba(0, 212, 255, 0.35);
}
.strategy-toc-text {
flex: 1 1 auto;
@@ -9822,7 +9863,7 @@ body:not(.hub-phone) #page-calculator .calc-layout[data-calc-tab="roll"] [data-c
.strategy-doc-body {
flex: 1 1 auto;
min-height: 0;
max-height: min(70vh, 820px);
max-height: none;
font-size: 0.88rem;
line-height: 1.55;
color: var(--text);
@@ -9832,6 +9873,10 @@ body:not(.hub-phone) #page-calculator .calc-layout[data-calc-tab="roll"] [data-c
scrollbar-gutter: stable;
}
.strategy-doc-body h2 {
display: flex;
align-items: center;
flex-wrap: wrap;
gap: 8px;
font-size: 1.05rem;
margin: 1.1em 0 0.55em;
color: var(--text);
@@ -9840,6 +9885,43 @@ body:not(.hub-phone) #page-calculator .calc-layout[data-calc-tab="roll"] [data-c
.strategy-doc-body h2:first-child {
margin-top: 0;
}
.strategy-sec-mark {
display: inline-flex;
align-items: center;
gap: 6px;
margin-right: 2px;
}
.strategy-sec-num {
display: inline-flex;
align-items: center;
justify-content: center;
min-width: 1.7em;
height: 1.7em;
padding: 0 6px;
border-radius: 999px;
font-size: 0.72rem;
font-weight: 700;
font-variant-numeric: tabular-nums;
color: #041018;
background: var(--accent);
}
.strategy-sec-tag {
display: inline-flex;
align-items: center;
padding: 2px 7px;
border-radius: 4px;
font-size: 0.68rem;
font-weight: 600;
letter-spacing: 0.02em;
color: var(--accent);
background: rgba(0, 212, 255, 0.1);
border: 1px solid rgba(0, 212, 255, 0.35);
}
.strategy-checklist-card {
height: calc(100dvh - 168px);
min-height: 420px;
max-height: calc(100dvh - 140px);
}
.strategy-doc-body h3 {
font-size: 0.94rem;
margin: 1em 0 0.4em;
@@ -9876,8 +9958,9 @@ body:not(.hub-phone) #page-calculator .calc-layout[data-calc-tab="roll"] [data-c
color: var(--muted);
}
.strategy-checklist-body {
flex: 0 0 auto;
overflow: visible;
flex: 1 1 auto;
min-height: 0;
overflow: auto;
padding: 2px 10px 2px 4px;
}
.strategy-checklist-body ul {
@@ -9925,20 +10008,28 @@ body:not(.hub-phone) #page-calculator .calc-layout[data-calc-tab="roll"] [data-c
.strategy-layout {
grid-template-columns: 1fr;
}
.strategy-doc-panel,
.strategy-checklist-card {
height: auto;
max-height: none;
min-height: 0;
}
.strategy-blog-layout {
grid-template-columns: 1fr;
}
.strategy-toc-card {
position: static;
max-height: none;
height: auto;
max-height: min(36vh, 280px);
order: -1;
}
.strategy-doc-card,
.strategy-checklist-card {
align-self: stretch;
}
.strategy-doc-body {
max-height: min(60vh, 640px);
.strategy-doc-body,
.strategy-checklist-body {
max-height: min(58vh, 560px);
}
}
+2 -2
View File
@@ -15,7 +15,7 @@
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
<link href="https://fonts.googleapis.com/css2?family=JetBrains+Mono:wght@400;500;600&family=Orbitron:wght@500;600;700&display=swap" rel="stylesheet" media="print" onload="this.media='all'" />
<noscript><link href="https://fonts.googleapis.com/css2?family=JetBrains+Mono:wght@400;500;600&family=Orbitron:wght@500;600;700&display=swap" rel="stylesheet" /></noscript>
<link rel="stylesheet" href="/assets/app.css?v=20260718-strategy-toc2" />
<link rel="stylesheet" href="/assets/app.css?v=20260718-strategy-marks" />
<link rel="stylesheet" href="/assets/trade_stats_calendar.css?v=4" />
<link rel="stylesheet" href="/assets/account_risk_badge.css?v=4" />
<script src="/assets/account_risk_badge.js?v=4"></script>
@@ -1385,7 +1385,7 @@
<script src="/assets/quotes.js?v=20260717-quotes-feed"></script>
<script src="/assets/funds.js?v=20260717-funds-scroll-fix"></script>
<script src="/assets/dashboard.js?v=20260717-dash-kpi-merge"></script>
<script src="/assets/strategy.js?v=7"></script>
<script src="/assets/strategy.js?v=8"></script>
<script src="/assets/help.js?v=1"></script>
<script src="/assets/logs.js?v=1"></script>
<script src="/assets/ai_review_render.js?v=3"></script>
+33 -6
View File
@@ -1,5 +1,5 @@
/**
* 策略说明:策略正文(博客目录 h2+h3) + 执行清单 Tab.
* 策略说明:策略正文(目录 h2 + 章节标识) + 执行清单 Tab.
*/
(function () {
const page = document.getElementById("page-strategy");
@@ -126,6 +126,22 @@
heads.forEach((h) => scrollSpyObs.observe(h));
}
function sectionTag(title) {
const t = String(title || "");
if (/账户|定位/.test(t)) return "账户";
if (/开仓类型|开仓|入场|反转|顺势|波段|假破|结构/.test(t)) return "入场";
if (/周期/.test(t)) return "周期";
if (/方向/.test(t)) return "方向";
if (/纪律|出场|笔数|节奏/.test(t)) return "纪律";
if (/持仓|离场|强平/.test(t)) return "离场";
if (/资金|杠杆|计仓/.test(t)) return "仓位";
if (/系统|字段|对接/.test(t)) return "系统";
if (/修订|记录/.test(t)) return "版本";
if (/边界|关系|行情状态/.test(t)) return "边界";
if (/选择|如何/.test(t)) return "选择";
return "章节";
}
function buildDocToc() {
if (!docBody || !docToc) return;
const heads = Array.from(docBody.querySelectorAll("h2"));
@@ -136,8 +152,10 @@
const used = {};
const items = [];
heads.forEach((el, idx) => {
const num = String(idx + 1);
let base = "st-" + num + "-" + slugify(el.textContent);
const num = String(idx + 1).padStart(2, "0");
const text = (el.textContent || "").trim();
const tag = sectionTag(text);
let base = "st-" + num + "-" + slugify(text);
if (!base || base === "st-" + num + "-") base = "st-" + num;
let id = base;
let n = 2;
@@ -147,9 +165,17 @@
}
used[id] = true;
el.id = id;
items.push({ num, id, text: (el.textContent || "").trim() });
if (!el.querySelector(".strategy-sec-mark")) {
const mark = document.createElement("span");
mark.className = "strategy-sec-mark";
mark.setAttribute("aria-hidden", "true");
mark.innerHTML =
`<span class="strategy-sec-num">${esc(num)}</span>` +
`<span class="strategy-sec-tag">${esc(tag)}</span>`;
el.insertBefore(mark, el.firstChild);
}
items.push({ num, id, text, tag });
});
// 正文内 h3 仍保留锚点,便于日后扩展,但不进目录
Array.from(docBody.querySelectorAll("h3")).forEach((el, idx) => {
if (el.id) return;
let base = "st-h3-" + (idx + 1) + "-" + slugify(el.textContent);
@@ -165,8 +191,9 @@
docToc.innerHTML = items
.map(
(it) =>
`<a href="#${esc(it.id)}" class="strategy-toc-item level-2" data-id="${esc(it.id)}">` +
`<a href="#${esc(it.id)}" class="strategy-toc-item" data-id="${esc(it.id)}">` +
`<span class="strategy-toc-num">${esc(it.num)}</span>` +
`<span class="strategy-toc-tag">${esc(it.tag)}</span>` +
`<span class="strategy-toc-text">${esc(it.text)}</span></a>`
)
.join("");