feat(ui): close the last gaps against the audit design (31/31)

check_design_parity.py reads its checklist from the audit page's own
proposals; it now reports every one of the 31 as implemented, with no
deliberate divergences left.

  * Schedule: the Kanban/Calendar drop-list became a pair of tabs, and the
    Running lane is outlined while it holds anything — dropping a card there
    starts the task for real, so it should not look like the other six.
  * Cowork: agent / routing / usage / folder moved out of the typing box into
    their own status strip beneath it, styled as status rather than a second
    toolbar. All of them stay interactive; the design's read-only strip would
    have cost features.
  * Folder: the path is written as the screen's title instead of sitting in a
    read-only text box that looked editable and cost a row.
  * GraphRAG: the second toolbar row is gone (Export joined the first), and
    the one button that relabelled itself became Đồ thị | Tin nhắn tabs, so
    the view you are NOT in is named too.
  * Settings gained the theme picker, so language / provider / theme are all
    reachable there as well as on the rail's account row.
  * Task editor: the five group boxes are grouped into three step tabs
    (Nội dung → Lịch chạy → Liên kết). All 22 fields verified present after
    the move; only the old section index is gone, replaced by the tabs.
  * The assistant dot now clears a screen's own bottom bar (Cowork's
    composer), measured from the composer's top edge in window coordinates.

Also adds .gitattributes: without it a Windows checkout records CRLF and
every file reads as fully rewritten to a Linux CI runner.

Verification: 7 check_*.py suites green, no screen clipped at 1920/1366/1280,
and no dialog scrolls sideways at 9/11/14pt.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
NamPDT
2026-08-17 12:25:25 +09:00
co-authored by Claude Opus 5
parent 0fa61b6a95
commit cb68f87b35
15 changed files with 454 additions and 93 deletions
+24 -5
View File
@@ -24,11 +24,30 @@ WIDTHS = (1100, 964, 820, 700)
POINTS = (9, 11, 14) # ~100%, ~125%, ~150% display scaling
def hscroll(dlg):
"""(scroll-area overflow, index overflow) — each True means a bar appears."""
def hscroll(dlg, app):
"""(scroll-area overflow, index overflow) — each True means content is
wider than the space it is given.
A dialog built from step tabs has one scroll area per page, and a page that
is not current has stale geometry — so each tab is brought to the front
before its page is measured.
"""
from PySide6.QtWidgets import QListWidget, QScrollArea
sa = dlg.findChildren(QScrollArea)[0]
over_area = sa.widget().sizeHint().width() > sa.viewport().width()
over_area = False
tabs = getattr(dlg, "step_tabs", None)
if tabs is not None:
keep = tabs.currentIndex()
for i in range(tabs.count()):
tabs.setCurrentIndex(i)
for _ in range(3):
app.processEvents()
sa = tabs.widget(i)
if sa.widget().sizeHint().width() > sa.viewport().width():
over_area = True
tabs.setCurrentIndex(keep)
else:
sa = dlg.findChildren(QScrollArea)[0]
over_area = sa.widget().sizeHint().width() > sa.viewport().width()
idx = dlg.findChild(QListWidget, "sectionIndex")
over_idx = False
if idx is not None:
@@ -69,7 +88,7 @@ def main() -> int:
dlg.resize(w, 900)
for _ in range(4):
app.processEvents()
over_area, over_idx = hscroll(dlg)
over_area, over_idx = hscroll(dlg, app)
row.append(f"{w}:{'A' if over_area else '.'}{'I' if over_idx else '.'}")
if over_area:
fails.append(f"{name} @ {pt}pt {w}px — vung cuon tran ngang")