From 0b3780e0cdf7d715757aafb54f970c54a04315ff Mon Sep 17 00:00:00 2001 From: yuetsh <517252939@qq.com> Date: Tue, 27 Oct 2026 09:31:29 +0800 Subject: [PATCH] =?UTF-8?q?fix:=20=E6=89=B9=E6=94=B9=E9=A1=B5=20J/K=20?= =?UTF-8?q?=E6=8C=89=E9=94=AE=E4=BD=8D=E5=AF=B9=E8=B0=83=EF=BC=9B=E9=A2=84?= =?UTF-8?q?=E8=A7=88=E6=8D=A2=E5=86=85=E5=AE=B9=E4=B8=8D=E5=86=8D=E8=BF=9B?= =?UTF-8?q?=E6=B5=8F=E8=A7=88=E5=99=A8=E5=8E=86=E5=8F=B2=EF=BC=8C=E2=80=9C?= =?UTF-8?q?=E5=90=8E=E9=80=80=E2=80=9D=E8=83=BD=E5=9B=9E=E5=88=B0=E4=BD=9C?= =?UTF-8?q?=E5=93=81=E5=A2=99?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - J 上一个、K 下一个,和面板上的左右箭头一致 - 打开的作品放进地址栏(?sub=):点开记一步历史,J/K 切换只替换,关闭 / Esc 退回那一步 - 所有会换内容的预览 iframe 加 key,换内容时换新的 iframe:在原 iframe 里改 srcdoc 是一次导航, 会进浏览器历史,“后退”就成了在预览里倒退(批改页切换学生、挑战页改代码都会这样) Co-Authored-By: Claude Opus 5.5 --- CLAUDE.md | 2 +- client/src/components/editor/Preview.vue | 5 +++ client/src/components/review/PeersDrawer.vue | 2 +- client/src/components/review/ReviewPanel.vue | 7 +-- .../src/components/workbench/RatingCard.vue | 3 +- client/src/pages/Review.vue | 44 +++++++++++++++---- client/src/pages/Submission.vue | 2 +- 7 files changed, 50 insertions(+), 15 deletions(-) diff --git a/CLAUDE.md b/CLAUDE.md index 6c84c85..2b1158d 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -32,7 +32,7 @@ The backend was rewritten from Django in 2026-10 to cut memory use (~25 MB vs. 1 - `src/icons.ts` — `` renders bundled `lucide-vue-next` icons (works offline); register new names in its map. Fonts are bundled too (`@fontsource/jetbrains-mono`) - `components/workbench/Workbench.vue` — shared challenge / creation page: left = brief + AI chat (`PromptPanel`), right = preview / code (`CodeTabs`) + `VersionBar`. Every assistant message with code is a version; hand edits and pasted external-AI code are saved as versions via `POST /prompt/versions` (`source` `edit` / `manual`, stored as a user+assistant pair). Challenges are submitted only when the student clicks “交这一版” (`POST /submission/` with `message_id`), never automatically. Editor code is per task (`composables/useTaskCode.ts`, localStorage `web-code::`); the tutorial page edits the shared `store/editors.ts` refs but `Workspace.vue` saves them under the same per-task key and `TutorialContent` restores them (example code only the first time) - `pages/ChallengeHome.vue` — challenge list page; `pages/TaskEditor.vue` (prop `kind`) is the single tutorial / challenge authoring page - - `pages/Review.vue` (“批改”, default teaching page) + `components/review/ReviewPanel.vue` (also opened from the gradebook) — opens as a large preview (wall hidden, Esc returns; “小面板” switches to a side panel, remembered); keys: J/K next/prev student, 1–5 rate, P present; “全部班级” groups the wall by class; `components/review/PeersDrawer.vue` is the students' “同学作品” (本班 / 全部班级) + - `pages/Review.vue` (“批改”, default teaching page) + `components/review/ReviewPanel.vue` (also opened from the gradebook) — opens as a large preview (wall hidden, Esc returns; “小面板” switches to a side panel, remembered); keys: J/K previous/next student (by key position), 1–5 rate, P present; “全部班级” groups the wall by class; `components/review/PeersDrawer.vue` is the students' “同学作品” (本班 / 全部班级) - `components/layout/AppShell.vue` — top bar for every page; `pages/Dashboard.vue` is the teaching sidebar (“教学”) under `/dashboard` - `src/store/` — Reactive state (plain Vue refs, not Vuex/Pinia); `prompt.ts` / `guidance.ts` own the WebSockets - `src/pages/`, `src/components/` — user management uses `components/dashboard/UserFormModal.vue` (there is no Django Admin anymore) diff --git a/client/src/components/editor/Preview.vue b/client/src/components/editor/Preview.vue index a03e480..b6d546c 100644 --- a/client/src/components/editor/Preview.vue +++ b/client/src/components/editor/Preview.vue @@ -46,6 +46,7 @@ ref="frame" class="iframe" :sandbox="PREVIEW_SANDBOX" + :key="frameKey" :srcdoc="previewContent" > @@ -141,8 +142,12 @@ function getContent(forDownload = false) { }) } +// 每次内容变了换一个新的 iframe:在同一个 iframe 里改 srcdoc 会进浏览器历史, +// 按“后退”就成了在预览里倒退,而不是离开页面 +const frameKey = ref(0) function preview() { previewContent.value = getContent() + frameKey.value++ } function download() { diff --git a/client/src/components/review/PeersDrawer.vue b/client/src/components/review/PeersDrawer.vue index 45feee3..1712373 100644 --- a/client/src/components/review/PeersDrawer.vue +++ b/client/src/components/review/PeersDrawer.vue @@ -61,7 +61,7 @@ @update:show="(v: boolean) => !v && (large = null)" >
- +
diff --git a/client/src/components/review/ReviewPanel.vue b/client/src/components/review/ReviewPanel.vue index 0c578cb..8ffb0b2 100644 --- a/client/src/components/review/ReviewPanel.vue +++ b/client/src/components/review/ReviewPanel.vue @@ -13,7 +13,7 @@ - 上一个学生(K) + 上一个学生(J) - 下一个学生(J) + 下一个学生(K)
- + +
diff --git a/client/src/components/workbench/RatingCard.vue b/client/src/components/workbench/RatingCard.vue index c8ce1f5..9dc984d 100644 --- a/client/src/components/workbench/RatingCard.vue +++ b/client/src/components/workbench/RatingCard.vue @@ -10,6 +10,7 @@