Files
solution-erp/broadcasts/inbox/namgroup/2026-06-09-namgroup-to-se-ui-design-conventions.md
pqhuy1987 84fa638006 [CLAUDE] Docs: check-email — pull NAMGROUP UI design conventions (namgroup→se, verify ✓, processed)
Harness 3 inbound: 2026-06-09-namgroup-to-se-ui-design-conventions. Whole-file + body SHA256 both PASS (0140b81f). Bộ quy ước UI density-first ERP (system-font, zinc-neutral, 2-panel list+detail, drawer/inline patterns; brand color Solution tự quyết).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-09 11:06:30 +07:00

177 lines
9.7 KiB
Markdown
Raw Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

---
id: 2026-06-09-namgroup-to-se-ui-design-conventions
from: namgroup
to: se
category: Coord
type: coord
date: 2026-06-09
content_sha256: 0140b81fb8a6cbe0ce1c36cf788e1c9057ef7f30c0c7c8bd865688429fc9246a
nac: sent
---
# NAMGROUP → Solution — Bộ quy ước giao diện (UI/UX · CSS · typography · layout · panel)
Chào team Solution 👋 Đây là tổng hợp **cách NAMGROUP bài trí giao diện web** để Solution tham khảo / áp dụng: kiến trúc layout, CSS methodology, typography, kích cỡ + mật độ, và các pattern panel / component.
> ⚠️ **Phạm vi (anh pqhuy chốt rõ):** NAMGROUP chia sẻ **cấu trúc + quy ước** (layout, CSS, font, sizing, cách bố trí panel). **Màu sắc thương hiệu, logo, nhận diện → Solution TỰ QUYẾT.** Mục "color system" bên dưới chỉ mô tả **cấu trúc token** (vai trò semantic), KHÔNG áp bảng màu cụ thể của NAMGROUP — Solution chọn hue thương hiệu riêng.
> **Nguồn:** design language NAMGROUP kế thừa từ **PURO / ERP_MINI** — triết lý *"Surgical Precision Minimalism: zero decoration, dense, fast, no noise"* (cảm hứng SAP Fiori + Linear.app). Canonical token nội bộ: `docs/reference/puro-design-tokens.md`.
> **Stack note:** ví dụ code dưới là **Tailwind CSS utility-first** (NAMGROUP dùng React 19 + Tailwind + `cn()` helper). Nếu Solution không dùng Tailwind → map class sang CSS tương ứng; **giá trị px + quy ước thì áp dụng được cho mọi stack**.
---
## 1. Triết lý mật độ — density-first
Mục tiêu: ERP nội bộ = nhiều dữ liệu, ít trang trí. Pack thông tin dày, đọc nhanh, không noise.
- Button dùng **12px** (`text-xs`), KHÔNG 14px — packs density.
- Input cao **≤ 36px** (`py-1.5`), KHÔNG `py-2` / `py-3`.
- Data cell bảng **12px**, meta/timestamp **11px**.
- Icon **14px** (`h-3.5 w-3.5`) — match tỉ lệ với text.
- **Reject:** shadow / gradient trang trí (trừ khi semantic) · button to · input cao.
---
## 2. Typography
**2.1 Font family — system stack thuần (KHÔNG load custom font):**
```
ui-sans-serif, system-ui, -apple-system, "Segoe UI", Roboto, Arial, "Apple Color Emoji", "Segoe UI Emoji"
-webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale;
```
→ tận dụng OS native rendering, zero network cost, render mượt nhất trên mọi máy. (Không Google Fonts / Inter.)
**2.2 Size scale:**
| Vai trò | Size | Class (Tailwind) |
|---|---|---|
| Body mặc định | 14px | `text-sm` |
| Tiêu đề trang (page header) | 15px | `text-[15px]` |
| Button | 12px | `text-xs` |
| Label / section header | 12px UPPERCASE | `text-xs uppercase tracking-wider` |
| Data cell (bảng) | 12px | `text-[12px]` |
| Meta (timestamp, helper) | 11px | `text-[11px]` |
| Stats display | 24px | `text-2xl` (chỉ số liệu) |
**2.3 Weight rules:**
- Button: **luôn** `font-semibold` (600) — KHÔNG `font-bold`.
- Label: `font-semibold` + `uppercase` + `tracking-wider` (scan pattern đặc trưng).
- Body: regular (400).
- Page header: `font-semibold` (KHÔNG `font-bold`).
**2.4 rem base:** `html { font-size: 14px }` (= 87.5% so với 16px mặc định) để `text-sm` body khớp PURO. ⚠️ Lưu ý: đổi root font-size sẽ scale TOÀN site theo rem — verify base trước khi port class.
---
## 3. Layout architecture (app shell)
**3.1 Khung tổng:** `Sidebar (w-72 = 288px) | Content (flex-1)`.
- Sidebar cố định trái, content cuộn. Mobile: sidebar thành drawer `fixed inset-y-0 translate-x-0/-translate-x-full` + backdrop, desktop `lg:relative lg:translate-x-0`.
**3.2 Page header (đầu mỗi trang):** `text-[15px] font-semibold text-zinc-800` + (tùy) toolbar CRUD bên phải. Gọn 1 dòng, KHÔNG block lớn.
**3.3 List + Detail 2-panel (pattern chủ lực cho màn quản lý):**
- `flex h-full`: LEFT = danh sách (drawer trên mobile) · RIGHT = chi tiết inline (KHÔNG modal giữa màn).
- Click row → đổi detail bên phải (giữ list context), KHÔNG mở popup che màn.
- Density: row bảng `text-[12px]`, header `th uppercase tracking-wider`.
---
## 4. Panel / component patterns
**4.1 Drawer slide-in (form ≥ 8 field):**
- Trượt từ phải, width **~600px** (form dày dùng tới **820px**), `max-w-[90vw]`.
- Backdrop `bg-black/30` (+ blur tùy chọn). Body = **2-col grid** form. Footer `bg-zinc-50/70` + nút Lưu bên phải.
- Keyframe: `@keyframes slideInRight { from { transform: translateX(100%) } to { transform: translateX(0) } }`.
- Dual-mode (create/edit) trong **1 drawer**: state `editingId: number | null` → POST vs PUT + đổi tiêu đề + label nút động.
**4.2 Inline edit "bậc thang" (sub-table ≤ 7 field):**
- Click "Thêm" → 1 **row inline** chèn lên đầu, nền accent nhạt (`bg-blue-50/40` create / `bg-amber-50/40` edit) + nút Lưu (check xanh) / Hủy (X) + phím tắt `Esc` / `Ctrl+Enter`.
- Cell đang sửa: `border-blue-300` + `focus:ring-1`. Chỉ 1 row sửa tại 1 thời điểm (state `editing` mutual-exclusion).
- < 7 field dùng bậc thang; 8 field dùng drawer (4.1).
**4.3 KPI card (dashboard):** card trắng + số `text-2xl` + label `text-xs uppercase` + (tùy) clickable filter. Bố cục grid đều.
**4.4 DataTable (bảng dữ liệu):**
- `thead` **sticky** `top-0 z-10`. `th` style label: `uppercase tracking-wider text-zinc-500`.
- Row hover nền nhạt (`hover:bg-{primary}-50/30`), selected đậm hơn (`/60`).
- Row actions (view/edit/delete) = icon-button **7×7** (`h-7 w-7 rounded-md`), icon 14px, hover đổi nền theo tone (default/danger/success). **KHÔNG** ẩn action sau `opacity-0 group-hover` (touch-device không thấy) để actions **luôn hiện**.
---
## 5. Form conventions
**5.1 Input field:**
```
mt-1 w-full rounded-lg border border-zinc-200 bg-white
px-3 py-1.5 text-sm outline-none transition-colors
focus:border-{primary}-400 focus:ring-2 focus:ring-{primary}-500/10
```
- Border `zinc-200` focus đổi sang hue primary (Solution chọn). Ring **10% opacity** = glow mềm, không loud.
- Padding `px-3 py-1.5` (compact). Radius `rounded-lg` (8px). Nền **trắng**. Gap dưới label `mt-1` (4px).
**5.2 Label:** `text-xs font-semibold text-zinc-400 uppercase tracking-wider`
- Màu `zinc-400` (nhạt, hierarchy mềm) + uppercase + tracking-wider = scan pattern đặc trưng.
**5.3 Field wrapper + grid:** wrapper `<label>` bọc (label-div + input), hỗ trợ `span2`/`span3` trong grid.
- Form dày: `grid-cols-2 md:grid-cols-4 gap-x-4 gap-y-3`. Section header `text-xs font-semibold uppercase` + `border-b` + nền nhạt + `px-4 py-1.5`.
---
## 6. Status badge + button
**6.1 Status badge (pattern brand-agnostic):**
```
rounded-full border px-1.5 py-0.5 text-xs font-semibold
bg-{color}-50 text-{color}-700 ← nền tint nhạt + chữ saturated
```
dụ map trạng thái (Solution đổi màu theo ý): Active = green-50/700 · Warning = amber-50/700 · Danger = red-50/600 · Draft = neutral-100/600.
**6.2 Button base (mọi variant share):**
```
inline-flex items-center justify-center gap-1.5
rounded-lg px-3 py-1.5 text-xs font-semibold transition-colors
focus-visible:ring-2 focus-visible:ring-offset-1
disabled:opacity-50 disabled:pointer-events-none
```
Icon trong button 14px. Variant theo **vai trò** (KHÔNG theo màu cứng): primary (action chính) · outline (hủy/đóng) · outline-add (thêm/tạo) · success (duyệt) · danger (xóa) · ghost (action nhẹ trong row). Loading thay icon bằng spinner 14px.
---
## 7. Color SYSTEM — chỉ CẤU TRÚC, hue do Solution chọn
> NAMGROUP **KHÔNG** áp bảng màu — đây là **cách tổ chức token** để Solution tự gắn hue thương hiệu:
1. **1 token `primary`** cho action chính (Tìm/Lưu/Login) + focus accent. Solution chọn hue.
2. **Neutral scale 1 họ duy nhất** NAMGROUP dùng `zinc` (nhất quán, KHÔNG trộn `gray`/`stone`). Vai trò: page-bg (50) · border (200/300) · text (900/700) · label-muted (400/500) · icon-ghost (400).
3. **Semantic status** cố định vai trò (success/warning/danger/info) pattern badge `bg-{c}-50 + text-{c}-700`. Hue Solution chọn.
4. **Khuyến nghị:** xài **utility class trực tiếp** (Tailwind) thay phụ thuộc CSS var `--primary` cho từng nút dễ đọc, ít magic. (CSS var chỉ để theme-level / branding runtime.)
**Logo, brand hue, nhận diện = Solution quyết hoàn toàn.** Chỉ giữ chung *cấu trúc 4 nhóm token* trên để hệ thống nhất quán.
---
## 8. Checklist nhanh khi áp dụng
- [ ] Font: system stack, KHÔNG custom font.
- [ ] Body `text-sm`, button `text-xs font-semibold`, label `text-xs uppercase tracking-wider`.
- [ ] Neutral 1 họ (zinc) KHÔNG trộn gray/stone.
- [ ] Input `py-1.5` (≤36px), `rounded-lg`, focus ring 10% opacity.
- [ ] List+Detail 2-panel inline (KHÔNG modal giữa màn cho detail).
- [ ] Form 8 field drawer slide-in; sub-table 7 field inline "bậc thang".
- [ ] Table actions LUÔN hiện (KHÔNG hover-hide).
- [ ] KHÔNG `font-bold` (dùng `font-semibold`), KHÔNG shadow/gradient trang trí.
---
## 9. References
- PURO live demo (tham khảo trực quan): `http://103.97.126.104:8080/` (IP-only HTTP).
- NAMGROUP portal (sau khi áp): `https://portaltest.namgroup.vn`.
- Token canonical nội bộ NAMGROUP: `docs/reference/puro-design-tokens.md` (10 mục: color · typography · form · button · badge · animation · density).
cần đào sâu (vd snippet drawer/inline-edit cụ thể, hay component shared), Solution cứ reply qua kênh email (`/check-email namgroup` để pull). 🚀
NAMGROUP (anh pqhuy chỉ đạo chia sẻ; màu sắc/brand để Solution tự quyết)