@agile-team/wl-skills-ui 1.13.1 → 1.13.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +7 -0
- package/README.md +4 -3
- package/docs/version-history.md +4 -0
- package/package.json +1 -1
- package/scanner/rules/componentStructure.mjs +7 -1
- package/scanner/rules/form.mjs +40 -1
- package/skills/element/el-form/SKILL.md +9 -6
- package/standards/rules.json +12 -0
- package/standards/ui/03-form.md +17 -0
package/CHANGELOG.md
CHANGED
|
@@ -6,6 +6,13 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/).
|
|
|
6
6
|
|
|
7
7
|
## [Unreleased]
|
|
8
8
|
|
|
9
|
+
## [1.13.2] - 2026-10-02
|
|
10
|
+
|
|
11
|
+
### Added
|
|
12
|
+
|
|
13
|
+
- R044 对多列表单静态 `label-width >= 240px` 及动态绑定中的宽字面量兜底值给出局部布局人工复核提示;R040 识别未登记的自定义 `stepper` 复合输入。均不自动改写业务页面。
|
|
14
|
+
- 表单规范与 Skill 增补单外壳文本步进控件、对称边距及宽/窄屏几何验收口径。
|
|
15
|
+
|
|
9
16
|
## [1.13.1] - 2026-09-30
|
|
10
17
|
|
|
11
18
|
### Fixed
|
package/README.md
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# @agile-team/wl-skills-ui
|
|
2
2
|
|
|
3
|
-
**企业级 UI 一致性与 AI 精确治理工具包 v1.13.
|
|
3
|
+
**企业级 UI 一致性与 AI 精确治理工具包 v1.13.2** — 面向 Vue 3 + Element Plus 的设计令牌、能力 Profile、样式皮肤、页面骨架、运行时能力、静态扫描、确定性修复、AI Skill、MCP 与脱敏 UI 模板契约。
|
|
4
4
|
|
|
5
5
|
它把“视觉统一、问题识别、机械修复、项目适配和样例沉淀”拆成可验证、可组合的工程能力。脚本、规则和 MCP 先完成确定性工作,AI 只处理业务语义与人工决策,从而减少重复读源码、上下文 token 和误修改。
|
|
6
6
|
|
|
@@ -13,7 +13,7 @@
|
|
|
13
13
|
| --- | --- | --- |
|
|
14
14
|
| 统一新项目视觉 | Design Tokens、Element Plus 原子样式、页面 Layout、Runtime Preset | 颜色、尺寸、间距、圆角、表格和业务状态从同一事实源产生 |
|
|
15
15
|
| 低成本治理老项目 | Skin 模式、Base*/jh-*/C_*/AG Grid 兼容层、定制页豁免 | 不改封装源码也能统一大部分视觉,避免一次性重构风险 |
|
|
16
|
-
| 阻止 UI 回归 |
|
|
16
|
+
| 阻止 UI 回归 | 40 条 R-rule、接入检查、漂移基线、Git 增量扫描、CI 门禁 | 表头/内容不共轴、按钮无图标、日期弹层全屏、密集表单失衡等问题在提交前暴露 |
|
|
17
17
|
| 安全机械修复 | Profile、only/skip、dry-run 计划哈希、快照、复检与回滚 | 自动化只处理可证明安全且已批准的动作,不让 AI 猜测批改 |
|
|
18
18
|
| 降低 AI token | summary、compact-v2 分页、changed-only、Skill 路由、13 个 MCP Tool | AI 先读总览和结构化事实,只在必要时获取有界明细或局部源码 |
|
|
19
19
|
| 沉淀领域样例 | `ui-contract` extract / validate / match | 页面转为脱敏语义 JSON,不复制整页代码、接口、字段值或原始文案 |
|
|
@@ -137,6 +137,7 @@ Vendor 覆盖顺序是:`Base* > jh-* > C_*/c_* > AG Grid > custom wrappers`。
|
|
|
137
137
|
- 普通按钮默认要求 `size="small"` 且带语义图标;已声明动态尺寸、link/text 或操作列图标按钮不会被误改。
|
|
138
138
|
- 表单输入、Select、Date/Time Picker 默认 small,日期时间输入根使用 `style="width:100%"`。
|
|
139
139
|
- 长标签布局按实际文本、字体和容器宽度确定:R008 对 `el-form`、`BaseForm`、`BaseQuery` 的静态 `labelWidth` / `label-width` 小于 150px 给出人工复核提示;150px 不是统一修复值。加宽标签时同步保证输入区至少 160px,必要时减少列数;不全局取消 jh/Base 标签省略。详见[表单规范](standards/ui/03-form.md)。
|
|
140
|
+
- 密集多列表单若静态标签宽度或动态绑定中的字面量兜底值达到 240px,R044 提醒人工核对左右留白与输入区宽度;仅在本表单调整标签预算和对称边距。自定义文本步进输入用单外壳边框与控件高度/步进区宽度 token,R040 可审查未登记的 `stepper` 复合结构。两类问题均不做危险的全局自动改写。详见[表单规范](standards/ui/03-form.md)。
|
|
140
141
|
- 原生 `el-date-picker` / `el-time-picker` 的面板通过 Teleport 渲染,面板同样带 `.el-date-picker` 类。包内 `_picker.scss`、R042 与浏览器契约共同阻止裸几何样式把弹层放大为全屏;输入宽度只作用于 `.el-date-editor` 或组件 style,弹层规则必须从 `.el-picker__popper` 限定。
|
|
141
142
|
|
|
142
143
|
```ts
|
|
@@ -473,7 +474,7 @@ npx wl-ui doctor --project . --print-overrides
|
|
|
473
474
|
|
|
474
475
|
## 版本与进一步阅读
|
|
475
476
|
|
|
476
|
-
当前 v1.13.1:R008 覆盖 jh/Base
|
|
477
|
+
当前 v1.13.2:R044 审查多列表单超宽静态标签和动态字面量兜底值,R040 增加自定义 `stepper` 复合结构识别;两者仅供人工复核,不自动改写项目样式。v1.13.1:R008 覆盖 jh/Base 表单静态标签宽度,并补充长标签与输入区的布局预算和浏览器验收口径。v1.13.0:新增 `native-jh-ag` 混合形态 Profile、显式 Profile 兼容承诺与联邦 AG 依赖识别。
|
|
477
478
|
|
|
478
479
|
- [版本摘要](docs/version-history.md)
|
|
479
480
|
- [完整 Changelog](CHANGELOG.md)
|
package/docs/version-history.md
CHANGED
|
@@ -2,6 +2,10 @@
|
|
|
2
2
|
|
|
3
3
|
本页保留面向使用者的版本能力摘要;逐提交级变更、修复细节和旧版本记录见根目录 [`CHANGELOG.md`](../CHANGELOG.md)。
|
|
4
4
|
|
|
5
|
+
## v1.13.2 — 密集表单与自定义步进输入
|
|
6
|
+
|
|
7
|
+
- R044 仅审查多列表单中静态标签宽度或动态字面量兜底值 `>= 240px` 的大留白风险;R040 增加 `stepper` 结构发现,修复均需按真实字段和 DOM 做局部验证,不批量覆盖全局样式。
|
|
8
|
+
|
|
5
9
|
## v1.13.1 — 长标签表单布局治理
|
|
6
10
|
|
|
7
11
|
- R008 扩展至 `BaseForm` / `BaseQuery` 的静态标签宽度写法,避免封装表单漏检;仍仅提示人工复核。
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@agile-team/wl-skills-ui",
|
|
3
|
-
"version": "1.13.
|
|
3
|
+
"version": "1.13.2",
|
|
4
4
|
"description": "企业级 UI 风格对齐框架 — Vue + Element Plus 项目通用化妆/原生双模式(tokens / element / vendors / layouts / runtime / scanner / fixer / skills)",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "./es/index.js",
|
|
@@ -25,13 +25,19 @@ export function findUnknownCompositeRoots(template) {
|
|
|
25
25
|
const isHybridElementWrapper =
|
|
26
26
|
classes.includes("el-input") && classes.includes("el-input__wrapper");
|
|
27
27
|
const looksComposite = COMPOSITE_NAME.test(classValue);
|
|
28
|
+
const looksStepper = /stepper/i.test(classValue);
|
|
28
29
|
const nearby = template.slice(match.index, match.index + 1600);
|
|
29
30
|
const containsInputStructure =
|
|
30
31
|
/<el-(?:input|select|autocomplete|cascader)\b|el-(?:input|select)__wrapper/.test(
|
|
31
32
|
nearby,
|
|
32
33
|
);
|
|
34
|
+
const containsStepButtons =
|
|
35
|
+
(nearby.match(/<(?:el-)?button\b/g) || []).length >= 2;
|
|
33
36
|
|
|
34
|
-
if (
|
|
37
|
+
if (
|
|
38
|
+
isHybridElementWrapper ||
|
|
39
|
+
((looksComposite || (looksStepper && containsStepButtons)) && containsInputStructure)
|
|
40
|
+
) {
|
|
35
41
|
findings.push({ index: match.index, classValue });
|
|
36
42
|
}
|
|
37
43
|
}
|
package/scanner/rules/form.mjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/** scanner/rules/form.mjs — 表单控件规则:R006 R007 R008 */
|
|
1
|
+
/** scanner/rules/form.mjs — 表单控件规则:R006 R007 R008 R042 R044 */
|
|
2
2
|
import { lineOf, issue, findTags } from "./_shared.mjs";
|
|
3
3
|
|
|
4
4
|
function isPickerPanelScoped(selector) {
|
|
@@ -149,4 +149,43 @@ export const formRules = [
|
|
|
149
149
|
return issues;
|
|
150
150
|
},
|
|
151
151
|
},
|
|
152
|
+
|
|
153
|
+
// R044: 多列表单的超宽静态标签或动态字面量兜底值会把首列输入推向右侧。
|
|
154
|
+
// 只做 review:标签文本、列宽和响应式断点都可能使宽标签成为必要配置。
|
|
155
|
+
{
|
|
156
|
+
id: "R044",
|
|
157
|
+
category: "form",
|
|
158
|
+
severity: "review",
|
|
159
|
+
name: "多列表单标签宽度过大(≥ 240px)",
|
|
160
|
+
check(template, file, lineOffset) {
|
|
161
|
+
const issues = [];
|
|
162
|
+
for (const tagName of ["el-form", "BaseForm", "base-form"]) {
|
|
163
|
+
for (const tag of findTags(template, tagName)) {
|
|
164
|
+
const widthAttribute = tag.text.match(
|
|
165
|
+
/(?:^|\s)(:)?(?:label-width|labelWidth)\s*=\s*(["'])([\s\S]*?)\2/,
|
|
166
|
+
);
|
|
167
|
+
if (!widthAttribute) continue;
|
|
168
|
+
const widths = widthAttribute[1]
|
|
169
|
+
? [...widthAttribute[3].matchAll(/(["'`])(\d+)px\1/g)].map((match) => Number(match[2]))
|
|
170
|
+
: [Number(/^(\d+)px$/.exec(widthAttribute[3].trim())?.[1])];
|
|
171
|
+
const wideWidth = widths.find((width) => width >= 240);
|
|
172
|
+
if (!wideWidth) continue;
|
|
173
|
+
const columns = tag.text.match(/(?:^|\s)(?::columns|columns)\s*=\s*["']([^"']+)["']/);
|
|
174
|
+
if (!columns || columns[1].trim() === "1") continue;
|
|
175
|
+
issues.push(
|
|
176
|
+
issue(
|
|
177
|
+
file,
|
|
178
|
+
lineOf(template, tag.index, lineOffset),
|
|
179
|
+
"R044",
|
|
180
|
+
"form",
|
|
181
|
+
"review",
|
|
182
|
+
`${tagName} 在多列布局中使用 ${wideWidth}px 标签宽度,可能造成首列大留白`,
|
|
183
|
+
"核对最长实际标签与输入区≥160px;仅在本表单缩窄标签并设置对称边距,宽/窄屏实测后再应用,不自动改写",
|
|
184
|
+
),
|
|
185
|
+
);
|
|
186
|
+
}
|
|
187
|
+
}
|
|
188
|
+
return issues;
|
|
189
|
+
},
|
|
190
|
+
},
|
|
152
191
|
];
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
|
+
name: el-form
|
|
2
3
|
description: |
|
|
3
|
-
|
|
4
|
-
覆盖规则:R006 R007 R008。
|
|
4
|
+
审查和修复 Vue/Element Plus 表单控件尺寸、标签预算与自定义步进输入的布局问题。
|
|
5
5
|
applyTo: "**/*.vue"
|
|
6
6
|
---
|
|
7
7
|
|
|
@@ -36,15 +36,18 @@ el-date-picker 默认宽度不会自动撑满 el-form-item,必须显式设置
|
|
|
36
36
|
|
|
37
37
|
## R008 — 表单静态标签宽度预警 【低危】
|
|
38
38
|
|
|
39
|
-
|
|
40
|
-
- <el-form :model="form" labelWidth="100px">
|
|
41
|
-
+ <el-form :model="form" labelWidth="150px">
|
|
42
|
-
```
|
|
39
|
+
`label-width="100px"` 等静态小宽度会触发人工检查;不要机械替换成固定 `150px`。
|
|
43
40
|
|
|
44
41
|
> 扫描覆盖 `el-form`、`BaseForm`、`BaseQuery` 的静态 `labelWidth` / `label-width`;150px 只是预警下限,不是所有表单的最终宽度。`jh-ui` 的 `.com-text` 可能强制单行省略,因此长标签(含单位、中英文混排)需按实际字体测量。
|
|
45
42
|
> 修复时先量最长标签,再同时检查列宽预算:每列至少容纳标签、间距和 160px 可输入区;不足时降低列数并设置响应式断点。只作用于受影响表单,不全局取消省略或强迫所有页面使用同一个宽度。tooltip 不能代替标签可见。该规则**仅提示人工确认**,不自动修改。
|
|
46
43
|
> 浏览器验收至少核对宽屏和窄屏:标签 `scrollWidth <= clientWidth`、输入区 ≥160px、相邻字段不重叠;若业务允许单列移动布局,可在更窄视口单独验收。
|
|
47
44
|
|
|
45
|
+
## R044 — 密集多列表单超宽固定标签 【人工复核】
|
|
46
|
+
|
|
47
|
+
静态 `label-width >= 240px`,或动态绑定中含同等宽度的字面量兜底值,且配置多列时,检查是否出现首列大留白、右侧贴边。无法静态判断的动态值不猜测。按实际最长标签缩窄**当前表单**标签宽度,并给卡片两侧同等内边距;不能把某个示例像素值批量写到所有页面。若长标签确实需要 240px 以上,保留并通过减列保障输入区。宽/窄屏几何验收同 R008,规则只提示不自动修复。
|
|
48
|
+
|
|
49
|
+
字母数字混合的炉号上下键属于复合文字输入,不能改成 `el-input-number`;外壳单独绘制唯一边框,按钮高度各半,统一使用 `--wk-form-control-height` 和 `--wk-form-number-controls-width`。自有根类包含 `stepper` 时 R040 会提醒登记结构契约。详见 `standards/ui/03-form.md`。
|
|
50
|
+
|
|
48
51
|
---
|
|
49
52
|
|
|
50
53
|
## 表单控件圆角一致性 【中危】
|
package/standards/rules.json
CHANGED
|
@@ -194,6 +194,18 @@
|
|
|
194
194
|
"scanner": "scanner/rules/form.mjs",
|
|
195
195
|
"skills": ["element/el-form"]
|
|
196
196
|
},
|
|
197
|
+
{
|
|
198
|
+
"id": "R044",
|
|
199
|
+
"category": "form",
|
|
200
|
+
"severity": "review",
|
|
201
|
+
"title": "多列表单标签宽度过大(≥ 240px)",
|
|
202
|
+
"rationale": "静态宽度或动态绑定中的宽字面量兜底值会在多列密集表单中制造首列大留白;需要结合真实标签文本、输入区和断点核对。",
|
|
203
|
+
"appliesTo": ["el-form", "BaseForm"],
|
|
204
|
+
"autoFixable": false,
|
|
205
|
+
"manualReason": "无法仅凭静态代码确定最长标签、真实列宽与响应式断点;必须局部实测,不可全局替换。",
|
|
206
|
+
"scanner": "scanner/rules/form.mjs",
|
|
207
|
+
"skills": ["element/el-form"]
|
|
208
|
+
},
|
|
197
209
|
{
|
|
198
210
|
"id": "R009",
|
|
199
211
|
"category": "tag",
|
package/standards/ui/03-form.md
CHANGED
|
@@ -11,6 +11,23 @@
|
|
|
11
11
|
<el-form :model="form" label-width="100px"></el-form>
|
|
12
12
|
```
|
|
13
13
|
|
|
14
|
+
## 规则 R044:密集多列表单的超宽标签预算
|
|
15
|
+
|
|
16
|
+
静态 `label-width >= 240px`,或动态绑定中包含 `240px` 以上的字面量兜底值,且声明多列时,扫描器只标记人工复核,**不自动改宽度**。无法静态判断的动态值不猜测。宽标签占据每列左侧,短标签右对齐后首列形成大面积空白;这与 R008 的“过窄截断”是同一预算的两端。
|
|
17
|
+
|
|
18
|
+
修复顺序:先量最长实际标签(含单位),再按每列 `标签宽 + 间距 + 输入区 ≥ 160px` 设局部宽度与响应式列数;卡片左右使用相同内边距。仅修改该表单容器,保留其他业务表单原布局。以宽屏、窄屏的真实 DOM 几何验收:标签不截断、左右外边距接近、输入区不小于 160px、字段无交叠;中文和英数混排均需检查。
|
|
19
|
+
|
|
20
|
+
```vue
|
|
21
|
+
<!-- 按真实字段测量后选择局部宽度,数字仅为示例 -->
|
|
22
|
+
<BaseForm :items="actualItems" :columns="responsiveColumns" label-width="184px" />
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
## 自定义“文本输入 + 上下步进”复合控件
|
|
26
|
+
|
|
27
|
+
炉号等字母数字混合字段不可换成纯数字输入。此类控件外壳负责**唯一**边框、圆角、hover/focus/error/disabled 状态;内部文本输入与两个按钮不得各画一层框。外壳高度用 `--wk-form-control-height`,按钮区宽度用 `--wk-form-number-controls-width`,上下各占半高并由一条水平线分隔,图标尺寸和颜色沿用数字输入步进区。保留按钮的 `type="button"`、可辨认名称、键盘焦点和禁用语义,不改变炉号进退算法。
|
|
28
|
+
|
|
29
|
+
项目自有复合控件根 class 建议包含 `stepper`,这样 R040 会将未登记结构纳入人工审查;明确边框所有者、高度策略及老/新版 Element DOM 后再登记结构契约。R040 不会自动套用全局 `.el-input-number` 样式到文字输入,也不自动修复,因为这会误伤组件状态和交互。
|
|
30
|
+
|
|
14
31
|
---
|
|
15
32
|
|
|
16
33
|
## 规则 R006:输入、选择、日期与时间控件必须加 size="small"
|