Skip to content

Commit b54ad01

Browse files
committed
Move schedule table to plan view
1 parent 9967336 commit b54ad01

3 files changed

Lines changed: 121 additions & 28 deletions

File tree

assets/site.js

Lines changed: 51 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -279,6 +279,7 @@ const copy = {
279279
zh: {
280280
brandLine: "AI Coding 工程工作流手册",
281281
plannerMode: "学习清单",
282+
scheduleMode: "学习计划",
282283
readerMode: "全文阅读",
283284
navKicker: "Feynman Loop",
284285
navTitle: "19 章 · 36 天费曼间隔练习",
@@ -303,6 +304,10 @@ const copy = {
303304
noteKicker: "Teach Back",
304305
noteTitle: "费曼讲解草稿",
305306
notePlaceholder: "我会这样向一个刚开始用 AI Coding 的朋友解释今天的内容...",
307+
scheduleKicker: "Learning Plan",
308+
scheduleTitle: "36 天学习计划",
309+
scheduleSummary: "每天一个新章,到期旧章按 2-3-5-7 间隔短复述。",
310+
scheduleOpenDay: "回到今日清单",
306311
matrixKicker: "Schedule Table",
307312
matrixTitle: "间隔学习总表",
308313
resetMatrix: "清空表格勾选",
@@ -344,6 +349,7 @@ const copy = {
344349
en: {
345350
brandLine: "AI coding engineering workflow",
346351
plannerMode: "Checklist",
352+
scheduleMode: "Plan",
347353
readerMode: "Reader",
348354
navKicker: "Feynman Loop",
349355
navTitle: "19 Chapters · 36-Day Feynman Spacing",
@@ -368,6 +374,10 @@ const copy = {
368374
noteKicker: "Teach Back",
369375
noteTitle: "Feynman Draft",
370376
notePlaceholder: "I would explain today's material to a friend starting AI coding like this...",
377+
scheduleKicker: "Learning Plan",
378+
scheduleTitle: "36-Day Learning Plan",
379+
scheduleSummary: "One new chapter per day; due reviews return on a 2-3-5-7 cadence.",
380+
scheduleOpenDay: "Today's checklist",
371381
matrixKicker: "Schedule Table",
372382
matrixTitle: "Spaced Learning Table",
373383
resetMatrix: "Clear table checks",
@@ -508,12 +518,14 @@ const els = {
508518
body: document.body,
509519
brandLine: document.querySelector("#brand-line"),
510520
plannerModeLabel: document.querySelector("#planner-mode-label"),
521+
scheduleModeLabel: document.querySelector("#schedule-mode-label"),
511522
readerModeLabel: document.querySelector("#reader-mode-label"),
512523
plannerView: document.querySelector("#planner-view"),
524+
scheduleView: document.querySelector("#schedule-view"),
513525
readerView: document.querySelector("#reader-view"),
514526
plannerNav: document.querySelector("#planner-nav"),
515527
readerNav: document.querySelector("#reader-nav"),
516-
modeButtons: [...document.querySelectorAll("button[data-mode]")],
528+
modeButtons: [...document.querySelectorAll(".view-toggle button[data-mode]")],
517529
langButtons: [...document.querySelectorAll("button[data-lang]")],
518530
pdf: document.querySelector("#pdf-link"),
519531
plannerNavKicker: document.querySelector("#planner-nav-kicker"),
@@ -554,6 +566,10 @@ const els = {
554566
noteKicker: document.querySelector("#note-kicker"),
555567
noteTitle: document.querySelector("#note-title"),
556568
note: document.querySelector("#explain-note"),
569+
scheduleKicker: document.querySelector("#schedule-kicker"),
570+
scheduleTitle: document.querySelector("#schedule-title"),
571+
scheduleSummary: document.querySelector("#schedule-summary"),
572+
scheduleOpenDayLabel: document.querySelector("#schedule-open-day-label"),
557573
checklistKicker: document.querySelector("#checklist-kicker"),
558574
checklistTitle: document.querySelector("#checklist-title"),
559575
resetDay: document.querySelector("#reset-day-button"),
@@ -588,7 +604,9 @@ function preferredLanguage() {
588604
function preferredMode() {
589605
const params = new URLSearchParams(window.location.search);
590606
const requested = params.get("view") || params.get("mode");
591-
return requested === "reader" || requested === "read" ? "reader" : "planner";
607+
if (requested === "reader" || requested === "read") return "reader";
608+
if (requested === "schedule" || requested === "plan") return "schedule";
609+
return "planner";
592610
}
593611

594612
function preferredDay() {
@@ -793,6 +811,7 @@ function setLanguageChrome(lang) {
793811
document.documentElement.lang = lang === "zh" ? "zh-CN" : "en";
794812
els.brandLine.textContent = text.brandLine;
795813
els.plannerModeLabel.textContent = text.plannerMode;
814+
els.scheduleModeLabel.textContent = text.scheduleMode;
796815
els.readerModeLabel.textContent = text.readerMode;
797816
els.pdf.href = doc.pdf;
798817
els.pdf.title = text.pdf;
@@ -814,11 +833,13 @@ function setLanguageChrome(lang) {
814833
}
815834

816835
function setMode(mode, shouldUpdateUrl = true) {
817-
state.mode = mode === "reader" ? "reader" : "planner";
836+
const modes = new Set(["planner", "schedule", "reader"]);
837+
state.mode = modes.has(mode) ? mode : "planner";
818838
els.body.dataset.mode = state.mode;
819839
els.plannerView.hidden = state.mode !== "planner";
840+
els.scheduleView.hidden = state.mode !== "schedule";
820841
els.readerView.hidden = state.mode !== "reader";
821-
els.plannerNav.hidden = state.mode !== "planner";
842+
els.plannerNav.hidden = state.mode === "reader";
822843
els.readerNav.hidden = state.mode !== "reader";
823844

824845
els.modeButtons.forEach((button) => {
@@ -836,7 +857,7 @@ function updateUrl() {
836857
const params = new URLSearchParams(window.location.search);
837858
params.set("lang", state.lang);
838859
params.set("day", String(state.day));
839-
params.set("view", state.mode === "reader" ? "reader" : "planner");
860+
params.set("view", state.mode);
840861
const hash = state.mode === "reader" ? window.location.hash : "";
841862
window.history.replaceState(null, "", `${window.location.pathname}?${params.toString()}${hash}`);
842863
}
@@ -958,9 +979,6 @@ function renderPlanner() {
958979
els.overallStatLabel.textContent = text.overallStat;
959980
els.scopeKicker.textContent = text.scopeKicker;
960981
els.scopeTitle.textContent = text.scopeTitle;
961-
els.matrixKicker.textContent = text.matrixKicker;
962-
els.matrixTitle.textContent = text.matrixTitle;
963-
els.resetMatrixLabel.textContent = text.resetMatrix;
964982
els.noteKicker.textContent = text.noteKicker;
965983
els.noteTitle.textContent = text.noteTitle;
966984
els.note.placeholder = text.notePlaceholder;
@@ -973,13 +991,27 @@ function renderPlanner() {
973991
els.note.value = getStoredText(noteId(state.day));
974992

975993
renderDayList();
976-
renderScheduleTable();
977994
renderScope();
978995
renderChecklist();
979996
updatePlannerProgress();
980997
window.lucide?.createIcons();
981998
}
982999

1000+
function renderSchedulePlan() {
1001+
const text = copy[state.lang];
1002+
1003+
els.scheduleKicker.textContent = text.scheduleKicker;
1004+
els.scheduleTitle.textContent = text.scheduleTitle;
1005+
els.scheduleSummary.textContent = text.scheduleSummary;
1006+
els.scheduleOpenDayLabel.textContent = text.scheduleOpenDay;
1007+
els.matrixKicker.textContent = text.matrixKicker;
1008+
els.matrixTitle.textContent = text.matrixTitle;
1009+
els.resetMatrixLabel.textContent = text.resetMatrix;
1010+
1011+
renderScheduleTable();
1012+
window.lucide?.createIcons();
1013+
}
1014+
9831015
function renderDayList() {
9841016
const text = copy[state.lang];
9851017
els.dayList.innerHTML = "";
@@ -1289,6 +1321,7 @@ function setDay(day, shouldUpdateUrl = true) {
12891321
state.day = next;
12901322
setStoredText("feynman:v4:last-day", String(next));
12911323
renderPlanner();
1324+
renderSchedulePlan();
12921325
if (shouldUpdateUrl) updateUrl();
12931326
window.scrollTo({ top: 0, behavior: "smooth" });
12941327
}
@@ -1297,6 +1330,7 @@ function resetDay(day) {
12971330
getDayTaskDefs(day).forEach((task) => removeStored(task.id));
12981331
removeStored(noteId(day));
12991332
renderPlanner();
1333+
renderSchedulePlan();
13001334
}
13011335

13021336
function resetAllProgress() {
@@ -1308,6 +1342,7 @@ function resetAllProgress() {
13081342
removeStored(noteId(day));
13091343
}
13101344
renderPlanner();
1345+
renderSchedulePlan();
13111346
}
13121347

13131348
function resetMatrixProgress() {
@@ -1316,13 +1351,14 @@ function resetMatrixProgress() {
13161351
for (let day = 1; day <= PLAN_DAY_COUNT; day += 1) {
13171352
getScheduleMatrixItems(day).forEach((item) => removeStored(item.id));
13181353
}
1319-
renderScheduleTable();
1354+
renderSchedulePlan();
13201355
}
13211356

13221357
async function loadGuide(lang, shouldUpdateUrl = true) {
13231358
state.lang = lang;
13241359
setLanguageChrome(lang);
13251360
renderPlanner();
1361+
renderSchedulePlan();
13261362
els.article.classList.add("loading");
13271363
els.article.innerHTML = copy[lang].loading;
13281364
els.status.textContent = `${docs[lang].status} · loading`;
@@ -1527,7 +1563,11 @@ document.addEventListener("click", (event) => {
15271563

15281564
const dayButton = event.target.closest("button[data-day]");
15291565
if (dayButton) {
1566+
const isScheduleDay = Boolean(dayButton.closest("#schedule-table"));
15301567
setDay(Number(dayButton.dataset.day));
1568+
if (isScheduleDay) {
1569+
setMode("planner");
1570+
}
15311571
return;
15321572
}
15331573

@@ -1586,5 +1626,6 @@ state.mode = preferredMode();
15861626
state.day = preferredDay();
15871627
setLanguageChrome(state.lang);
15881628
renderPlanner();
1629+
renderSchedulePlan();
15891630
setMode(state.mode, false);
15901631
state.guidePromise = loadGuide(state.lang, false).catch(showError);

assets/styles.css

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -489,13 +489,18 @@ button:disabled {
489489
}
490490

491491
.planner-view,
492+
.schedule-view,
492493
.reader-view {
493494
width: min(100%, calc(var(--content) + clamp(2rem, 7vw, 7rem)));
494495
max-width: 100%;
495496
margin: 0 auto;
496497
padding: clamp(1rem, 3vw, 2.4rem) clamp(1rem, 4vw, 3.5rem) 5rem;
497498
}
498499

500+
.schedule-view {
501+
width: min(100%, calc(72rem + clamp(2rem, 7vw, 7rem)));
502+
}
503+
499504
.reader-view {
500505
width: min(100%, calc(var(--reader-content) + clamp(2rem, 7vw, 7rem)));
501506
}
@@ -525,6 +530,7 @@ button:disabled {
525530
}
526531

527532
.learning-hero p:not(.eyebrow),
533+
.schedule-hero p,
528534
.reader-summary {
529535
max-width: 45rem;
530536
margin: 0;
@@ -608,6 +614,23 @@ button:disabled {
608614
line-height: 1;
609615
}
610616

617+
.schedule-hero {
618+
display: grid;
619+
grid-template-columns: minmax(0, 1fr) auto;
620+
gap: 1rem;
621+
align-items: end;
622+
padding: clamp(1rem, 3vw, 2rem) 0 clamp(1.25rem, 3vw, 2.25rem);
623+
border-bottom: 1px solid var(--line);
624+
}
625+
626+
.schedule-hero h1 {
627+
max-width: 45rem;
628+
margin: 0.2rem 0 0;
629+
font-size: clamp(2rem, 4vw, 3.4rem);
630+
line-height: 1.05;
631+
letter-spacing: 0;
632+
}
633+
611634
.matrix-section,
612635
.scope-section,
613636
.note-section,
@@ -616,6 +639,10 @@ button:disabled {
616639
border-top: 1px solid var(--line);
617640
}
618641

642+
.schedule-view .matrix-section {
643+
border-top: 0;
644+
}
645+
619646
.section-heading {
620647
display: grid;
621648
gap: 0.38rem;
@@ -1284,6 +1311,7 @@ button:disabled {
12841311
}
12851312

12861313
.planner-view,
1314+
.schedule-view,
12871315
.reader-view {
12881316
padding-top: 1rem;
12891317
}
@@ -1345,10 +1373,16 @@ button:disabled {
13451373
}
13461374

13471375
.learning-hero h1,
1376+
.schedule-hero h1,
13481377
.reader-hero h1 {
13491378
font-size: 2.12rem;
13501379
}
13511380

1381+
.schedule-hero {
1382+
grid-template-columns: 1fr;
1383+
align-items: start;
1384+
}
1385+
13521386
.hero-actions {
13531387
display: grid;
13541388
grid-template-columns: 1fr;

index.html

Lines changed: 36 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -19,12 +19,12 @@
1919
<meta name="twitter:card" content="summary" />
2020
<link rel="canonical" href="https://lling0000.github.io/Vibe_coding_guide/" />
2121
<title>Vibe Coding Guide | AI Coding 工程工作流手册</title>
22-
<link rel="stylesheet" href="./assets/styles.css?v=20260617" />
22+
<link rel="stylesheet" href="./assets/styles.css?v=20260617-plan" />
2323
<script defer src="https://cdn.jsdelivr.net/npm/dompurify@3.2.6/dist/purify.min.js"></script>
2424
<script defer src="https://cdn.jsdelivr.net/npm/marked@15.0.12/marked.min.js"></script>
2525
<script defer src="https://cdn.jsdelivr.net/npm/mermaid@11.4.1/dist/mermaid.min.js"></script>
2626
<script defer src="https://cdn.jsdelivr.net/npm/lucide@0.475.0/dist/umd/lucide.min.js"></script>
27-
<script defer src="./assets/site.js?v=20260617-spaced"></script>
27+
<script defer src="./assets/site.js?v=20260617-plan"></script>
2828
</head>
2929
<body data-mode="planner">
3030
<div class="site-progress" aria-hidden="true">
@@ -46,6 +46,10 @@
4646
<i data-lucide="list-checks" aria-hidden="true"></i>
4747
<span id="planner-mode-label">学习清单</span>
4848
</button>
49+
<button type="button" class="segmented-button" data-mode="schedule" aria-pressed="false">
50+
<i data-lucide="calendar-days" aria-hidden="true"></i>
51+
<span id="schedule-mode-label">学习计划</span>
52+
</button>
4953
<button type="button" class="segmented-button" data-mode="reader" aria-pressed="false">
5054
<i data-lucide="book-open-text" aria-hidden="true"></i>
5155
<span id="reader-mode-label">全文阅读</span>
@@ -157,22 +161,6 @@ <h1 id="planner-title">Day 1:新学第 1 章</h1>
157161
</div>
158162
</div>
159163

160-
<section class="matrix-section" aria-labelledby="matrix-title">
161-
<div class="section-heading split">
162-
<div>
163-
<p class="eyebrow" id="matrix-kicker">Schedule Table</p>
164-
<h2 id="matrix-title">间隔学习总表</h2>
165-
</div>
166-
<button type="button" class="text-button" id="reset-matrix-button">
167-
<i data-lucide="eraser" aria-hidden="true"></i>
168-
<span id="reset-matrix-label">清空表格勾选</span>
169-
</button>
170-
</div>
171-
<div class="schedule-table-wrap">
172-
<table class="schedule-table" id="schedule-table"></table>
173-
</div>
174-
</section>
175-
176164
<section class="scope-section" aria-labelledby="scope-title">
177165
<div class="section-heading">
178166
<p class="eyebrow" id="scope-kicker">Spaced Practice</p>
@@ -204,6 +192,36 @@ <h2 id="checklist-title">今日任务清单</h2>
204192
</section>
205193
</section>
206194

195+
<section class="schedule-view" id="schedule-view" aria-labelledby="schedule-title" hidden>
196+
<div class="schedule-hero">
197+
<div>
198+
<p class="eyebrow" id="schedule-kicker">Learning Plan</p>
199+
<h1 id="schedule-title">36 天学习计划</h1>
200+
<p id="schedule-summary">每天一个新章,到期旧章按 2-3-5-7 间隔短复述。</p>
201+
</div>
202+
<button type="button" class="text-button primary" data-mode="planner">
203+
<i data-lucide="list-checks" aria-hidden="true"></i>
204+
<span id="schedule-open-day-label">回到今日清单</span>
205+
</button>
206+
</div>
207+
208+
<section class="matrix-section" aria-labelledby="matrix-title">
209+
<div class="section-heading split">
210+
<div>
211+
<p class="eyebrow" id="matrix-kicker">Schedule Table</p>
212+
<h2 id="matrix-title">间隔学习总表</h2>
213+
</div>
214+
<button type="button" class="text-button" id="reset-matrix-button">
215+
<i data-lucide="eraser" aria-hidden="true"></i>
216+
<span id="reset-matrix-label">清空表格勾选</span>
217+
</button>
218+
</div>
219+
<div class="schedule-table-wrap">
220+
<table class="schedule-table" id="schedule-table"></table>
221+
</div>
222+
</section>
223+
</section>
224+
207225
<section class="reader-view" id="reader-view" aria-labelledby="reader-title" hidden>
208226
<div class="reader-hero">
209227
<p class="eyebrow" id="reader-kicker">Field Guide</p>

0 commit comments

Comments
 (0)