From c5a4a375081d3333cf8af7bfcd8ca6cf140272ad Mon Sep 17 00:00:00 2001 From: HIsheR Date: Mon, 26 Oct 2026 11:11:23 +0800 Subject: [PATCH] =?UTF-8?q?iter(g21):=20pagination=20=E8=B7=B3=E9=A1=B5?= =?UTF-8?q?=E8=BE=93=E5=85=A5=E6=A1=86?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .ua/backlog.json | 8 ++++++++ .ua/index.json | 4 ++-- apps/demo/main.ts | 2 +- llms-full.txt | 4 ++-- llms.txt | 2 +- packages/skin/ui/src/pagination.ts | 12 +++++++++++- packages/skin/ui/src/types.ts | 1 + packages/skin/ui/ua.manifest.json | 2 +- packages/skin/ui/ui.css | 21 +++++++++++++++++++++ 9 files changed, 48 insertions(+), 8 deletions(-) diff --git a/.ua/backlog.json b/.ua/backlog.json index 4225e34..6a3b2b6 100644 --- a/.ua/backlog.json +++ b/.ua/backlog.json @@ -524,6 +524,14 @@ "acceptance": "按住 −/+ 按钮 400ms 后每 100ms 连续步进,松开或移出即停;单击行为不变;npm run check 全绿", "status": "done", "notes": "自补:既有组件可用性细节" + }, + { + "id": "g21", + "title": "pagination 跳页输入框", + "motivation": "页数多时逐页点击太慢,主流分页器都提供直接跳页入口", + "acceptance": "jumpable 开启且总页数 > 1 时末尾显示页码输入 + 总页数,回车跳转并钳制合法范围;npm run check 全绿", + "status": "open", + "notes": "自补:既有组件可用性细节" } ] } diff --git a/.ua/index.json b/.ua/index.json index 951ad35..406b2b8 100644 --- a/.ua/index.json +++ b/.ua/index.json @@ -1,6 +1,6 @@ { "$schema": "ui-arch-registry-index/0.1", - "generatedAt": "2026-10-26T03:08:02.585Z", + "generatedAt": "2026-10-26T03:10:41.109Z", "repoRoot": ".", "packages": [ { @@ -164,7 +164,7 @@ "tooltip(props, trigger):悬浮提示,包裹触发器,hover / focus 延迟 150ms 出场,移出 / 失焦 / Esc 收起;视口一侧空间不足时自动翻转", "popover(props, trigger):可交互气泡卡片,包裹触发器,默认点击开合 + 点外部 / Esc 收起,content 可放按钮等交互元素;视口一侧空间不足时自动翻转", "skeleton(props):骨架屏占位,variant = text | rect | circle,text 支持 rows 多行,扫光微动画", - "pagination(props):独立分页器,page 信号双向绑定,页码过多折叠省略号,首末页禁用翻页,键盘可达", + "pagination(props):独立分页器,page 信号双向绑定,页码过多折叠省略号,首末页禁用翻页,jumpable 时末尾可输入页码直接跳转,键盘可达", "spinner(props):加载指示器,size 控制直径", "progress(props):进度条,value 信号驱动 0-100(满格切 success 色);不传 value 退化为不确定态无限往复", "tabs(props):标签页,active 信号双向绑定,滑动指示条 + 方向键环形导航,支持禁用页签", diff --git a/apps/demo/main.ts b/apps/demo/main.ts index f9d3fa1..c27309e 100644 --- a/apps/demo/main.ts +++ b/apps/demo/main.ts @@ -677,7 +677,7 @@ const content = h( pageSize: 3, page: tablePage, }), - pagination({ page: tablePage, pageSize: 3, total: users.length, onChange: (p) => tablePage(p) }), + pagination({ page: tablePage, pageSize: 3, total: users.length, jumpable: true, onChange: (p) => tablePage(p) }), ), ), section( diff --git a/llms-full.txt b/llms-full.txt index 0587475..e738845 100644 --- a/llms-full.txt +++ b/llms-full.txt @@ -1,6 +1,6 @@ # @ui-arch 组件库 Agent 文档(无图形版) -> 自动生成于 2026-10-26T03:08:02.585Z,数据源:各包 ua.manifest.json,勿手改。人类版文档站:apps/docs/index.html。 +> 自动生成于 2026-10-26T03:10:41.109Z,数据源:各包 ua.manifest.json,勿手改。人类版文档站:apps/docs/index.html。 > 组件 = 普通函数,传 props 返回 DOM;状态用 signal 双向绑定:读 signal() 写 signal(v)。 ## 快速上手 @@ -1029,7 +1029,7 @@ API 速览: - tooltip(props, trigger):悬浮提示,包裹触发器,hover / focus 延迟 150ms 出场,移出 / 失焦 / Esc 收起;视口一侧空间不足时自动翻转 - popover(props, trigger):可交互气泡卡片,包裹触发器,默认点击开合 + 点外部 / Esc 收起,content 可放按钮等交互元素;视口一侧空间不足时自动翻转 - skeleton(props):骨架屏占位,variant = text | rect | circle,text 支持 rows 多行,扫光微动画 -- pagination(props):独立分页器,page 信号双向绑定,页码过多折叠省略号,首末页禁用翻页,键盘可达 +- pagination(props):独立分页器,page 信号双向绑定,页码过多折叠省略号,首末页禁用翻页,jumpable 时末尾可输入页码直接跳转,键盘可达 - spinner(props):加载指示器,size 控制直径 - progress(props):进度条,value 信号驱动 0-100(满格切 success 色);不传 value 退化为不确定态无限往复 - tabs(props):标签页,active 信号双向绑定,滑动指示条 + 方向键环形导航,支持禁用页签 diff --git a/llms.txt b/llms.txt index 4bee5c0..943b54b 100644 --- a/llms.txt +++ b/llms.txt @@ -69,7 +69,7 @@ - tooltip(props, trigger):悬浮提示,包裹触发器,hover / focus 延迟 150ms 出场,移出 / 失焦 / Esc 收起;视口一侧空间不足时自动翻转 - popover(props, trigger):可交互气泡卡片,包裹触发器,默认点击开合 + 点外部 / Esc 收起,content 可放按钮等交互元素;视口一侧空间不足时自动翻转 - skeleton(props):骨架屏占位,variant = text | rect | circle,text 支持 rows 多行,扫光微动画 - - pagination(props):独立分页器,page 信号双向绑定,页码过多折叠省略号,首末页禁用翻页,键盘可达 + - pagination(props):独立分页器,page 信号双向绑定,页码过多折叠省略号,首末页禁用翻页,jumpable 时末尾可输入页码直接跳转,键盘可达 - spinner(props):加载指示器,size 控制直径 - progress(props):进度条,value 信号驱动 0-100(满格切 success 色);不传 value 退化为不确定态无限往复 - tabs(props):标签页,active 信号双向绑定,滑动指示条 + 方向键环形导航,支持禁用页签 diff --git a/packages/skin/ui/src/pagination.ts b/packages/skin/ui/src/pagination.ts index 418c7f0..0e40361 100644 --- a/packages/skin/ui/src/pagination.ts +++ b/packages/skin/ui/src/pagination.ts @@ -15,7 +15,7 @@ function pageSequence(page: number, totalPages: number): (number | null)[] { return seq; } -/*** 独立分页器:受控组件,page 为双向绑定信号;页码过多折叠省略号,首末页禁用翻页,原生 button 保证键盘可达 ***/ +/*** 独立分页器:受控组件,page 为双向绑定信号;页码过多折叠省略号,首末页禁用翻页,jumpable 时末尾可跳页,原生 button 保证键盘可达 ***/ export function pagination(props: PaginationProps): HTMLElement { const totalPages = Math.max(1, Math.ceil(props.total / props.pageSize)); // 总页数 const go = (p: number) => { @@ -23,6 +23,15 @@ export function pagination(props: PaginationProps): HTMLElement { props.page(next); props.onChange?.(next); }; + // —— 跳页输入:jumpable 且多页时渲染在末尾,回车跳转 —— + const jump = props.jumpable && totalPages > 1 ? (h('input', { class: 'ua-page-jump', inputmode: 'numeric', 'aria-label': `跳转到指定页,共 ${totalPages} 页` }) as HTMLInputElement) : null; + if (jump) { + jump.addEventListener('change', () => { + const n = parseInt(jump.value, 10); + jump.value = ''; // 跳转后清空输入,避免残留旧页码 + if (!Number.isNaN(n)) go(n); // 非数字忽略,由 go 钳制范围 + }); + } const nav = h('nav', { class: 'ua-pagination', 'aria-label': '分页' }); renderList(nav, () => { @@ -36,6 +45,7 @@ export function pagination(props: PaginationProps): HTMLElement { ); } items.push(h('button', { class: 'ua-page-btn', disabled: page >= totalPages, 'aria-label': '下一页', onClick: () => go(page + 1) }, '›')); + if (jump) items.push(h('span', { class: 'ua-page-jump-wrap' }, jump, h('span', { class: 'ua-page-total' }, `/ ${totalPages} 页`))); // 跳页入口固定在末尾 return items; }); return nav; diff --git a/packages/skin/ui/src/types.ts b/packages/skin/ui/src/types.ts index 3ecdc00..2966d93 100644 --- a/packages/skin/ui/src/types.ts +++ b/packages/skin/ui/src/types.ts @@ -278,6 +278,7 @@ export interface PaginationProps { page: Signal; // 当前页码信号,双向绑定(外部赋值自动翻页) pageSize: number; // 每页条数 total: number; // 总条数 + jumpable?: boolean; // 开启后在末尾显示跳页输入框(总页数 > 1 才出现) onChange?: (page: number) => void; // 翻页回调 } diff --git a/packages/skin/ui/ua.manifest.json b/packages/skin/ui/ua.manifest.json index 4c80c2d..a0d4ad3 100644 --- a/packages/skin/ui/ua.manifest.json +++ b/packages/skin/ui/ua.manifest.json @@ -35,7 +35,7 @@ "tooltip(props, trigger):悬浮提示,包裹触发器,hover / focus 延迟 150ms 出场,移出 / 失焦 / Esc 收起;视口一侧空间不足时自动翻转", "popover(props, trigger):可交互气泡卡片,包裹触发器,默认点击开合 + 点外部 / Esc 收起,content 可放按钮等交互元素;视口一侧空间不足时自动翻转", "skeleton(props):骨架屏占位,variant = text | rect | circle,text 支持 rows 多行,扫光微动画", - "pagination(props):独立分页器,page 信号双向绑定,页码过多折叠省略号,首末页禁用翻页,键盘可达", + "pagination(props):独立分页器,page 信号双向绑定,页码过多折叠省略号,首末页禁用翻页,jumpable 时末尾可输入页码直接跳转,键盘可达", "spinner(props):加载指示器,size 控制直径", "progress(props):进度条,value 信号驱动 0-100(满格切 success 色);不传 value 退化为不确定态无限往复", "tabs(props):标签页,active 信号双向绑定,滑动指示条 + 方向键环形导航,支持禁用页签", diff --git a/packages/skin/ui/ui.css b/packages/skin/ui/ui.css index f937eaa..ffd4d56 100644 --- a/packages/skin/ui/ui.css +++ b/packages/skin/ui/ui.css @@ -998,6 +998,27 @@ button.ua-step-dot:hover { align-items: center; gap: var(--ua-space-1); } +.ua-page-jump-wrap { + display: inline-flex; /* 跳页输入 + 总页数说明 */ + align-items: center; + gap: 4px; + margin-left: var(--ua-space-2); + color: var(--ua-color-text-muted); + font-size: var(--ua-font-size-sm); +} +.ua-page-jump { + width: 48px; + padding: 4px 6px; + border: 1px solid var(--ua-color-border); + border-radius: var(--ua-radius-sm); + background: var(--ua-color-bg); + color: var(--ua-color-text); + font-size: var(--ua-font-size-sm); + text-align: center; +} +.ua-page-total { + white-space: nowrap; +} .ua-page-btn { min-width: 28px; height: 28px;