Эх сурвалжийг харах

fix(admin): tighten schedule toolbar layout

彭峰 2 сар өмнө
parent
commit
70f08f1850

+ 47 - 0
design-qa.md

@@ -49,6 +49,53 @@ final result: passed
 
 ---
 
+# Design QA: 排课中心筛选工具栏收紧
+
+## Evidence
+
+- Source visual truth: `/var/folders/yx/cq4gbk4x6w702x_slllw80mw0000gn/T/TemporaryItems/NSIRD_screencaptureui_SnOJSi/截屏2026-08-20 09.27.50.png`.
+- Source dimensions: 2974 x 228 px toolbar crop captured from the existing desktop page.
+- Implementation route: `http://127.0.0.1:54535/admin/schedule`.
+- Implementation screenshot: `/Users/mac/.codex/visualizations/2026/08/18/01a0129d-4374-7200-b8f1-0c65ae6eebc9/schedule-search-audit/08-toolbar-after-refine.png`.
+- Implementation viewport and dimensions: 1792 x 1064 CSS px at the browser capture density.
+- State: authenticated operations administrator, day view, historical date `2024-07-20`, all coaches selected, latest-data shortcut visible.
+- Density normalization: the source is a high-density focused toolbar crop while the implementation is a full-page browser capture. The same toolbar state was opened together for a focused structural comparison; pixel-identical scaling was not used because the requested result intentionally changes the source proportions.
+
+## Full-View Comparison
+
+- The shortened coach selector leaves a clear flexible gap before the latest-data shortcut and removes the visually dominant full-width dropdown.
+- The toolbar remains a single row at the verified desktop viewport and preserves the existing page hierarchy, summary cards, and schedule lanes.
+- The latest-data shortcut stays right-aligned and all existing interactions remain available.
+
+## Focused Comparison
+
+- The source crop and implementation screenshot were opened together in one comparison input.
+- The day/week/list switcher, previous button, date input, next button, coach selector, and latest-data button now share a 44 px control height.
+- The coach selector is capped at 360 px on wide screens, reduces to a flexible 340 px maximum below 1300 px, and becomes full-width below 700 px.
+
+## Findings
+
+- No actionable P0, P1, or P2 differences remain for the requested changes.
+- Typography: existing application font, weight, labels, and hierarchy are preserved; no wrapping or truncation was introduced.
+- Spacing and layout: the oversized coach-filter track was replaced with a bounded control while retaining 12 px toolbar gaps and bottom alignment.
+- Colors and tokens: existing border, surface, focus, and brand-green tokens are unchanged.
+- Image quality and assets: this toolbar contains no raster imagery or custom decorative assets; existing Lucide interface icons remain sharp.
+- Copy and content: all operational labels and values are unchanged.
+
+## Comparison History
+
+1. Source finding: the coach dropdown consumed nearly all remaining horizontal space and the control heights appeared inconsistent.
+2. Fix: added dedicated `coach-filter` and `latest-data` layout classes, capped the filter width, and normalized interactive controls to 44 px.
+3. Post-fix evidence: the implementation screenshot shows a compact selector, consistent control heights, preserved right alignment, and no desktop overflow.
+
+## Follow-up Polish
+
+- No additional P3 changes are needed for this focused request.
+
+final result: passed
+
+---
+
 # Design QA: 学习记录 AI 阅读入口
 
 ## Evidence

+ 2 - 2
src/app/admin/pages/operations-schedule.component.html

@@ -15,8 +15,8 @@
   <button type="button" aria-label="上一时间段" (click)="move(view()==='week'?-7:-1)"><lucide-icon [img]="icons.ChevronLeft" [size]="17" /></button>
   <label><span>日期</span><input type="date" [ngModel]="date()" (ngModelChange)="date.set($event);load()" /></label>
   <button type="button" aria-label="下一时间段" (click)="move(view()==='week'?7:1)"><lucide-icon [img]="icons.ChevronRight" [size]="17" /></button>
-  <label class="grow"><span>陪练筛选</span><select [ngModel]="coachFilter()" (ngModelChange)="coachFilter.set(+$event);load()"><option [ngValue]="0">全部陪练</option>@for(coach of data()?.coaches||[];track coach.userId){<option [ngValue]="coach.userId">{{coach.displayName}}</option>}</select></label>
-  @if(data()?.dataDateTo){<button type="button" (click)="showLatest()">最近有数据:{{data()?.dataDateTo}}</button>}
+  <label class="coach-filter"><span>陪练筛选</span><select [ngModel]="coachFilter()" (ngModelChange)="coachFilter.set(+$event);load()"><option [ngValue]="0">全部陪练</option>@for(coach of data()?.coaches||[];track coach.userId){<option [ngValue]="coach.userId">{{coach.displayName}}</option>}</select></label>
+  @if(data()?.dataDateTo){<button class="latest-data" type="button" (click)="showLatest()">最近有数据:{{data()?.dataDateTo}}</button>}
 </section>
 
 @if(message()){<p class="notice" role="status">{{message()}}</p>}

+ 51 - 0
src/app/admin/pages/operations-schedule.component.scss

@@ -61,6 +61,41 @@ textarea:focus-visible {
   border-radius: 12px;
 }
 
+.toolbar > button,
+.toolbar label input,
+.toolbar label select,
+.toolbar .segmented {
+  box-sizing: border-box;
+  height: 44px;
+  min-height: 44px;
+}
+
+.toolbar .segmented {
+  flex: 0 0 auto;
+  align-items: stretch;
+}
+
+.toolbar .segmented button {
+  min-height: 36px;
+}
+
+.toolbar .coach-filter {
+  flex: 0 1 360px;
+  width: 360px;
+  min-width: 260px;
+  max-width: 360px;
+}
+
+.toolbar .coach-filter select {
+  width: 100%;
+}
+
+.toolbar .latest-data {
+  flex: 0 0 auto;
+  margin-left: auto;
+  white-space: nowrap;
+}
+
 .toolbar .segmented,
 .drawer > .segmented {
   border-radius: 13px;
@@ -313,6 +348,12 @@ textarea:focus-visible {
   .summary-grid {
     grid-template-columns: repeat(3, minmax(0, 1fr));
   }
+
+  .toolbar .coach-filter {
+    flex: 1 1 280px;
+    width: auto;
+    max-width: 340px;
+  }
 }
 
 @media (max-width: 700px) {
@@ -328,4 +369,14 @@ textarea:focus-visible {
   .summary-grid {
     grid-template-columns: 1fr;
   }
+
+  .toolbar .coach-filter {
+    flex-basis: 100%;
+    width: 100%;
+    max-width: none;
+  }
+
+  .toolbar .latest-data {
+    margin-left: 0;
+  }
 }