@microi.net/cli 4.6.2 → 4.6.7
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/dist/mcp-server.js +101 -93
- package/dist/microi-cli.js +198 -47
- package/dist/microi-skills.meta.json +148 -142
- package/dist/microi.skills/.microi-skills-version.json +2 -2
- package/dist/microi.skills/README.md +3 -2
- package/dist/microi.skills/ai-engine/SKILL.md +38 -11
- package/dist/microi.skills/app-store/SKILL.md +134 -99
- package/dist/microi.skills/message-notification/agents/openai.yaml +0 -1
- package/dist/microi.skills/microi-ai-application/SKILL.md +8 -0
- package/dist/microi.skills/microi-client-frontend/SKILL.md +401 -394
- package/dist/microi.skills/microi-db-schema/SKILL.md +165 -164
- package/dist/microi.skills/microi-deployment/SKILL.md +29 -3
- package/dist/microi.skills/microi-docs-coverage/references/capability-map.md +4 -3
- package/dist/microi.skills/microi-docs-coverage/scripts/audit-doc-skill-coverage.mjs +10 -3
- package/dist/microi.skills/microi-form-engine/SKILL.md +165 -159
- package/dist/microi.skills/microi-system-delivery/SKILL.md +205 -196
- package/dist/microi.skills/microi-ui/SKILL.md +330 -321
- package/dist/microi.skills/microi.v8.js +1818 -1758
- package/dist/microi.skills/ocr-engine/SKILL.md +111 -0
- package/dist/microi.skills/ocr-engine/agents/openai.yaml +4 -0
- package/dist/microi.skills/page-engine/SKILL.md +2 -0
- package/dist/microi.skills/performance-testing/SKILL.md +2 -2
- package/dist/microi.skills/playwright-e2e/SKILL.md +14 -40
- package/dist/microi.skills/print-engine/SKILL.md +9 -3
- package/dist/microi.skills/report-engine/SKILL.md +1 -1
- package/dist/microi.skills/translate-engine/SKILL.md +47 -5
- package/dist/microi.skills/ui-design/SKILL.md +1596 -1575
- package/dist/microi.skills/ui-design/assets/templates/MCI-DESIGN.md +199 -98
- package/dist/microi.skills/ui-design/references/design-pattern-library.md +184 -171
- package/dist/microi.skills/ui-design/references/mci-design-contract.md +163 -84
- package/dist/microi.skills/v8-file-upload/SKILL.md +8 -0
- package/dist/microi.skills/v8-frontend-events/SKILL.md +4 -1
- package/dist/microi.skills/v8-frontend-events/references/bluetooth-print.md +28 -22
- package/dist/microi.skills/v8-http-integration/SKILL.md +22 -1
- package/dist/microi.skills/v8-saas-multi-tenant/SKILL.md +2 -1
- package/dist/microi.skills/v8-security/SKILL.md +7 -6
- package/dist/microi.skills/v8-utilities/references/server-api-index.md +1 -0
- package/dist/microi.skills/workspace-conventions/SKILL.md +22 -23
- package/package.json +1 -1
|
@@ -1,1575 +1,1596 @@
|
|
|
1
|
-
---
|
|
2
|
-
name: ui-design
|
|
3
|
-
description: Microi UI 设计系统指南。用于设计 PC Vue、Element Plus、uni-app H5、仪表盘、表单、卡片、渐变、响应式布局、骨架屏、移动安全区和视觉打磨。
|
|
4
|
-
---
|
|
5
|
-
|
|
6
|
-
# Microi吾码设计规范
|
|
7
|
-
|
|
8
|
-
你正在为 Microi 吾码平台创建界面。所有页面、组件、弹窗必须遵循本规范,打造高级、克制、具有科技感和品牌识别度的视觉体验。
|
|
9
|
-
|
|
10
|
-
> **适用平台**:PC 端(Vue 3 + Element Plus + SCSS)、移动端 H5/uni-app/原生 WebView(纯 CSS / 无第三方组件库)
|
|
11
|
-
> **核心理念**:高级但不浮夸,动效丰富但可维护,多端统一同时尊重平台差异
|
|
12
|
-
> **变量前缀**:所有 CSS 变量统一使用 `--mci-` 前缀(Microi Interface)
|
|
13
|
-
|
|
14
|
-
---
|
|
15
|
-
|
|
16
|
-
## 整体风格定义
|
|
17
|
-
|
|
18
|
-
- **风格关键词**:高级、通透、科技感、品牌化、轻量精致、视觉张力。
|
|
19
|
-
- **质感**:柔和多层阴影、清晰边界、结构化光影、细腻纹理、精致微动效。
|
|
20
|
-
- **氛围**:默认亮色多彩主题(colorful + gradient + soft shadow),暗黑主题作为可选切换;避免廉价装饰,优先用布局、层级、动效和真实内容建立高级感。
|
|
21
|
-
- **参考吸收**:可参考成熟移动端 UI 灵感库的组件完整度、色彩节奏、入场动效和模板化能力,但 Microi 视觉必须通过 `--mci-*` token 与 MCI-UI 组件形成自己的品牌系统,不照搬第三方外观,也不在吾码源码、文档或样式命名中保留外部 UI 品牌痕迹。
|
|
22
|
-
|
|
23
|
-
### Microi 设计模式选择(必须)
|
|
24
|
-
|
|
25
|
-
- 当需求只描述“高级、主流、好看”而没有明确视觉方向时,先从 Microi 内置模式中确定一种主结构:品牌叙事、真实产品流程、趋势构图、沉浸互动、动态首屏或数据工作台;再选择至多两种辅助能力。禁止把多套视觉语言堆成拼盘。
|
|
26
|
-
- 设计结果必须被拆成可执行规则:首屏目标、信息层级、栅格与最大宽度、字体层级、语义颜色、间距、圆角/阴影、组件状态、动效时间线、响应式重排、低性能降级和 `prefers-reduced-motion`。
|
|
27
|
-
- 先完成默认、加载、空、错误、成功、权限、禁用等真实业务状态,再增加装饰和动效;任何看起来可点击的元素都必须有真实结果。
|
|
28
|
-
- 所有成品只使用 Microi 自有内容、`--mci-*` token、`mci-*` 组件/类名和项目合法资产。禁止复制第三方页面、源码、图片、字体、3D 模型、商标或原始设计 token。
|
|
29
|
-
- 设计前必须读取 [references/design-pattern-library.md](references/design-pattern-library.md);涉及登录、订阅、支付、权限、搜索、设置等流程时再读 [references/product-flow-recipes.md](references/product-flow-recipes.md);涉及滚动、3D、Canvas/WebGL 或动态 Hero 时再读 [references/motion-and-media.md](references/motion-and-media.md);生成整站或交给 AI 延续设计时使用 [references/mci-design-contract.md](references/mci-design-contract.md)。
|
|
30
|
-
- 可运行原创案例位于 [assets/pattern-showcase/index.html](assets/pattern-showcase/index.html),用于理解结构和状态,不作为需要逐像素复制的模板。
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
-
|
|
37
|
-
-
|
|
38
|
-
-
|
|
39
|
-
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
-
|
|
48
|
-
-
|
|
49
|
-
-
|
|
50
|
-
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
-
|
|
57
|
-
-
|
|
58
|
-
-
|
|
59
|
-
-
|
|
60
|
-
-
|
|
61
|
-
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
-
|
|
70
|
-
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
```
|
|
105
|
-
|
|
106
|
-
-
|
|
107
|
-
-
|
|
108
|
-
|
|
109
|
-
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
:
|
|
121
|
-
|
|
122
|
-
--mci-
|
|
123
|
-
--mci-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
--mci-
|
|
144
|
-
--mci-
|
|
145
|
-
--mci-
|
|
146
|
-
--mci-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
--mci-
|
|
152
|
-
--mci-
|
|
153
|
-
--mci-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
--mci-
|
|
159
|
-
--mci-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
--mci-
|
|
164
|
-
--mci-
|
|
165
|
-
--mci-
|
|
166
|
-
--mci-
|
|
167
|
-
--mci-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
--mci-
|
|
176
|
-
--mci-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
--mci-color-
|
|
181
|
-
--mci-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
--mci-
|
|
185
|
-
|
|
186
|
-
--mci-
|
|
187
|
-
--mci-
|
|
188
|
-
--mci-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
--mci-
|
|
197
|
-
--mci-
|
|
198
|
-
--mci-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
--mci-
|
|
202
|
-
--mci-
|
|
203
|
-
--mci-
|
|
204
|
-
--mci-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
--mci-
|
|
208
|
-
--mci-
|
|
209
|
-
|
|
210
|
-
--mci-
|
|
211
|
-
|
|
212
|
-
--mci-
|
|
213
|
-
--mci-
|
|
214
|
-
--mci-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
-
|
|
225
|
-
-
|
|
226
|
-
|
|
227
|
-
-
|
|
228
|
-
-
|
|
229
|
-
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
-
|
|
251
|
-
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
:root {
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
--mci-
|
|
289
|
-
|
|
290
|
-
--mci-
|
|
291
|
-
|
|
292
|
-
--mci-
|
|
293
|
-
0 0
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
:
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
|
337
|
-
|
|
338
|
-
|
|
|
339
|
-
|
|
|
340
|
-
|
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
:
|
|
350
|
-
--mci-
|
|
351
|
-
--mci-
|
|
352
|
-
|
|
353
|
-
/*
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
|
|
382
|
-
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
|
|
417
|
-
|
|
418
|
-
|
|
419
|
-
-
|
|
420
|
-
-
|
|
421
|
-
-
|
|
422
|
-
|
|
423
|
-
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
```
|
|
428
|
-
:
|
|
429
|
-
|
|
430
|
-
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
|
|
435
|
-
|
|
436
|
-
|
|
437
|
-
|
|
438
|
-
|
|
439
|
-
|
|
440
|
-
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
```
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
-
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
|
|
455
|
-
-
|
|
456
|
-
|
|
457
|
-
|
|
458
|
-
|
|
459
|
-
|
|
460
|
-
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
|
|
464
|
-
-
|
|
465
|
-
-
|
|
466
|
-
-
|
|
467
|
-
-
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
|
|
471
|
-
|
|
472
|
-
|
|
473
|
-
|
|
474
|
-
|
|
475
|
-
|
|
476
|
-
|
|
477
|
-
|
|
478
|
-
|
|
479
|
-
|
|
480
|
-
|
|
481
|
-
|
|
482
|
-
|
|
483
|
-
|
|
484
|
-
|
|
485
|
-
|
|
486
|
-
|
|
487
|
-
|
|
488
|
-
|
|
489
|
-
|
|
490
|
-
|
|
491
|
-
|
|
492
|
-
|
|
493
|
-
|
|
494
|
-
|
|
495
|
-
|
|
496
|
-
|
|
497
|
-
|
|
498
|
-
|
|
499
|
-
|
|
500
|
-
|
|
501
|
-
|
|
502
|
-
|
|
503
|
-
|
|
504
|
-
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
|
|
508
|
-
|
|
509
|
-
|
|
510
|
-
|
|
511
|
-
|
|
512
|
-
|
|
513
|
-
|
|
514
|
-
|
|
515
|
-
|
|
516
|
-
|
|
517
|
-
|
|
518
|
-
|
|
519
|
-
|
|
520
|
-
|
|
521
|
-
|
|
522
|
-
|
|
523
|
-
|
|
524
|
-
|
|
525
|
-
|
|
526
|
-
|
|
527
|
-
|
|
528
|
-
|
|
529
|
-
|
|
530
|
-
|
|
531
|
-
|
|
532
|
-
|
|
533
|
-
|
|
534
|
-
|
|
535
|
-
|
|
536
|
-
|
|
537
|
-
|
|
538
|
-
|
|
539
|
-
|
|
540
|
-
|
|
541
|
-
|
|
542
|
-
|
|
543
|
-
|
|
544
|
-
|
|
545
|
-
|
|
546
|
-
|
|
547
|
-
|
|
548
|
-
|
|
549
|
-
|
|
550
|
-
|
|
551
|
-
|
|
552
|
-
|
|
553
|
-
|
|
554
|
-
|
|
555
|
-
|
|
556
|
-
|
|
557
|
-
|
|
558
|
-
|
|
559
|
-
|
|
560
|
-
|
|
561
|
-
|
|
562
|
-
|
|
563
|
-
|
|
564
|
-
|
|
565
|
-
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
}
|
|
570
|
-
|
|
571
|
-
|
|
572
|
-
|
|
573
|
-
|
|
574
|
-
|
|
575
|
-
|
|
576
|
-
|
|
577
|
-
|
|
578
|
-
|
|
579
|
-
|
|
580
|
-
|
|
581
|
-
|
|
582
|
-
|
|
583
|
-
|
|
584
|
-
|
|
585
|
-
|
|
586
|
-
|
|
587
|
-
|
|
588
|
-
|
|
589
|
-
|
|
590
|
-
|
|
591
|
-
|
|
592
|
-
|
|
593
|
-
|
|
594
|
-
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
|
|
598
|
-
|
|
599
|
-
|
|
600
|
-
|
|
601
|
-
|
|
602
|
-
|
|
603
|
-
|
|
604
|
-
|
|
605
|
-
|
|
606
|
-
|
|
607
|
-
|
|
608
|
-
|
|
609
|
-
|
|
610
|
-
|
|
611
|
-
|
|
612
|
-
|
|
613
|
-
|
|
614
|
-
|
|
615
|
-
|
|
616
|
-
|
|
617
|
-
|
|
618
|
-
|
|
619
|
-
|
|
620
|
-
|
|
621
|
-
|
|
622
|
-
|
|
623
|
-
|
|
624
|
-
|
|
625
|
-
|
|
626
|
-
|
|
627
|
-
|
|
628
|
-
|
|
629
|
-
|
|
630
|
-
|
|
631
|
-
|
|
632
|
-
|
|
633
|
-
|
|
634
|
-
|
|
635
|
-
|
|
636
|
-
|
|
637
|
-
|
|
638
|
-
|
|
639
|
-
|
|
640
|
-
|
|
641
|
-
|
|
642
|
-
|
|
643
|
-
|
|
644
|
-
|
|
645
|
-
|
|
646
|
-
|
|
647
|
-
|
|
648
|
-
|
|
649
|
-
|
|
650
|
-
|
|
651
|
-
|
|
652
|
-
|
|
653
|
-
|
|
654
|
-
|
|
655
|
-
|
|
656
|
-
|
|
657
|
-
|
|
658
|
-
|
|
659
|
-
|
|
660
|
-
|
|
661
|
-
|
|
662
|
-
|
|
663
|
-
|
|
664
|
-
|
|
665
|
-
|
|
666
|
-
|
|
667
|
-
|
|
668
|
-
|
|
669
|
-
|
|
670
|
-
|
|
671
|
-
|
|
672
|
-
|
|
673
|
-
|
|
674
|
-
|
|
675
|
-
|
|
676
|
-
|
|
677
|
-
|
|
678
|
-
|
|
679
|
-
|
|
680
|
-
|
|
681
|
-
|
|
682
|
-
|
|
683
|
-
|
|
684
|
-
|
|
685
|
-
|
|
686
|
-
|
|
687
|
-
|
|
688
|
-
}
|
|
689
|
-
|
|
690
|
-
|
|
691
|
-
|
|
692
|
-
|
|
693
|
-
|
|
694
|
-
|
|
695
|
-
|
|
696
|
-
|
|
697
|
-
|
|
698
|
-
|
|
699
|
-
|
|
700
|
-
.
|
|
701
|
-
|
|
702
|
-
|
|
703
|
-
|
|
704
|
-
|
|
705
|
-
|
|
706
|
-
|
|
707
|
-
|
|
708
|
-
|
|
709
|
-
|
|
710
|
-
|
|
711
|
-
|
|
712
|
-
|
|
713
|
-
|
|
714
|
-
|
|
715
|
-
|
|
716
|
-
|
|
717
|
-
|
|
718
|
-
|
|
719
|
-
|
|
720
|
-
|
|
721
|
-
|
|
722
|
-
|
|
723
|
-
|
|
724
|
-
|
|
725
|
-
|
|
726
|
-
|
|
727
|
-
|
|
728
|
-
|
|
729
|
-
|
|
730
|
-
|
|
731
|
-
|
|
732
|
-
|
|
733
|
-
|
|
734
|
-
|
|
735
|
-
|
|
736
|
-
|
|
737
|
-
|
|
738
|
-
|
|
739
|
-
|
|
740
|
-
|
|
741
|
-
|
|
742
|
-
|
|
743
|
-
|
|
744
|
-
|
|
745
|
-
|
|
746
|
-
|
|
747
|
-
|
|
748
|
-
|
|
749
|
-
box-shadow: var(--mci-shadow-
|
|
750
|
-
|
|
751
|
-
|
|
752
|
-
|
|
753
|
-
|
|
754
|
-
|
|
755
|
-
|
|
756
|
-
|
|
757
|
-
|
|
758
|
-
|
|
759
|
-
|
|
760
|
-
|
|
761
|
-
|
|
762
|
-
|
|
763
|
-
|
|
764
|
-
|
|
765
|
-
|
|
766
|
-
|
|
767
|
-
|
|
768
|
-
|
|
769
|
-
|
|
770
|
-
|
|
771
|
-
|
|
772
|
-
|
|
773
|
-
|
|
774
|
-
|
|
775
|
-
|
|
776
|
-
|
|
777
|
-
|
|
778
|
-
|
|
779
|
-
|
|
780
|
-
|
|
781
|
-
|
|
782
|
-
|
|
783
|
-
|
|
784
|
-
|
|
785
|
-
|
|
786
|
-
|
|
787
|
-
|
|
788
|
-
|
|
789
|
-
|
|
790
|
-
|
|
791
|
-
|
|
792
|
-
|
|
793
|
-
|
|
794
|
-
|
|
795
|
-
|
|
796
|
-
|
|
797
|
-
|
|
798
|
-
|
|
799
|
-
|
|
800
|
-
|
|
801
|
-
|
|
802
|
-
|
|
803
|
-
|
|
804
|
-
|
|
805
|
-
|
|
806
|
-
|
|
807
|
-
|
|
808
|
-
|
|
809
|
-
|
|
810
|
-
|
|
811
|
-
|
|
812
|
-
|
|
813
|
-
|
|
814
|
-
|
|
815
|
-
|
|
816
|
-
|
|
817
|
-
|
|
818
|
-
|
|
819
|
-
|
|
820
|
-
|
|
821
|
-
|
|
822
|
-
|
|
823
|
-
|
|
824
|
-
```
|
|
825
|
-
|
|
826
|
-
|
|
827
|
-
|
|
828
|
-
|
|
829
|
-
:
|
|
830
|
-
|
|
831
|
-
|
|
832
|
-
|
|
833
|
-
|
|
834
|
-
|
|
835
|
-
|
|
836
|
-
|
|
837
|
-
|
|
838
|
-
|
|
839
|
-
|
|
840
|
-
|
|
841
|
-
|
|
842
|
-
|
|
843
|
-
|
|
844
|
-
|
|
845
|
-
|
|
846
|
-
|
|
847
|
-
|
|
848
|
-
|
|
849
|
-
|
|
850
|
-
|
|
851
|
-
|
|
852
|
-
|
|
853
|
-
|
|
854
|
-
|
|
855
|
-
|
|
856
|
-
|
|
857
|
-
|
|
858
|
-
|
|
859
|
-
|
|
860
|
-
|
|
861
|
-
|
|
862
|
-
|
|
863
|
-
|
|
864
|
-
|
|
865
|
-
|
|
866
|
-
|
|
867
|
-
|
|
868
|
-
|
|
869
|
-
|
|
870
|
-
|
|
871
|
-
|
|
872
|
-
|
|
873
|
-
|
|
874
|
-
|
|
875
|
-
|
|
876
|
-
|
|
877
|
-
|
|
878
|
-
|
|
879
|
-
|
|
880
|
-
|
|
881
|
-
|
|
882
|
-
|
|
883
|
-
|
|
884
|
-
|
|
885
|
-
|
|
886
|
-
|
|
887
|
-
|
|
888
|
-
|
|
889
|
-
|
|
890
|
-
|
|
891
|
-
|
|
892
|
-
|
|
893
|
-
|
|
894
|
-
|
|
895
|
-
|
|
896
|
-
|
|
897
|
-
|
|
898
|
-
-
|
|
899
|
-
|
|
900
|
-
|
|
901
|
-
|
|
902
|
-
|
|
903
|
-
|
|
904
|
-
|
|
905
|
-
|
|
906
|
-
|
|
907
|
-
|
|
908
|
-
|
|
909
|
-
|
|
910
|
-
|
|
911
|
-
|
|
912
|
-
|
|
913
|
-
|
|
914
|
-
|
|
915
|
-
|
|
916
|
-
|
|
917
|
-
|
|
918
|
-
|
|
919
|
-
|
|
920
|
-
|
|
921
|
-
|
|
922
|
-
|
|
923
|
-
|
|
924
|
-
|
|
925
|
-
|
|
926
|
-
|
|
927
|
-
|
|
928
|
-
|
|
929
|
-
|
|
930
|
-
|
|
931
|
-
|
|
932
|
-
|
|
933
|
-
|
|
934
|
-
|
|
935
|
-
|
|
936
|
-
|
|
937
|
-
|
|
938
|
-
|
|
939
|
-
|
|
940
|
-
|
|
941
|
-
|
|
942
|
-
|
|
943
|
-
|
|
944
|
-
|
|
945
|
-
|
|
946
|
-
|
|
947
|
-
|
|
948
|
-
|
|
949
|
-
|
|
950
|
-
|
|
951
|
-
}
|
|
952
|
-
|
|
953
|
-
.
|
|
954
|
-
|
|
955
|
-
|
|
956
|
-
|
|
957
|
-
|
|
958
|
-
|
|
959
|
-
|
|
960
|
-
```
|
|
961
|
-
|
|
962
|
-
|
|
963
|
-
|
|
964
|
-
|
|
965
|
-
|
|
966
|
-
|
|
967
|
-
|
|
968
|
-
|
|
969
|
-
padding: var(--mci-
|
|
970
|
-
background: var(--mci-bg-
|
|
971
|
-
|
|
972
|
-
|
|
973
|
-
|
|
974
|
-
|
|
975
|
-
|
|
976
|
-
|
|
977
|
-
|
|
978
|
-
|
|
979
|
-
|
|
980
|
-
|
|
981
|
-
|
|
982
|
-
|
|
983
|
-
|
|
984
|
-
|
|
985
|
-
|
|
986
|
-
|
|
987
|
-
|
|
988
|
-
-
|
|
989
|
-
-
|
|
990
|
-
-
|
|
991
|
-
|
|
992
|
-
-
|
|
993
|
-
|
|
994
|
-
|
|
995
|
-
|
|
996
|
-
|
|
997
|
-
|
|
998
|
-
|
|
999
|
-
|
|
1000
|
-
|
|
1001
|
-
|
|
1002
|
-
|
|
1003
|
-
|
|
1004
|
-
|
|
1005
|
-
|
|
1006
|
-
|
|
1007
|
-
|
|
1008
|
-
|
|
1009
|
-
|
|
1010
|
-
|
|
1011
|
-
|
|
1012
|
-
|
|
1013
|
-
|
|
1014
|
-
|
|
1015
|
-
|
|
1016
|
-
|
|
1017
|
-
|
|
1018
|
-
|
|
1019
|
-
|
|
1020
|
-
|
|
1021
|
-
|
|
1022
|
-
|
|
1023
|
-
|
|
1024
|
-
|
|
1025
|
-
|
|
1026
|
-
|
|
1027
|
-
|
|
1028
|
-
|
|
1029
|
-
|
|
1030
|
-
|
|
1031
|
-
|
|
1032
|
-
|
|
1033
|
-
|
|
1034
|
-
|
|
1035
|
-
|
|
1036
|
-
|
|
1037
|
-
|
|
1038
|
-
|
|
1039
|
-
|
|
1040
|
-
|
|
1041
|
-
|
|
1042
|
-
|
|
1043
|
-
|
|
1044
|
-
|
|
1045
|
-
|
|
1046
|
-
|
|
1047
|
-
|
|
1048
|
-
|
|
1049
|
-
|
|
1050
|
-
|
|
1051
|
-
|
|
1052
|
-
|
|
1053
|
-
|
|
1054
|
-
|
|
1055
|
-
|
|
1056
|
-
|
|
1057
|
-
|
|
1058
|
-
|
|
1059
|
-
|
|
1060
|
-
|
|
1061
|
-
|
|
1062
|
-
}
|
|
1063
|
-
|
|
1064
|
-
|
|
1065
|
-
|
|
1066
|
-
|
|
1067
|
-
|
|
1068
|
-
|
|
1069
|
-
|
|
1070
|
-
|
|
1071
|
-
-
|
|
1072
|
-
-
|
|
1073
|
-
-
|
|
1074
|
-
|
|
1075
|
-
|
|
1076
|
-
|
|
1077
|
-
|
|
1078
|
-
-
|
|
1079
|
-
-
|
|
1080
|
-
-
|
|
1081
|
-
-
|
|
1082
|
-
-
|
|
1083
|
-
|
|
1084
|
-
|
|
1085
|
-
|
|
1086
|
-
|
|
1087
|
-
|
|
1088
|
-
|
|
1089
|
-
|
|
1090
|
-
|
|
1091
|
-
|
|
1092
|
-
|
|
1093
|
-
|
|
1094
|
-
|
|
1095
|
-
|
|
1096
|
-
|
|
1097
|
-
|
|
1098
|
-
|
|
1099
|
-
|
|
1100
|
-
|
|
1101
|
-
|
|
1102
|
-
|
|
1103
|
-
|
|
1104
|
-
|
|
1105
|
-
|
|
1106
|
-
|
|
1107
|
-
|
|
1108
|
-
|
|
1109
|
-
|
|
1110
|
-
|
|
1111
|
-
|
|
1112
|
-
|
|
1113
|
-
|
|
1114
|
-
|
|
1115
|
-
|
|
1116
|
-
|
|
1117
|
-
|
|
1118
|
-
|
|
1119
|
-
|
|
1120
|
-
|
|
1121
|
-
|
|
1122
|
-
|
|
1123
|
-
|
|
1124
|
-
|
|
1125
|
-
}
|
|
1126
|
-
|
|
1127
|
-
|
|
1128
|
-
|
|
1129
|
-
|
|
1130
|
-
|
|
1131
|
-
|
|
1132
|
-
|
|
1133
|
-
|
|
1134
|
-
|
|
1135
|
-
|
|
1136
|
-
|
|
1137
|
-
|
|
1138
|
-
|
|
1139
|
-
|
|
1140
|
-
|
|
1141
|
-
|
|
1142
|
-
|
|
1143
|
-
|
|
1144
|
-
|
|
1145
|
-
|
|
1146
|
-
|
|
1147
|
-
|
|
1148
|
-
|
|
1149
|
-
|
|
1150
|
-
|
|
1151
|
-
|
|
1152
|
-
|
|
1153
|
-
|
|
1154
|
-
|
|
1155
|
-
|
|
1156
|
-
|
|
1157
|
-
|
|
1158
|
-
|
|
1159
|
-
|
|
1160
|
-
|
|
1161
|
-
|
|
1162
|
-
|
|
1163
|
-
|
|
1164
|
-
|
|
1165
|
-
|
|
1166
|
-
|
|
1167
|
-
|
|
1168
|
-
|
|
1169
|
-
```
|
|
1170
|
-
|
|
1171
|
-
|
|
1172
|
-
|
|
1173
|
-
|
|
1174
|
-
|
|
1175
|
-
|
|
1176
|
-
|
|
1177
|
-
|
|
1178
|
-
|
|
1179
|
-
|
|
1180
|
-
|
|
1181
|
-
|
|
1182
|
-
|
|
1183
|
-
|
|
1184
|
-
|
|
1185
|
-
|
|
1186
|
-
|
|
1187
|
-
|
|
1188
|
-
|
|
1189
|
-
|
|
1190
|
-
|
|
1191
|
-
|
|
1192
|
-
|
|
1193
|
-
|
|
1194
|
-
|
|
1195
|
-
|
|
1196
|
-
|
|
1197
|
-
|
|
1198
|
-
|
|
1199
|
-
|
|
1200
|
-
|
|
1201
|
-
|
|
1202
|
-
|
|
1203
|
-
|
|
1204
|
-
|
|
1205
|
-
|
|
1206
|
-
|
|
1207
|
-
|
|
1208
|
-
|
|
1209
|
-
|
|
1210
|
-
|
|
1211
|
-
|
|
1212
|
-
|
|
1213
|
-
|
|
1214
|
-
|
|
1215
|
-
|
|
1216
|
-
|
|
1217
|
-
|
|
1218
|
-
|
|
1219
|
-
|
|
1220
|
-
|
|
1221
|
-
|
|
1222
|
-
|
|
1223
|
-
|
|
1224
|
-
|
|
1225
|
-
|
|
1226
|
-
|
|
1227
|
-
|
|
1228
|
-
|
|
1229
|
-
|
|
1230
|
-
|
|
1231
|
-
|
|
1232
|
-
|
|
1233
|
-
|
|
1234
|
-
|
|
1235
|
-
|
|
1236
|
-
|
|
1237
|
-
|
|
1238
|
-
|
|
1239
|
-
|
|
1240
|
-
|
|
1241
|
-
|
|
1242
|
-
|
|
1243
|
-
|
|
1244
|
-
|
|
1245
|
-
|
|
1246
|
-
|
|
1247
|
-
|
|
1248
|
-
```
|
|
1249
|
-
|
|
1250
|
-
|
|
1251
|
-
|
|
1252
|
-
|
|
1253
|
-
|
|
1254
|
-
|
|
1255
|
-
|
|
1256
|
-
|
|
1257
|
-
|
|
1258
|
-
|
|
1259
|
-
|
|
1260
|
-
|
|
1261
|
-
|
|
1262
|
-
|
|
1263
|
-
|
|
1264
|
-
|
|
1265
|
-
|
|
1266
|
-
|
|
1267
|
-
|
|
1268
|
-
|
|
1269
|
-
|
|
1270
|
-
|
|
1271
|
-
-
|
|
1272
|
-
|
|
1273
|
-
|
|
1274
|
-
|
|
1275
|
-
|
|
1276
|
-
|
|
1277
|
-
|
|
1278
|
-
|
|
1279
|
-
|
|
1280
|
-
|
|
1281
|
-
|
|
1282
|
-
|
|
1283
|
-
|
|
1284
|
-
|
|
1285
|
-
|
|
1286
|
-
|
|
1287
|
-
|
|
1288
|
-
|
|
1289
|
-
|
|
1290
|
-
|
|
1291
|
-
|
|
1292
|
-
|
|
1293
|
-
|
|
1294
|
-
|
|
1295
|
-
|
|
1296
|
-
|
|
1297
|
-
|
|
1298
|
-
|
|
1299
|
-
|
|
1300
|
-
|
|
1301
|
-
|
|
1302
|
-
|
|
1303
|
-
|
|
1304
|
-
|
|
1305
|
-
|
|
1306
|
-
<
|
|
1307
|
-
|
|
1308
|
-
|
|
1309
|
-
|
|
1310
|
-
|
|
1311
|
-
|
|
1312
|
-
|
|
1313
|
-
.
|
|
1314
|
-
|
|
1315
|
-
|
|
1316
|
-
|
|
1317
|
-
|
|
1318
|
-
|
|
1319
|
-
}
|
|
1320
|
-
|
|
1321
|
-
|
|
1322
|
-
|
|
1323
|
-
|
|
1324
|
-
|
|
1325
|
-
|
|
1326
|
-
|
|
1327
|
-
|
|
1328
|
-
|
|
1329
|
-
|
|
1330
|
-
|
|
1331
|
-
|
|
1332
|
-
|
|
1333
|
-
|
|
1334
|
-
|
|
1335
|
-
|
|
1336
|
-
-
|
|
1337
|
-
|
|
1338
|
-
-
|
|
1339
|
-
|
|
1340
|
-
|
|
1341
|
-
|
|
1342
|
-
-
|
|
1343
|
-
-
|
|
1344
|
-
|
|
1345
|
-
|
|
1346
|
-
|
|
1347
|
-
|
|
1348
|
-
|
|
1349
|
-
|
|
1350
|
-
|
|
1351
|
-
|
|
1352
|
-
|
|
1353
|
-
|
|
1354
|
-
|
|
1355
|
-
###
|
|
1356
|
-
|
|
1357
|
-
-
|
|
1358
|
-
-
|
|
1359
|
-
-
|
|
1360
|
-
|
|
1361
|
-
###
|
|
1362
|
-
|
|
1363
|
-
|
|
1364
|
-
|
|
1365
|
-
|
|
1366
|
-
|
|
1367
|
-
|
|
1368
|
-
|
|
1369
|
-
|
|
1370
|
-
|
|
1371
|
-
|
|
1372
|
-
|
|
1373
|
-
|
|
1374
|
-
|
|
1375
|
-
|
|
1376
|
-
|
|
1377
|
-
|
|
1378
|
-
|
|
1379
|
-
|
|
1380
|
-
|
|
1381
|
-
|
|
1382
|
-
|
|
1383
|
-
|
|
1384
|
-
|
|
1385
|
-
|
|
1386
|
-
|
|
1387
|
-
|
|
1388
|
-
|
|
1389
|
-
-
|
|
1390
|
-
|
|
1391
|
-
|
|
1392
|
-
-
|
|
1393
|
-
|
|
1394
|
-
|
|
1395
|
-
|
|
1396
|
-
|
|
1397
|
-
|
|
1398
|
-
|
|
1399
|
-
|
|
1400
|
-
```
|
|
1401
|
-
|
|
1402
|
-
|
|
1403
|
-
|
|
1404
|
-
|
|
1405
|
-
|
|
1406
|
-
|
|
1407
|
-
|
|
1408
|
-
|
|
1409
|
-
|
|
1410
|
-
|
|
1411
|
-
|
|
1412
|
-
-
|
|
1413
|
-
-
|
|
1414
|
-
|
|
1415
|
-
|
|
1416
|
-
|
|
1417
|
-
|
|
1418
|
-
|
|
1419
|
-
|
|
1420
|
-
|
|
1421
|
-
|
|
1422
|
-
|
|
1423
|
-
|
|
1424
|
-
|
|
1425
|
-
|
|
1426
|
-
|
|
1427
|
-
|
|
1428
|
-
|
|
1429
|
-
|
|
1430
|
-
|
|
1431
|
-
|
|
1432
|
-
|
|
1433
|
-
|
|
1434
|
-
|
|
1435
|
-
|
|
1436
|
-
|
|
1437
|
-
|
|
1438
|
-
|
|
1439
|
-
|
|
1440
|
-
|
|
1441
|
-
|
|
1442
|
-
|
|
1443
|
-
|
|
1444
|
-
|
|
1445
|
-
|
|
1446
|
-
|
|
1447
|
-
|
|
1448
|
-
|
|
1449
|
-
|
|
1450
|
-
|
|
1451
|
-
|
|
1452
|
-
|
|
1453
|
-
|
|
1454
|
-
|
|
1455
|
-
|
|
1456
|
-
|
|
1457
|
-
|
|
1458
|
-
|
|
1459
|
-
|
|
1460
|
-
|
|
1461
|
-
|
|
1462
|
-
|
|
1463
|
-
|
|
1464
|
-
|
|
1465
|
-
|
|
1466
|
-
|
|
1467
|
-
|
|
1468
|
-
|
|
1469
|
-
|
|
1470
|
-
|
|
1471
|
-
|
|
1472
|
-
|
|
1473
|
-
|
|
1474
|
-
|
|
1475
|
-
|
|
1476
|
-
|
|
1477
|
-
|
|
1478
|
-
|
|
1479
|
-
|
|
1480
|
-
|
|
1481
|
-
|
|
1482
|
-
|
|
1483
|
-
|
|
1484
|
-
|
|
1485
|
-
###
|
|
1486
|
-
|
|
1487
|
-
|
|
1488
|
-
|
|
1489
|
-
|
|
1490
|
-
|
|
1491
|
-
|
|
1492
|
-
|
|
1493
|
-
|
|
1494
|
-
|
|
1495
|
-
|
|
1496
|
-
|
|
1497
|
-
|
|
1498
|
-
|
|
1499
|
-
|
|
1500
|
-
|
|
1501
|
-
|
|
1502
|
-
|
|
1503
|
-
|
|
1504
|
-
|
|
1505
|
-
|
|
1506
|
-
|
|
1507
|
-
|
|
1508
|
-
|
|
1509
|
-
|
|
1510
|
-
|
|
1511
|
-
|
|
1512
|
-
|
|
1513
|
-
|
|
1514
|
-
|
|
1515
|
-
|
|
1516
|
-
|
|
1517
|
-
|
|
1518
|
-
|
|
1519
|
-
|
|
1520
|
-
|
|
1521
|
-
|
|
1522
|
-
|
|
1523
|
-
|
|
1524
|
-
|
|
1525
|
-
|
|
1526
|
-
|
|
1527
|
-
|
|
1528
|
-
|
|
1529
|
-
|
|
1530
|
-
|
|
1531
|
-
|
|
1532
|
-
|
|
1533
|
-
|
|
1534
|
-
|
|
1535
|
-
|
|
1536
|
-
|
|
1537
|
-
|
|
1538
|
-
|
|
1539
|
-
|
|
1540
|
-
|
|
1541
|
-
|
|
1542
|
-
|
|
1543
|
-
|
|
1544
|
-
|
|
1545
|
-
|
|
1546
|
-
|
|
1547
|
-
|
|
1548
|
-
|
|
1549
|
-
|
|
1550
|
-
|
|
1551
|
-
|
|
1552
|
-
|
|
1553
|
-
|
|
1554
|
-
|
|
1555
|
-
|
|
1556
|
-
|
|
1557
|
-
|
|
1558
|
-
|
|
1559
|
-
|
|
1560
|
-
|
|
1561
|
-
|
|
1562
|
-
|
|
1563
|
-
|
|
1564
|
-
|
|
1565
|
-
|
|
1566
|
-
|
|
1567
|
-
|
|
1568
|
-
|
|
1569
|
-
|
|
1570
|
-
|
|
1571
|
-
|
|
1572
|
-
-
|
|
1573
|
-
|
|
1574
|
-
-
|
|
1575
|
-
|
|
1
|
+
---
|
|
2
|
+
name: ui-design
|
|
3
|
+
description: Microi UI 设计系统指南。用于设计 PC Vue、Element Plus、uni-app H5、仪表盘、表单、卡片、渐变、响应式布局、骨架屏、移动安全区和视觉打磨。
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# Microi吾码设计规范
|
|
7
|
+
|
|
8
|
+
你正在为 Microi 吾码平台创建界面。所有页面、组件、弹窗必须遵循本规范,打造高级、克制、具有科技感和品牌识别度的视觉体验。
|
|
9
|
+
|
|
10
|
+
> **适用平台**:PC 端(Vue 3 + Element Plus + SCSS)、移动端 H5/uni-app/原生 WebView(纯 CSS / 无第三方组件库)
|
|
11
|
+
> **核心理念**:高级但不浮夸,动效丰富但可维护,多端统一同时尊重平台差异
|
|
12
|
+
> **变量前缀**:所有 CSS 变量统一使用 `--mci-` 前缀(Microi Interface)
|
|
13
|
+
|
|
14
|
+
---
|
|
15
|
+
|
|
16
|
+
## 整体风格定义
|
|
17
|
+
|
|
18
|
+
- **风格关键词**:高级、通透、科技感、品牌化、轻量精致、视觉张力。
|
|
19
|
+
- **质感**:柔和多层阴影、清晰边界、结构化光影、细腻纹理、精致微动效。
|
|
20
|
+
- **氛围**:默认亮色多彩主题(colorful + gradient + soft shadow),暗黑主题作为可选切换;避免廉价装饰,优先用布局、层级、动效和真实内容建立高级感。
|
|
21
|
+
- **参考吸收**:可参考成熟移动端 UI 灵感库的组件完整度、色彩节奏、入场动效和模板化能力,但 Microi 视觉必须通过 `--mci-*` token 与 MCI-UI 组件形成自己的品牌系统,不照搬第三方外观,也不在吾码源码、文档或样式命名中保留外部 UI 品牌痕迹。
|
|
22
|
+
|
|
23
|
+
### Microi 设计模式选择(必须)
|
|
24
|
+
|
|
25
|
+
- 当需求只描述“高级、主流、好看”而没有明确视觉方向时,先从 Microi 内置模式中确定一种主结构:品牌叙事、真实产品流程、趋势构图、沉浸互动、动态首屏或数据工作台;再选择至多两种辅助能力。禁止把多套视觉语言堆成拼盘。
|
|
26
|
+
- 设计结果必须被拆成可执行规则:首屏目标、信息层级、栅格与最大宽度、字体层级、语义颜色、间距、圆角/阴影、组件状态、动效时间线、响应式重排、低性能降级和 `prefers-reduced-motion`。
|
|
27
|
+
- 先完成默认、加载、空、错误、成功、权限、禁用等真实业务状态,再增加装饰和动效;任何看起来可点击的元素都必须有真实结果。
|
|
28
|
+
- 所有成品只使用 Microi 自有内容、`--mci-*` token、`mci-*` 组件/类名和项目合法资产。禁止复制第三方页面、源码、图片、字体、3D 模型、商标或原始设计 token。
|
|
29
|
+
- 设计前必须读取 [references/design-pattern-library.md](references/design-pattern-library.md);涉及登录、订阅、支付、权限、搜索、设置等流程时再读 [references/product-flow-recipes.md](references/product-flow-recipes.md);涉及滚动、3D、Canvas/WebGL 或动态 Hero 时再读 [references/motion-and-media.md](references/motion-and-media.md);生成整站或交给 AI 延续设计时使用 [references/mci-design-contract.md](references/mci-design-contract.md)。
|
|
30
|
+
- 可运行原创案例位于 [assets/pattern-showcase/index.html](assets/pattern-showcase/index.html),用于理解结构和状态,不作为需要逐像素复制的模板。
|
|
31
|
+
|
|
32
|
+
### 可执行设计契约(整站与长期项目强制)
|
|
33
|
+
|
|
34
|
+
- `MCI-DESIGN.md` 必须同时维护机器可读层和人类可读层:前者保存精确 token、引用和组件状态,后者保存目标用户、情绪、具体视觉隐喻、选择理由和禁区。只有 token 会失去取舍依据,只有形容词无法稳定实现。
|
|
35
|
+
- 设计意图按“用户任务 → 主情绪 → 具体视觉隐喻 → 应当/禁止 → token 与组件”收敛。具体隐喻必须能自然约束色彩、材质、密度、形状和动效;禁止只堆“高级、现代、极简、科技”等宽泛词。
|
|
36
|
+
- 核心章节固定为:产品与用户、视觉性格、颜色、字体、布局与间距、层级与形状、组件与状态、页面模式、动效与媒体、响应式、安全与降级、应当与禁止。扩展章节放在末尾,未知扩展要保留,核心章节不得重复或用近似拼写另起一套。
|
|
37
|
+
- token 使用语义命名并允许组件以 `{路径}` 复用;必须检查缺失/循环引用、错误类型、主色缺失、透明色叠加底、对比度、孤立 token、未覆盖状态和无理由省略。组件至少按适用场景定义 default/hover/focus/pressed/loading/empty/error/disabled/selected/success。
|
|
38
|
+
- 契约与实现必须一起评审差异;意外删除、重命名、大范围 token 漂移或只改契约不改页面都视为未完成。运行时变量或其它主题格式只能从已校验的机器块派生,禁止维护第二份手工 token。
|
|
39
|
+
- 契约格式必须锁定版本,升级时先检查语义差异再迁移;跨平台校验脚本提供稳定入口。完整结构、示例与验收见 [references/mci-design-contract.md](references/mci-design-contract.md),新项目复制 [assets/templates/MCI-DESIGN.md](assets/templates/MCI-DESIGN.md)。
|
|
40
|
+
|
|
41
|
+
---
|
|
42
|
+
|
|
43
|
+
## 样式隔离与抗覆盖
|
|
44
|
+
|
|
45
|
+
- Microi.UI 页面或局部 UI 必须使用 `.mci-page`、`data-mci-ui-root` 或项目级 `.mci-*` 根容器包裹,避免被宿主项目、第三方组件库、Markdown 渲染器的全局 CSS 意外覆盖。
|
|
46
|
+
- 所有可复用组件必须使用 `mci-` 前缀和 BEM 风格类名;不要写全局 `button`、`input`、`img`、`table`、`div` 选择器。确实需要 reset 时必须限制在 `.mci-page` 或 `[data-mci-ui-root]` 内。
|
|
47
|
+
- 业务页面不得用高优先级全局选择器覆盖 MCI 组件,例如 `.card *`、`button {}`、`img {}`、`.page .mci-card {}`。需要定制时用组件 props、CSS 变量或项目级 wrapper。
|
|
48
|
+
- 第三方 UI 组件必须放在项目 wrapper 内,例如 `.mci-third-party-scope`,颜色、圆角、阴影、间距映射到 `--mci-*` token,而不是直接把第三方默认主题暴露到页面。
|
|
49
|
+
- Web 项目优先用 Vue `scoped` / CSS Modules / 明确命名空间;uni-app 项目优先用页面级 `mci-*` 根类和组件根类。新增全局样式前必须检查是否会影响其它项目页面。
|
|
50
|
+
- 文档站、官网、企业站这类 Markdown/VitePress 项目,应在主题层统一收口视觉,不要在每一篇文档里写互相竞争的散装 CSS。
|
|
51
|
+
|
|
52
|
+
---
|
|
53
|
+
|
|
54
|
+
## 高端视觉标准
|
|
55
|
+
|
|
56
|
+
- 每个新页面必须有首屏视觉重心:核心数据、主任务、产品/品牌对象或可操作内容应在第一屏明确出现,不能只有说明文字或空白装饰。
|
|
57
|
+
- 页面进入必须有轻量入场动效,默认使用 `mci-page-enter` / `mci-fade-up`;列表、商品、指标卡使用 30-60ms 交错延迟,不能整页同时僵硬出现。
|
|
58
|
+
- 页面停留时允许微弱的停留动效:扫光、细线流动、图标轻浮动、状态光标闪烁等;振幅必须小,且只用 `transform` / `opacity` / `background-position`。
|
|
59
|
+
- 所有可点击元素必须有三态反馈:默认、hover/focus、active/pressed;PC 使用 hover lift,移动端使用按压缩放或背景反馈。
|
|
60
|
+
- 扁平风格也要有层次:减少圆角不等于没有阴影,必须保留细边框、柔和投影、hover 伪元素阴影和清晰分组。
|
|
61
|
+
- 背景装饰优先使用结构化方案:网格、细线、扫描高光、低透明纹理、内容相关图片或 3D 场景;不要使用离散光球、散点噪声、模糊色块堆叠作为主要视觉。
|
|
62
|
+
- 导航栏必须和首屏背景属于同一视觉语境:深色英雄区使用深色玻璃或透明暗底导航,浅色内容页才使用浅色导航;导航文字、Logo、搜索框和下拉入口必须截图检查对比度。
|
|
63
|
+
- 主按钮/胶囊按钮必须使用 `inline-flex` 或等价布局垂直居中,明确 `align-items:center`、`justify-content:center`、稳定高度和 `line-height:1`;不能只靠 padding 让文字“看起来差不多”。
|
|
64
|
+
- 按钮、标签、Tab、空态行动按钮、登录/授权入口等只要文字语义是居中呈现,就必须同时做到上下居中和左右居中;截图或视觉断言发现文字偏上、偏下、偏左、偏右都算未完成。
|
|
65
|
+
- 所有弹窗/对话框默认必须上下左右居中;PC 端应支持通过标题栏拖动,拖动后仍保持在可视区域内;移动端如改为底部抽屉或全屏弹层必须有明确业务理由。弹窗不得贴在左上角、底部或被遮罩/导航/输入框遮挡,截图验收必须覆盖默认居中态和至少一次拖动后的可用状态。
|
|
66
|
+
- 禁止在任何交付界面中直接调用浏览器原生 `window.alert`、`window.confirm`、`window.prompt` 或其无前缀别名。简单提示优先使用吾码平台 `Tips`/`DiyCommon.Tips`,确认操作使用 `V8.ConfirmTips`、Element Plus `ElMessageBox`,独立微服务则使用符合本规范的可访问确认弹层;原生浏览器对话框会阻塞线程、无法主题化,也无法满足吾码视觉与自动化标准。
|
|
67
|
+
- Toast、错误反馈、提交结果和二次确认必须脱离业务滚动容器:优先 teleport/append 到 `body`,使用 `position:fixed`、明确遮罩和高于宿主弹窗的层级,并在当前可视区域上下左右居中。用户把长弹窗滚到任意位置后仍必须立刻看到完整提示;禁止把反馈放在内容顶部、滚动层内部或仅靠 `top: 0` 伪装固定。
|
|
68
|
+
- 确认框必须说明“即将执行什么、作用范围、当前任务状态、确认与取消动作”。只有真实检测到正在执行/排队任务时才能写“已有任务”;没有检测到时应明确“提交后新建任务”,并把并发到来时的排队策略作为条件说明,不能用固定模板误导用户。
|
|
69
|
+
- 同一类 UI 在两个及以上页面出现时,必须优先封装为 `Mci*` 或项目级 `mci-*` 组件,通过 props/slots/events 配置标题、说明、图标、按钮、路由、状态和少量变体;不要复制两份卡片、空态、登录提示、按钮组、筛选栏或底部操作栏。
|
|
70
|
+
- 卡片背景必须服务页面氛围:暗色科技背景上的展示卡、价格卡、聊天卡不应突然变成大面积灰白卡;浅色卡片只在整体页面转为浅色内容区时使用,并且要有过渡带或区块背景承接。
|
|
71
|
+
|
|
72
|
+
---
|
|
73
|
+
|
|
74
|
+
## PC 后台菜单宫格 / 入口页规范
|
|
75
|
+
|
|
76
|
+
适用于 `sys_menu` 子菜单入口、工作台快捷入口、后台功能入口页。此类页面是操作入口,不是营销卡片墙,重点是密度克制、对齐稳定、快速识别。
|
|
77
|
+
|
|
78
|
+
- 宽屏不能无上限铺满一整行。1366-1920 宽度下推荐 6-8 个入口/行;超宽屏也不要因为 `repeat(auto-fill, minmax(..., 1fr))` 自动挤出 10 个以上入口。应使用固定/上限列宽、`max-width`、`justify-content:start` 控制节奏。
|
|
79
|
+
- 同一宫格内所有入口卡片必须宽高一致,优先使用固定 `width/height` 或 `aspect-ratio + max-width`。禁止让卡片随标题长度、是否有统计信息而高度不一致。
|
|
80
|
+
- 卡片内部必须建立固定槽位:图标区、标题区、辅助信息区。每张卡的图标、标题首行、统计胶囊应在同一水平线上;有无辅助信息都要通过固定 body 高度或预留槽位保持对齐。
|
|
81
|
+
- 标题与子菜单统计/辅助胶囊的间距控制在 4-6px,不能贴底,也不能和标题隔得很远。统计胶囊应跟随标题成为一个信息组。
|
|
82
|
+
- PC 卡片内边距不小于 14-18px,图标背景到卡片边缘不小于 16px;移动端内边距不小于 12px。不能出现图标、文字、统计贴边的效果。
|
|
83
|
+
- 标题最多两行并截断或自然换行,长词必须 `overflow-wrap:anywhere`,不允许撑破卡片。图标按钮、标题、统计文本都要垂直和水平对齐。
|
|
84
|
+
- 修改后必须截图验收 1366/1440/1920 桌面宽度和 390 左右移动宽度,检查每行数量、行列对齐、卡片内边距、标题与统计间距、文字溢出和横向滚动。
|
|
85
|
+
|
|
86
|
+
## PC 后台数据卡片模式规范
|
|
87
|
+
|
|
88
|
+
适用于 `diy-table` 卡片模式、任务/应用/客户/资产列表。它是高频数据操作容器,不是营销海报或入口宫格。
|
|
89
|
+
|
|
90
|
+
- 信息顺序固定为“真实图片或紧凑身份标记 → 标题与状态 → 2—4 个关键字段 → 时间/辅助标签 → 操作区”。标题与状态在首屏可扫读,次要字段不能抢占标题层级。
|
|
91
|
+
- 配置了图片但某行无图时,用 40—44px 首字或业务图标承接身份;禁止生成大面积渐变、发光字母、旋转方块等伪图片占据内容高度。真实图片按稳定比例使用 `cover/contain`。
|
|
92
|
+
- 无显式配置时桌面默认四列,以最小可读宽度优先;显式 `TableCardCol` 配置必须保留。中等宽度降为三列/两列,移动端单列,禁止为“同屏更多”把标题和四个操作挤进过窄卡片。
|
|
93
|
+
- 卡片依靠表面、细边框、轻阴影和 1—2px hover lift 建立层级;不要给每张卡加顶部霓虹线、径向光斑、彩虹渐变或重投影。选中态只改边框/焦点环,不能导致网格跳动。
|
|
94
|
+
- 操作区优先一个主动作、一至两个次动作,其余进入“更多”;危险动作不得与主动作同权。按钮使用 8—10px 软圆角而非满屏胶囊,移动端高度不小于 44px。
|
|
95
|
+
- 整卡可打开详情时提供可见 `focus-visible`、Enter/Space 触发;内部按钮和选择控件阻止冒泡。骨架屏要复刻图片(如有)、标题、字段和按钮的最终几何,不能先显示大图骨架再塌缩为空白。
|
|
96
|
+
- 视觉验收至少覆盖:无图/有图、长标题、多个按钮、选中态、加载/空态、亮/暗主题、1366/1440/1920 桌面与 390 移动。
|
|
97
|
+
|
|
98
|
+
---
|
|
99
|
+
|
|
100
|
+
## 形态模式(圆角 / 扁平)
|
|
101
|
+
|
|
102
|
+
Microi 项目必须支持用户或项目级形态偏好:`data-mci-shape="rounded"` 与 `data-mci-shape="flat"`。
|
|
103
|
+
|
|
104
|
+
```css
|
|
105
|
+
:root {
|
|
106
|
+
--mci-shape-card: var(--mci-radius-xl);
|
|
107
|
+
--mci-shape-panel: var(--mci-radius-lg);
|
|
108
|
+
--mci-shape-button: var(--mci-radius-pill);
|
|
109
|
+
--mci-shape-input: var(--mci-radius-md);
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
:root[data-mci-shape="rounded"] {
|
|
113
|
+
--mci-shape-card: 20px;
|
|
114
|
+
--mci-shape-panel: 16px;
|
|
115
|
+
--mci-shape-button: 999px;
|
|
116
|
+
--mci-shape-input: 12px;
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
:root[data-mci-shape="flat"] {
|
|
120
|
+
--mci-shape-card: 6px;
|
|
121
|
+
--mci-shape-panel: 4px;
|
|
122
|
+
--mci-shape-button: 4px;
|
|
123
|
+
--mci-shape-input: 4px;
|
|
124
|
+
}
|
|
125
|
+
```
|
|
126
|
+
|
|
127
|
+
- 圆角风格适合移动端商城、会员中心、消费类应用、品牌展示页。
|
|
128
|
+
- 扁平风格适合 B 端官网、数据看板、工具型 Web、强调效率的页面。
|
|
129
|
+
- 所有组件只引用 `--mci-shape-*`,不要在业务页面硬编码一堆 `border-radius`。
|
|
130
|
+
- 切换形态时只改变圆角 token,不改变布局尺寸,避免切换主题时页面跳动。
|
|
131
|
+
|
|
132
|
+
---
|
|
133
|
+
|
|
134
|
+
## 颜色体系(CSS Variables — 支持主题切换)
|
|
135
|
+
|
|
136
|
+
所有颜色必须通过 CSS 变量引用,禁止硬编码色值。变量定义放在全局样式入口(PC 端 `src/styles/mci-design.scss`,移动端 `<style>` 内或独立 CSS 文件)。
|
|
137
|
+
|
|
138
|
+
### 暗黑主题(可选切换 — `data-theme="dark"`)
|
|
139
|
+
|
|
140
|
+
```css
|
|
141
|
+
:root[data-theme="dark"] {
|
|
142
|
+
/* 主色 — 科技紫蓝 */
|
|
143
|
+
--mci-color-primary: #722BFF;
|
|
144
|
+
--mci-color-primary-light: #9B5FFF;
|
|
145
|
+
--mci-color-primary-dark: #5A1FCC;
|
|
146
|
+
--mci-color-primary-glow: rgba(114, 43, 255, 0.35);
|
|
147
|
+
|
|
148
|
+
/* 辅助色 */
|
|
149
|
+
--mci-color-accent-red: #FF2E63;
|
|
150
|
+
--mci-color-accent-blue: #29B8FF;
|
|
151
|
+
--mci-color-accent-gold: #FFD100;
|
|
152
|
+
--mci-color-accent-cyan: #00F5D4;
|
|
153
|
+
--mci-color-accent-pink: #FF6EC7;
|
|
154
|
+
|
|
155
|
+
/* 语义色(成功/警告/错误/信息) */
|
|
156
|
+
--mci-color-success: #00F5D4;
|
|
157
|
+
--mci-color-warning: #FFD100;
|
|
158
|
+
--mci-color-danger: #FF2E63;
|
|
159
|
+
--mci-color-info: #29B8FF;
|
|
160
|
+
|
|
161
|
+
/* 背景 */
|
|
162
|
+
--mci-bg-base: #0A0A0F;
|
|
163
|
+
--mci-bg-elevated: #121218;
|
|
164
|
+
--mci-bg-surface: #1A1A24;
|
|
165
|
+
--mci-bg-card: rgba(255, 255, 255, 0.04);
|
|
166
|
+
--mci-bg-card-hover: rgba(255, 255, 255, 0.08);
|
|
167
|
+
--mci-bg-glass: rgba(255, 255, 255, 0.06);
|
|
168
|
+
--mci-bg-glass-border: rgba(255, 255, 255, 0.1);
|
|
169
|
+
--mci-bg-mask: rgba(0, 0, 0, 0.6);
|
|
170
|
+
|
|
171
|
+
/* 文字 */
|
|
172
|
+
--mci-text-primary: #FFFFFF;
|
|
173
|
+
--mci-text-secondary: #A0A0B8;
|
|
174
|
+
--mci-text-tertiary: #6B6B80;
|
|
175
|
+
--mci-text-disabled: #4A4A5A;
|
|
176
|
+
--mci-text-on-primary: #FFFFFF;
|
|
177
|
+
|
|
178
|
+
/* 边框 */
|
|
179
|
+
--mci-border-color: rgba(255, 255, 255, 0.08);
|
|
180
|
+
--mci-border-color-hover: rgba(255, 255, 255, 0.15);
|
|
181
|
+
--mci-border-glow: rgba(114, 43, 255, 0.3);
|
|
182
|
+
|
|
183
|
+
/* 渐变 */
|
|
184
|
+
--mci-gradient-primary: linear-gradient(135deg, #722BFF 0%, #29B8FF 100%);
|
|
185
|
+
--mci-gradient-hot: linear-gradient(135deg, #FF2E63 0%, #FF6EC7 100%);
|
|
186
|
+
--mci-gradient-gold: linear-gradient(135deg, #FFD100 0%, #FF8C00 100%);
|
|
187
|
+
--mci-gradient-cyber: linear-gradient(135deg, #00F5D4 0%, #722BFF 50%, #FF2E63 100%);
|
|
188
|
+
--mci-gradient-bg: radial-gradient(ellipse at 20% 50%, rgba(114, 43, 255, 0.08) 0%, transparent 60%);
|
|
189
|
+
}
|
|
190
|
+
```
|
|
191
|
+
|
|
192
|
+
### 亮色主题(默认)
|
|
193
|
+
|
|
194
|
+
```css
|
|
195
|
+
:root[data-theme="light"], :root {
|
|
196
|
+
--mci-color-primary: #6C2BD9;
|
|
197
|
+
--mci-color-primary-light: #8B5CF6;
|
|
198
|
+
--mci-color-primary-dark: #5521B5;
|
|
199
|
+
--mci-color-primary-glow: rgba(108, 43, 217, 0.15);
|
|
200
|
+
|
|
201
|
+
--mci-color-accent-red: #E8294A;
|
|
202
|
+
--mci-color-accent-blue: #2196F3;
|
|
203
|
+
--mci-color-accent-gold: #F59E0B;
|
|
204
|
+
--mci-color-accent-cyan: #06B6D4;
|
|
205
|
+
--mci-color-accent-pink: #EC4899;
|
|
206
|
+
|
|
207
|
+
--mci-color-success: #06B6D4;
|
|
208
|
+
--mci-color-warning: #F59E0B;
|
|
209
|
+
--mci-color-danger: #E8294A;
|
|
210
|
+
--mci-color-info: #2196F3;
|
|
211
|
+
|
|
212
|
+
--mci-bg-base: #F5F5FA;
|
|
213
|
+
--mci-bg-elevated: #FFFFFF;
|
|
214
|
+
--mci-bg-surface: #F0F0F8;
|
|
215
|
+
--mci-bg-card: rgba(255, 255, 255, 0.9);
|
|
216
|
+
--mci-bg-card-hover: rgba(255, 255, 255, 1);
|
|
217
|
+
--mci-bg-glass: rgba(255, 255, 255, 0.7);
|
|
218
|
+
--mci-bg-glass-border: rgba(0, 0, 0, 0.08);
|
|
219
|
+
--mci-bg-mask: rgba(0, 0, 0, 0.4);
|
|
220
|
+
|
|
221
|
+
--mci-text-primary: #1A1A2E;
|
|
222
|
+
--mci-text-secondary: #64648C;
|
|
223
|
+
--mci-text-tertiary: #9898B0;
|
|
224
|
+
--mci-text-disabled: #C0C0D0;
|
|
225
|
+
--mci-text-on-primary: #FFFFFF;
|
|
226
|
+
|
|
227
|
+
--mci-border-color: rgba(0, 0, 0, 0.06);
|
|
228
|
+
--mci-border-color-hover: rgba(0, 0, 0, 0.12);
|
|
229
|
+
--mci-border-glow: rgba(108, 43, 217, 0.2);
|
|
230
|
+
|
|
231
|
+
--mci-gradient-primary: linear-gradient(135deg, #6C2BD9 0%, #2196F3 100%);
|
|
232
|
+
--mci-gradient-hot: linear-gradient(135deg, #E8294A 0%, #EC4899 100%);
|
|
233
|
+
--mci-gradient-gold: linear-gradient(135deg, #F59E0B 0%, #EA580C 100%);
|
|
234
|
+
--mci-gradient-cyber: linear-gradient(135deg, #06B6D4 0%, #6C2BD9 50%, #E8294A 100%);
|
|
235
|
+
--mci-gradient-bg: radial-gradient(ellipse at 20% 50%, rgba(108, 43, 217, 0.04) 0%, transparent 60%);
|
|
236
|
+
}
|
|
237
|
+
```
|
|
238
|
+
|
|
239
|
+
### 颜色使用规则
|
|
240
|
+
|
|
241
|
+
- **主题模型分两层**:`data-theme="light|dark"` 控制明暗底色,`data-mci-palette="black|white|red|orange|yellow|green|cyan|blue|purple"` 控制品牌主色。
|
|
242
|
+
- **所有移动端与 PC 网站项目必须支持主流主色切换**:黑、白、红、橙、黄、绿、青、蓝、紫至少 9 个 palette。后台管理系统可由 Element Plus 主题承载,但也必须映射到 `--mci-*` token。
|
|
243
|
+
- **palette 不得只换按钮底色**:必须同步覆盖 `--mci-color-primary`、`--mci-color-primary-strong`、`--mci-text-on-primary`、`--mci-border-glow`、`--mci-gradient-primary`、`--mci-shadow-button`、`--mci-shadow-button-hover`。
|
|
244
|
+
- **白色/黄色主题必须单独处理文字颜色**:主按钮文字使用 `--mci-text-on-primary`,白色主题用深色字,黄色主题用深棕/深灰字,禁止固定白字。
|
|
245
|
+
- **主色**用于核心交互元素(按钮、链接、选中态)
|
|
246
|
+
- **Accent Red / Danger** 用于危险操作、错误、热门标记
|
|
247
|
+
- **Accent Blue / Info** 用于信息提示、次要按钮
|
|
248
|
+
- **Accent Gold / Warning** 用于重要强调、VIP 标签、价格、警告
|
|
249
|
+
- **Accent Cyan / Success** 用于成功状态、在线标识
|
|
250
|
+
- 默认主题为亮色 + 红色 palette;暗黑主题和主色 palette 都作为用户可选项。
|
|
251
|
+
- 用户主题偏好持久化到 `mci-theme`、`mci-palette`、`mci-shape`,初次访问可跟随系统 `prefers-color-scheme`。
|
|
252
|
+
|
|
253
|
+
### 主色 Palette 必备定义
|
|
254
|
+
|
|
255
|
+
```css
|
|
256
|
+
:root[data-mci-palette="black"] { --mci-color-primary:#111827; --mci-text-on-primary:#fff; }
|
|
257
|
+
:root[data-mci-palette="white"] { --mci-color-primary:#F8FAFC; --mci-text-on-primary:#111827; }
|
|
258
|
+
:root[data-mci-palette="red"] { --mci-color-primary:#B51220; --mci-text-on-primary:#fff; }
|
|
259
|
+
:root[data-mci-palette="orange"] { --mci-color-primary:#EA580C; --mci-text-on-primary:#fff; }
|
|
260
|
+
:root[data-mci-palette="yellow"] { --mci-color-primary:#D9A23A; --mci-text-on-primary:#3A2500; }
|
|
261
|
+
:root[data-mci-palette="green"] { --mci-color-primary:#16A34A; --mci-text-on-primary:#fff; }
|
|
262
|
+
:root[data-mci-palette="cyan"] { --mci-color-primary:#0891B2; --mci-text-on-primary:#fff; }
|
|
263
|
+
:root[data-mci-palette="blue"] { --mci-color-primary:#2563EB; --mci-text-on-primary:#fff; }
|
|
264
|
+
:root[data-mci-palette="purple"] { --mci-color-primary:#7C3AED; --mci-text-on-primary:#fff; }
|
|
265
|
+
```
|
|
266
|
+
|
|
267
|
+
实际项目优先直接使用 `Microi.UI/src/theme/tokens.css`,不要复制这段最小示例;新增 palette 时必须补充悬浮阴影、边框高光和渐变。
|
|
268
|
+
|
|
269
|
+
### 移动端可读性底线
|
|
270
|
+
|
|
271
|
+
- 移动端首页、商城、分享海报、资产页必须优先保证阅读清楚。浅色背景上的正文、占位文字、标签、金额、按钮文字不得使用低透明度浅灰或低对比金色。
|
|
272
|
+
- 移动端底部导航、首页快捷入口、个人中心快捷入口的图标对比度与文字同等重要。彩色圆底图标必须显式设定内部图标色,并在每个主题截图确认可见。
|
|
273
|
+
- 关键正文与背景对比度建议不低于 4.5:1;大标题、海报大字、促销卡标题不低于 3:1。金色渐变按钮默认使用深红/深棕文字,不使用白字。
|
|
274
|
+
- 在渐变、图片、红金背景上放文字时,文字必须是实色且有足够字重;不要依赖 `opacity: .6` 这类弱化文字承载业务信息。
|
|
275
|
+
- 完成移动端风格改造后,必须配合 Playwright、浏览器 DevTools、微信开发者工具自动化或项目已有 E2E 工具进行截图和关键文字对比度检查,复核首页第一屏、列表页、登录页、分享海报、空态/未登录态和关键按钮。
|
|
276
|
+
- 用户要求“全自动化测试”“自动化验收”“跑完整测试”等时,如果本次涉及 UI/前端改动,自动化链路必须包含截图验证或视觉断言;只运行构建、lint、静态检查不能宣称已完成全自动化 UI 验收。若当前环境无法启动浏览器/小程序开发者工具,必须明确说明未完成截图验证。
|
|
277
|
+
|
|
278
|
+
---
|
|
279
|
+
|
|
280
|
+
## 阴影体系(层次与质感)
|
|
281
|
+
|
|
282
|
+
阴影是塑造层次感、可点击性和高级质感的关键。采用多层阴影叠加,但不要做脏、糊、重的阴影。
|
|
283
|
+
|
|
284
|
+
```css
|
|
285
|
+
:root {
|
|
286
|
+
/* 基础层级阴影 */
|
|
287
|
+
--mci-shadow-sm: 0 2px 8px rgba(0, 0, 0, 0.25);
|
|
288
|
+
--mci-shadow-md: 0 4px 16px rgba(0, 0, 0, 0.3),
|
|
289
|
+
0 0 12px var(--mci-color-primary-glow);
|
|
290
|
+
--mci-shadow-lg: 0 8px 30px rgba(0, 0, 0, 0.35),
|
|
291
|
+
0 0 20px var(--mci-color-primary-glow);
|
|
292
|
+
--mci-shadow-xl: 0 20px 60px rgba(0, 0, 0, 0.5),
|
|
293
|
+
0 0 40px var(--mci-color-primary-glow);
|
|
294
|
+
|
|
295
|
+
/* 专用阴影 */
|
|
296
|
+
--mci-shadow-card: 0 4px 20px rgba(0, 0, 0, 0.3),
|
|
297
|
+
0 0 15px rgba(114, 43, 255, 0.08);
|
|
298
|
+
--mci-shadow-card-hover: 0 8px 30px rgba(0, 0, 0, 0.4),
|
|
299
|
+
0 0 25px rgba(114, 43, 255, 0.15),
|
|
300
|
+
0 0 60px rgba(114, 43, 255, 0.05);
|
|
301
|
+
--mci-shadow-button: 0 4px 15px var(--mci-color-primary-glow);
|
|
302
|
+
--mci-shadow-button-hover: 0 8px 25px var(--mci-color-primary-glow);
|
|
303
|
+
--mci-shadow-dialog: 0 25px 80px rgba(0, 0, 0, 0.6),
|
|
304
|
+
0 0 50px rgba(114, 43, 255, 0.1);
|
|
305
|
+
--mci-shadow-dropdown: 0 10px 40px rgba(0, 0, 0, 0.45),
|
|
306
|
+
0 0 20px rgba(114, 43, 255, 0.08);
|
|
307
|
+
|
|
308
|
+
/* 强调发光 */
|
|
309
|
+
--mci-glow-primary: 0 0 15px var(--mci-color-primary-glow),
|
|
310
|
+
0 0 45px rgba(114, 43, 255, 0.1);
|
|
311
|
+
--mci-glow-red: 0 0 15px rgba(255, 46, 99, 0.3),
|
|
312
|
+
0 0 45px rgba(255, 46, 99, 0.1);
|
|
313
|
+
--mci-glow-cyan: 0 0 15px rgba(0, 245, 212, 0.3),
|
|
314
|
+
0 0 45px rgba(0, 245, 212, 0.1);
|
|
315
|
+
}
|
|
316
|
+
|
|
317
|
+
/* 移动端阴影减半 — 移动端 GPU 较弱,且小屏幕不需要过强阴影 */
|
|
318
|
+
@media (max-width: 768px) {
|
|
319
|
+
:root {
|
|
320
|
+
--mci-shadow-card: 0 2px 12px rgba(0, 0, 0, 0.3),
|
|
321
|
+
0 0 8px rgba(114, 43, 255, 0.06);
|
|
322
|
+
--mci-shadow-card-hover: 0 4px 18px rgba(0, 0, 0, 0.4),
|
|
323
|
+
0 0 12px rgba(114, 43, 255, 0.1);
|
|
324
|
+
--mci-shadow-button: 0 2px 10px var(--mci-color-primary-glow);
|
|
325
|
+
--mci-shadow-dialog: 0 12px 40px rgba(0, 0, 0, 0.6);
|
|
326
|
+
}
|
|
327
|
+
}
|
|
328
|
+
```
|
|
329
|
+
|
|
330
|
+
### 阴影使用规则
|
|
331
|
+
|
|
332
|
+
| 场景 | 使用阴影 |
|
|
333
|
+
|------|---------|
|
|
334
|
+
| 卡片默认态 | `--mci-shadow-card` |
|
|
335
|
+
| 卡片悬浮态(PC) | `--mci-shadow-card-hover` |
|
|
336
|
+
| 按钮默认态 | `--mci-shadow-button` |
|
|
337
|
+
| 按钮按下态 | `--mci-shadow-button-hover`(移动端无 hover,只用按下/默认) |
|
|
338
|
+
| 弹窗/抽屉 | `--mci-shadow-dialog` |
|
|
339
|
+
| 下拉菜单 | `--mci-shadow-dropdown` |
|
|
340
|
+
| 强调元素 | `--mci-glow-*` |
|
|
341
|
+
|
|
342
|
+
---
|
|
343
|
+
|
|
344
|
+
## 圆角
|
|
345
|
+
|
|
346
|
+
```css
|
|
347
|
+
:root {
|
|
348
|
+
--mci-radius-sm: 8px;
|
|
349
|
+
--mci-radius-md: 12px;
|
|
350
|
+
--mci-radius-lg: 16px;
|
|
351
|
+
--mci-radius-xl: 20px;
|
|
352
|
+
--mci-radius-2xl: 24px;
|
|
353
|
+
--mci-radius-full: 9999px; /* 胶囊按钮 */
|
|
354
|
+
}
|
|
355
|
+
```
|
|
356
|
+
|
|
357
|
+
| 元素 | 圆角 |
|
|
358
|
+
|------|------|
|
|
359
|
+
| 小按钮/标签 | `--mci-radius-sm` (8px) |
|
|
360
|
+
| 常规按钮 | `--mci-radius-md` (12px) |
|
|
361
|
+
| 卡片 | `--mci-radius-xl` (20px) |
|
|
362
|
+
| 弹窗 | `--mci-radius-2xl` (24px) |
|
|
363
|
+
| 胶囊按钮/搜索框 | `--mci-radius-full` |
|
|
364
|
+
|
|
365
|
+
---
|
|
366
|
+
|
|
367
|
+
## 字体
|
|
368
|
+
|
|
369
|
+
```css
|
|
370
|
+
:root {
|
|
371
|
+
--mci-font-family: 'Inter', -apple-system, 'PingFang SC', 'Microsoft YaHei', system-ui, sans-serif;
|
|
372
|
+
--mci-font-mono: 'JetBrains Mono', 'SF Mono', 'Consolas', monospace;
|
|
373
|
+
|
|
374
|
+
/* 字号 — PC */
|
|
375
|
+
--mci-text-xs: 12px;
|
|
376
|
+
--mci-text-sm: 13px;
|
|
377
|
+
--mci-text-base: 14px;
|
|
378
|
+
--mci-text-lg: 16px;
|
|
379
|
+
--mci-text-xl: 20px;
|
|
380
|
+
--mci-text-2xl: 24px;
|
|
381
|
+
--mci-text-3xl: 32px;
|
|
382
|
+
--mci-text-4xl: 40px;
|
|
383
|
+
|
|
384
|
+
/* 字重 */
|
|
385
|
+
--mci-font-normal: 400;
|
|
386
|
+
--mci-font-medium: 500;
|
|
387
|
+
--mci-font-semibold: 600;
|
|
388
|
+
--mci-font-bold: 700;
|
|
389
|
+
--mci-font-black: 900;
|
|
390
|
+
}
|
|
391
|
+
|
|
392
|
+
/* 移动端字号略大,更适合小屏阅读 */
|
|
393
|
+
@media (max-width: 768px) {
|
|
394
|
+
:root {
|
|
395
|
+
--mci-text-xs: 11px;
|
|
396
|
+
--mci-text-sm: 13px;
|
|
397
|
+
--mci-text-base: 15px;
|
|
398
|
+
--mci-text-lg: 17px;
|
|
399
|
+
--mci-text-xl: 20px;
|
|
400
|
+
--mci-text-2xl: 24px;
|
|
401
|
+
--mci-text-3xl: 28px;
|
|
402
|
+
--mci-text-4xl: 34px;
|
|
403
|
+
}
|
|
404
|
+
}
|
|
405
|
+
```
|
|
406
|
+
|
|
407
|
+
### 字体规则
|
|
408
|
+
|
|
409
|
+
- **大标题**:`--mci-text-3xl` + `--mci-font-black`,可配合渐变色文字
|
|
410
|
+
- **小标题**:`--mci-text-xl` + `--mci-font-semibold`
|
|
411
|
+
- **正文**:`--mci-text-base` + `--mci-font-normal`
|
|
412
|
+
- **辅助文字**:`--mci-text-sm` + `--mci-text-secondary`
|
|
413
|
+
- **数据/价格**:`--mci-text-2xl` + `--mci-font-bold` + 渐变色
|
|
414
|
+
|
|
415
|
+
渐变文字写法:
|
|
416
|
+
```css
|
|
417
|
+
.mci-text-gradient {
|
|
418
|
+
background: var(--mci-gradient-primary);
|
|
419
|
+
-webkit-background-clip: text;
|
|
420
|
+
-webkit-text-fill-color: transparent;
|
|
421
|
+
background-clip: text;
|
|
422
|
+
}
|
|
423
|
+
```
|
|
424
|
+
|
|
425
|
+
> ⚠️ **渐变文字低对比陷阱(已反复踩坑)**:`background-clip:text + color/-webkit-text-fill-color:transparent` 在部分 H5 webview / 安卓内核下渲染会失败,导致文字**透明不可见**。
|
|
426
|
+
> 对**关键标题/品牌名/重要文案**优先使用实色高对比文字(如 `color:#8E0613`),或用 `@supports` 做降级:
|
|
427
|
+
> ```scss
|
|
428
|
+
> .mci-text-gradient { color: var(--mci-color-primary); -webkit-text-fill-color: var(--mci-color-primary); }
|
|
429
|
+
> @supports ((-webkit-background-clip:text) or (background-clip:text)) {
|
|
430
|
+
> .mci-text-gradient { background: var(--mci-gradient-primary); -webkit-background-clip:text; background-clip:text; -webkit-text-fill-color:transparent; color:transparent; }
|
|
431
|
+
> }
|
|
432
|
+
> ```
|
|
433
|
+
|
|
434
|
+
---
|
|
435
|
+
|
|
436
|
+
## 间距与触摸目标
|
|
437
|
+
|
|
438
|
+
### 界面引擎仪表盘密度与对齐
|
|
439
|
+
|
|
440
|
+
- 界面引擎首页和仪表盘默认采用单一外层滚动。单个卡片容器尽量完整展示内容,不设置独立纵向滚动条;固定高度不足时应压缩卡片、工具栏、表格行高与间距,或让容器自然增高。
|
|
441
|
+
- 同一层级的卡片必须统一外边距、内边距、圆角、标题高度和内容起始线;同排卡片应使用相同最小高度,左右边缘及底部视觉对齐。
|
|
442
|
+
- 表格容器以默认 15 条数据、表头、工具栏和分页全部可见为桌面端验收基准;日历与公告同样要完整显示头部操作、主体和底部区域。
|
|
443
|
+
- 页面编辑、快捷操作等悬浮按钮必须脱离文档流,不能通过额外空白行或页面顶部内边距占位;半透明悬浮元素需保证文字对比度和 hover 可识别性。
|
|
444
|
+
- 避免组件底部出现大片无信息空白。优先调整组件内部纵向分布、最小高度和网格密度;不得用内部滚动条或隐藏分页来伪装紧凑。
|
|
445
|
+
- 界面引擎移动端必须按真实视口自动改为单列容器;卡片内高频指标和短快捷入口可以采用两列紧凑网格,不能把桌面 4 列机械改成 4 个超高单列卡片。嵌入式列表的返回栏、全局 FAB、固定操作条必须降级为容器内操作,不能覆盖前后兄弟组件。
|
|
446
|
+
- 容器标题右侧存在“更多/进入/刷新/界面设计”等多个动作时,必须放入同一个 `display:flex; align-items:center` 操作区;窄屏允许整体换行并右对齐,禁止依赖 float 或绝对定位造成文字上下错位、互相遮挡。
|
|
447
|
+
|
|
448
|
+
```css
|
|
449
|
+
:root {
|
|
450
|
+
--mci-space-1: 4px;
|
|
451
|
+
--mci-space-2: 8px;
|
|
452
|
+
--mci-space-3: 12px;
|
|
453
|
+
--mci-space-4: 16px;
|
|
454
|
+
--mci-space-5: 20px;
|
|
455
|
+
--mci-space-6: 24px;
|
|
456
|
+
--mci-space-8: 32px;
|
|
457
|
+
--mci-space-10: 40px;
|
|
458
|
+
--mci-space-12: 48px;
|
|
459
|
+
|
|
460
|
+
/* 移动端最小触摸目标 — Apple HIG 44pt / Material 48dp */
|
|
461
|
+
--mci-touch-target: 44px;
|
|
462
|
+
|
|
463
|
+
/* 安全区域(移动端刘海/底部 home indicator) */
|
|
464
|
+
--mci-safe-top: env(safe-area-inset-top, 0);
|
|
465
|
+
--mci-safe-bottom: env(safe-area-inset-bottom, 0);
|
|
466
|
+
--mci-safe-left: env(safe-area-inset-left, 0);
|
|
467
|
+
--mci-safe-right: env(safe-area-inset-right, 0);
|
|
468
|
+
}
|
|
469
|
+
```
|
|
470
|
+
|
|
471
|
+
### 移动端规则
|
|
472
|
+
- 所有可点击元素(按钮、tab、列表项)**最小尺寸 44×44px**
|
|
473
|
+
- 顶部导航栏、沉浸式 header、返回按钮区域必须包含 `var(--mci-safe-top)`,不能假设状态栏固定 20px 或 44px。
|
|
474
|
+
- 底部 tab bar、底部固定操作栏、悬浮购买按钮必须包含 `var(--mci-safe-bottom)`,不能贴住 iPhone home indicator 或 Android 手势条。
|
|
475
|
+
- 左右全屏容器、横屏弹窗、沉浸式背景必须兼容 `var(--mci-safe-left/right)`,避免刘海横屏遮挡。
|
|
476
|
+
- 列表项之间最小间距 8px,避免误触
|
|
477
|
+
|
|
478
|
+
---
|
|
479
|
+
|
|
480
|
+
## 骨架屏 Loading 设计规范
|
|
481
|
+
|
|
482
|
+
所有依赖接口、数据库、远程资源或异步计算的数据区域,首屏加载态必须使用骨架屏(Skeleton Screen),不能只显示 spinner、进度圈、空图标或“数据加载中...”文案。骨架屏属于基础体验规范,适用于 PC、移动端 H5、uni-app、小程序和 WebView。
|
|
483
|
+
|
|
484
|
+
- 骨架屏形态必须接近最终内容版式:列表用行骨架,表格用表头+行骨架,卡片/商品用网格骨架,详情页用大图区+标题/段落骨架,仪表盘用指标卡骨架。
|
|
485
|
+
- 加载期间不能提前显示“暂无数据/暂无明细/空空如也”;空态只能在请求完成且确认无数据后出现。
|
|
486
|
+
- 骨架颜色使用主题变量或中性色阶,不要使用高饱和主色大面积闪烁;亮色主题推荐 `rgba(255,255,255,.72)` 与 `rgba(232,221,205,.9)`,暗色主题推荐低对比深灰阶。
|
|
487
|
+
- 动画只允许使用 `background-position`、`opacity` 或 `transform`,节奏控制在 1.0s 到 1.4s;必须支持 `prefers-reduced-motion` 关闭或弱化动画。
|
|
488
|
+
- 分页加载下一页时,只在列表底部追加紧凑骨架,不覆盖已有内容;切换筛选/分类重载第一页时才显示首屏骨架。
|
|
489
|
+
- 骨架块必须有稳定尺寸、圆角和间距,加载前后不能造成明显布局跳动。
|
|
490
|
+
|
|
491
|
+
参考样式:
|
|
492
|
+
|
|
493
|
+
```scss
|
|
494
|
+
.mci-skeleton {
|
|
495
|
+
position: relative;
|
|
496
|
+
overflow: hidden;
|
|
497
|
+
background: linear-gradient(90deg, rgba(255,255,255,.72), rgba(232,221,205,.9), rgba(255,255,255,.72));
|
|
498
|
+
background-size: 240% 100%;
|
|
499
|
+
animation: mciSkeleton 1.15s ease-in-out infinite;
|
|
500
|
+
}
|
|
501
|
+
@keyframes mciSkeleton {
|
|
502
|
+
0% { background-position: 120% 0; }
|
|
503
|
+
100% { background-position: -120% 0; }
|
|
504
|
+
}
|
|
505
|
+
@media (prefers-reduced-motion: reduce) {
|
|
506
|
+
.mci-skeleton { animation: none; }
|
|
507
|
+
}
|
|
508
|
+
```
|
|
509
|
+
|
|
510
|
+
---
|
|
511
|
+
|
|
512
|
+
## 动效规范(丰富但不卡)
|
|
513
|
+
|
|
514
|
+
### 性能铁律
|
|
515
|
+
|
|
516
|
+
1. **只用 `transform` 和 `opacity` 做动画** — 走 GPU 合成层,不触发重排重绘
|
|
517
|
+
2. **禁止动画 `width/height/top/left/margin/padding`** — 会触发 Layout,导致卡顿
|
|
518
|
+
3. **禁止动画 `box-shadow`** — 改用伪元素 `::after` 的 `opacity` 切换预设阴影
|
|
519
|
+
4. **`will-change` 不要滥用** — 只在动画激活时添加,静态元素禁止使用
|
|
520
|
+
5. **动画时长控制**:微交互 150-250ms,转场 300-400ms,装饰动效 600ms-2s
|
|
521
|
+
6. **使用 `prefers-reduced-motion` 媒体查询**提供无动画回退
|
|
522
|
+
7. **移动端额外限制**:禁用 `backdrop-filter: blur()` 大面积使用(中低端机型严重掉帧),最多用于小型胶囊/标签
|
|
523
|
+
8. **移动端装饰背景**:优先使用结构化渐变、网格、细线、扫光和内容图片;禁用 Canvas 装饰点、密集散点、离散光球、模糊色块堆叠。
|
|
524
|
+
|
|
525
|
+
### Timing Functions
|
|
526
|
+
|
|
527
|
+
```css
|
|
528
|
+
:root {
|
|
529
|
+
--mci-ease-out: cubic-bezier(0.25, 0.46, 0.45, 0.94);
|
|
530
|
+
--mci-ease-spring: cubic-bezier(0.34, 1.56, 0.64, 1);
|
|
531
|
+
--mci-ease-smooth: cubic-bezier(0.4, 0, 0.2, 1);
|
|
532
|
+
--mci-ease-bounce: cubic-bezier(0.68, -0.55, 0.265, 1.55);
|
|
533
|
+
|
|
534
|
+
--mci-duration-fast: 150ms;
|
|
535
|
+
--mci-duration-base: 250ms;
|
|
536
|
+
--mci-duration-slow: 400ms;
|
|
537
|
+
--mci-duration-decorative: 800ms;
|
|
538
|
+
}
|
|
539
|
+
```
|
|
540
|
+
|
|
541
|
+
### 标准动效库
|
|
542
|
+
|
|
543
|
+
#### 1. 卡片悬浮 / 按下(高性能阴影切换)
|
|
544
|
+
|
|
545
|
+
```scss
|
|
546
|
+
.mci-card {
|
|
547
|
+
position: relative;
|
|
548
|
+
border-radius: var(--mci-radius-xl);
|
|
549
|
+
background: var(--mci-bg-card);
|
|
550
|
+
box-shadow: var(--mci-shadow-card);
|
|
551
|
+
transition: transform var(--mci-duration-base) var(--mci-ease-out);
|
|
552
|
+
|
|
553
|
+
&::after {
|
|
554
|
+
content: '';
|
|
555
|
+
position: absolute;
|
|
556
|
+
inset: 0;
|
|
557
|
+
border-radius: inherit;
|
|
558
|
+
box-shadow: var(--mci-shadow-card-hover);
|
|
559
|
+
opacity: 0;
|
|
560
|
+
transition: opacity var(--mci-duration-base) var(--mci-ease-out);
|
|
561
|
+
pointer-events: none;
|
|
562
|
+
z-index: -1;
|
|
563
|
+
}
|
|
564
|
+
|
|
565
|
+
/* PC: hover */
|
|
566
|
+
@media (hover: hover) {
|
|
567
|
+
&:hover {
|
|
568
|
+
transform: translateY(-4px) scale(1.01);
|
|
569
|
+
&::after { opacity: 1; }
|
|
570
|
+
}
|
|
571
|
+
}
|
|
572
|
+
|
|
573
|
+
/* 移动端:active 按压反馈 */
|
|
574
|
+
&:active {
|
|
575
|
+
transform: scale(0.98);
|
|
576
|
+
transition-duration: var(--mci-duration-fast);
|
|
577
|
+
}
|
|
578
|
+
}
|
|
579
|
+
```
|
|
580
|
+
|
|
581
|
+
#### 2. 淡入上浮(列表/卡片进入)
|
|
582
|
+
|
|
583
|
+
```scss
|
|
584
|
+
.mci-fade-up-enter {
|
|
585
|
+
opacity: 0;
|
|
586
|
+
transform: translateY(20px);
|
|
587
|
+
}
|
|
588
|
+
.mci-fade-up-enter-active {
|
|
589
|
+
animation: mciFadeUp var(--mci-duration-slow) var(--mci-ease-out) forwards;
|
|
590
|
+
}
|
|
591
|
+
|
|
592
|
+
@keyframes mciFadeUp {
|
|
593
|
+
to {
|
|
594
|
+
opacity: 1;
|
|
595
|
+
transform: translateY(0);
|
|
596
|
+
}
|
|
597
|
+
}
|
|
598
|
+
|
|
599
|
+
/* 列表交错进入 */
|
|
600
|
+
.mci-stagger-item {
|
|
601
|
+
opacity: 0;
|
|
602
|
+
transform: translateY(16px);
|
|
603
|
+
animation: mciFadeUp var(--mci-duration-slow) var(--mci-ease-out) forwards;
|
|
604
|
+
animation-delay: calc(var(--mci-index, 0) * 60ms);
|
|
605
|
+
}
|
|
606
|
+
```
|
|
607
|
+
|
|
608
|
+
#### 3. 按钮渐变扫光
|
|
609
|
+
|
|
610
|
+
```scss
|
|
611
|
+
.mci-btn-glow {
|
|
612
|
+
position: relative;
|
|
613
|
+
overflow: hidden;
|
|
614
|
+
background: var(--mci-gradient-primary);
|
|
615
|
+
border: none;
|
|
616
|
+
border-radius: var(--mci-radius-md);
|
|
617
|
+
color: var(--mci-text-on-primary);
|
|
618
|
+
box-shadow: var(--mci-shadow-button);
|
|
619
|
+
transition: transform var(--mci-duration-fast) var(--mci-ease-out);
|
|
620
|
+
|
|
621
|
+
&::before {
|
|
622
|
+
content: '';
|
|
623
|
+
position: absolute;
|
|
624
|
+
top: 0;
|
|
625
|
+
left: -100%;
|
|
626
|
+
width: 100%;
|
|
627
|
+
height: 100%;
|
|
628
|
+
background: linear-gradient(
|
|
629
|
+
90deg,
|
|
630
|
+
transparent,
|
|
631
|
+
rgba(255, 255, 255, 0.2),
|
|
632
|
+
transparent
|
|
633
|
+
);
|
|
634
|
+
}
|
|
635
|
+
|
|
636
|
+
@media (hover: hover) {
|
|
637
|
+
&:hover {
|
|
638
|
+
transform: translateY(-2px);
|
|
639
|
+
&::before {
|
|
640
|
+
left: 100%;
|
|
641
|
+
transition: left 0.5s var(--mci-ease-smooth);
|
|
642
|
+
}
|
|
643
|
+
}
|
|
644
|
+
}
|
|
645
|
+
|
|
646
|
+
&:active { transform: scale(0.97); }
|
|
647
|
+
}
|
|
648
|
+
```
|
|
649
|
+
|
|
650
|
+
#### 4. 焦点边框扫光
|
|
651
|
+
|
|
652
|
+
```scss
|
|
653
|
+
.mci-focus-border {
|
|
654
|
+
position: relative;
|
|
655
|
+
border: 1px solid var(--mci-border-glow);
|
|
656
|
+
border-radius: var(--mci-radius-lg);
|
|
657
|
+
overflow: hidden;
|
|
658
|
+
|
|
659
|
+
&::before {
|
|
660
|
+
content: '';
|
|
661
|
+
position: absolute;
|
|
662
|
+
inset: 0;
|
|
663
|
+
border-radius: inherit;
|
|
664
|
+
background: linear-gradient(90deg, transparent, rgba(255,255,255,.28), transparent);
|
|
665
|
+
transform: translateX(-110%) skewX(-18deg);
|
|
666
|
+
animation: mciFocusSweep 3.6s ease-in-out infinite;
|
|
667
|
+
pointer-events: none;
|
|
668
|
+
}
|
|
669
|
+
}
|
|
670
|
+
|
|
671
|
+
@keyframes mciFocusSweep {
|
|
672
|
+
0%, 42% { transform: translateX(-110%) skewX(-18deg); opacity: 0; }
|
|
673
|
+
58% { opacity: .85; }
|
|
674
|
+
100% { transform: translateX(120%) skewX(-18deg); opacity: 0; }
|
|
675
|
+
}
|
|
676
|
+
```
|
|
677
|
+
|
|
678
|
+
#### 5. 玻璃拟态容器(PC 用,移动端慎用)
|
|
679
|
+
|
|
680
|
+
```scss
|
|
681
|
+
.mci-glass {
|
|
682
|
+
background: var(--mci-bg-glass);
|
|
683
|
+
backdrop-filter: blur(12px) saturate(1.5);
|
|
684
|
+
-webkit-backdrop-filter: blur(12px) saturate(1.5);
|
|
685
|
+
border: 1px solid var(--mci-bg-glass-border);
|
|
686
|
+
border-radius: var(--mci-radius-xl);
|
|
687
|
+
box-shadow: var(--mci-shadow-md);
|
|
688
|
+
}
|
|
689
|
+
|
|
690
|
+
/* 移动端降级:用半透明色块代替模糊 */
|
|
691
|
+
@media (max-width: 768px) {
|
|
692
|
+
.mci-glass {
|
|
693
|
+
background: var(--mci-bg-elevated);
|
|
694
|
+
backdrop-filter: none;
|
|
695
|
+
-webkit-backdrop-filter: none;
|
|
696
|
+
}
|
|
697
|
+
}
|
|
698
|
+
```
|
|
699
|
+
|
|
700
|
+
#### 6. 无障碍动效回退
|
|
701
|
+
|
|
702
|
+
```scss
|
|
703
|
+
@media (prefers-reduced-motion: reduce) {
|
|
704
|
+
*, *::before, *::after {
|
|
705
|
+
animation-duration: 0.01ms !important;
|
|
706
|
+
animation-iteration-count: 1 !important;
|
|
707
|
+
transition-duration: 0.01ms !important;
|
|
708
|
+
}
|
|
709
|
+
}
|
|
710
|
+
```
|
|
711
|
+
|
|
712
|
+
---
|
|
713
|
+
|
|
714
|
+
## Vue 3 过渡动画
|
|
715
|
+
|
|
716
|
+
```scss
|
|
717
|
+
/* 淡入上浮 */
|
|
718
|
+
.mci-up-enter-active { transition: all var(--mci-duration-slow) var(--mci-ease-out); }
|
|
719
|
+
.mci-up-leave-active { transition: all var(--mci-duration-base) var(--mci-ease-smooth); }
|
|
720
|
+
.mci-up-enter-from { opacity: 0; transform: translateY(20px); }
|
|
721
|
+
.mci-up-leave-to { opacity: 0; transform: translateY(-10px); }
|
|
722
|
+
|
|
723
|
+
/* 缩放弹出 */
|
|
724
|
+
.mci-scale-enter-active { transition: all var(--mci-duration-base) var(--mci-ease-spring); }
|
|
725
|
+
.mci-scale-leave-active { transition: all var(--mci-duration-fast) var(--mci-ease-smooth); }
|
|
726
|
+
.mci-scale-enter-from { opacity: 0; transform: scale(0.92); }
|
|
727
|
+
.mci-scale-leave-to { opacity: 0; transform: scale(0.95); }
|
|
728
|
+
|
|
729
|
+
/* 列表交错 */
|
|
730
|
+
.mci-list-move,
|
|
731
|
+
.mci-list-enter-active { transition: all var(--mci-duration-slow) var(--mci-ease-out); }
|
|
732
|
+
.mci-list-leave-active { transition: all var(--mci-duration-base) var(--mci-ease-smooth); position: absolute; }
|
|
733
|
+
.mci-list-enter-from { opacity: 0; transform: translateX(-20px); }
|
|
734
|
+
.mci-list-leave-to { opacity: 0; transform: translateX(20px); }
|
|
735
|
+
```
|
|
736
|
+
|
|
737
|
+
---
|
|
738
|
+
|
|
739
|
+
## 组件风格速查
|
|
740
|
+
|
|
741
|
+
### 卡片(通用)
|
|
742
|
+
|
|
743
|
+
```scss
|
|
744
|
+
.mci-card {
|
|
745
|
+
background: var(--mci-bg-card);
|
|
746
|
+
border: 1px solid var(--mci-border-color);
|
|
747
|
+
border-radius: var(--mci-radius-xl);
|
|
748
|
+
padding: var(--mci-space-6);
|
|
749
|
+
box-shadow: var(--mci-shadow-card);
|
|
750
|
+
}
|
|
751
|
+
```
|
|
752
|
+
|
|
753
|
+
### 渐变按钮(主要操作)
|
|
754
|
+
|
|
755
|
+
```scss
|
|
756
|
+
.mci-btn {
|
|
757
|
+
display: inline-flex;
|
|
758
|
+
align-items: center;
|
|
759
|
+
justify-content: center;
|
|
760
|
+
gap: var(--mci-space-2);
|
|
761
|
+
min-height: var(--mci-touch-target);
|
|
762
|
+
padding: 0 var(--mci-space-6);
|
|
763
|
+
background: var(--mci-gradient-primary);
|
|
764
|
+
color: var(--mci-text-on-primary);
|
|
765
|
+
border: none;
|
|
766
|
+
border-radius: var(--mci-radius-md);
|
|
767
|
+
font-size: var(--mci-text-base);
|
|
768
|
+
font-weight: var(--mci-font-semibold);
|
|
769
|
+
cursor: pointer;
|
|
770
|
+
box-shadow: var(--mci-shadow-button);
|
|
771
|
+
transition: transform var(--mci-duration-fast) var(--mci-ease-out);
|
|
772
|
+
|
|
773
|
+
&:active { transform: scale(0.97); }
|
|
774
|
+
@media (hover: hover) {
|
|
775
|
+
&:hover { transform: translateY(-2px); box-shadow: var(--mci-shadow-button-hover); }
|
|
776
|
+
}
|
|
777
|
+
|
|
778
|
+
&--outline {
|
|
779
|
+
background: transparent;
|
|
780
|
+
color: var(--mci-color-primary-light);
|
|
781
|
+
border: 1.5px solid var(--mci-color-primary);
|
|
782
|
+
box-shadow: none;
|
|
783
|
+
}
|
|
784
|
+
|
|
785
|
+
&--ghost {
|
|
786
|
+
background: var(--mci-bg-card);
|
|
787
|
+
color: var(--mci-text-primary);
|
|
788
|
+
box-shadow: none;
|
|
789
|
+
}
|
|
790
|
+
}
|
|
791
|
+
```
|
|
792
|
+
|
|
793
|
+
### 标签 / Badge
|
|
794
|
+
|
|
795
|
+
```scss
|
|
796
|
+
.mci-tag {
|
|
797
|
+
display: inline-flex;
|
|
798
|
+
align-items: center;
|
|
799
|
+
padding: 4px 10px;
|
|
800
|
+
border-radius: var(--mci-radius-full);
|
|
801
|
+
font-size: var(--mci-text-xs);
|
|
802
|
+
font-weight: var(--mci-font-medium);
|
|
803
|
+
|
|
804
|
+
&--hot {
|
|
805
|
+
background: linear-gradient(135deg, rgba(255,46,99,0.15), rgba(255,110,199,0.15));
|
|
806
|
+
color: var(--mci-color-accent-red);
|
|
807
|
+
border: 1px solid rgba(255, 46, 99, 0.2);
|
|
808
|
+
}
|
|
809
|
+
&--new {
|
|
810
|
+
background: linear-gradient(135deg, rgba(0,245,212,0.1), rgba(41,184,255,0.1));
|
|
811
|
+
color: var(--mci-color-accent-cyan);
|
|
812
|
+
border: 1px solid rgba(0, 245, 212, 0.2);
|
|
813
|
+
}
|
|
814
|
+
&--vip {
|
|
815
|
+
background: var(--mci-gradient-gold);
|
|
816
|
+
color: #1A1A2E;
|
|
817
|
+
font-weight: var(--mci-font-bold);
|
|
818
|
+
}
|
|
819
|
+
}
|
|
820
|
+
```
|
|
821
|
+
|
|
822
|
+
### 输入框
|
|
823
|
+
|
|
824
|
+
```scss
|
|
825
|
+
.mci-input {
|
|
826
|
+
display: block;
|
|
827
|
+
width: 100%;
|
|
828
|
+
min-height: var(--mci-touch-target);
|
|
829
|
+
background: var(--mci-bg-surface);
|
|
830
|
+
border: 1px solid var(--mci-border-color);
|
|
831
|
+
border-radius: var(--mci-radius-md);
|
|
832
|
+
padding: 0 var(--mci-space-4);
|
|
833
|
+
color: var(--mci-text-primary);
|
|
834
|
+
font-size: var(--mci-text-base);
|
|
835
|
+
transition: border-color var(--mci-duration-fast) var(--mci-ease-out),
|
|
836
|
+
box-shadow var(--mci-duration-fast) var(--mci-ease-out);
|
|
837
|
+
|
|
838
|
+
&:focus {
|
|
839
|
+
border-color: var(--mci-color-primary);
|
|
840
|
+
box-shadow: 0 0 0 3px var(--mci-color-primary-glow);
|
|
841
|
+
outline: none;
|
|
842
|
+
}
|
|
843
|
+
&::placeholder { color: var(--mci-text-tertiary); }
|
|
844
|
+
}
|
|
845
|
+
```
|
|
846
|
+
|
|
847
|
+
### Element Plus 主题整合(PC)
|
|
848
|
+
|
|
849
|
+
```scss
|
|
850
|
+
:root {
|
|
851
|
+
--el-color-primary: var(--mci-color-primary);
|
|
852
|
+
--el-color-success: var(--mci-color-success);
|
|
853
|
+
--el-color-warning: var(--mci-color-warning);
|
|
854
|
+
--el-color-danger: var(--mci-color-danger);
|
|
855
|
+
--el-color-info: var(--mci-color-info);
|
|
856
|
+
|
|
857
|
+
--el-bg-color: var(--mci-bg-elevated);
|
|
858
|
+
--el-bg-color-overlay: var(--mci-bg-surface);
|
|
859
|
+
--el-text-color-primary: var(--mci-text-primary);
|
|
860
|
+
--el-text-color-regular: var(--mci-text-secondary);
|
|
861
|
+
--el-text-color-secondary: var(--mci-text-tertiary);
|
|
862
|
+
--el-text-color-placeholder: var(--mci-text-disabled);
|
|
863
|
+
|
|
864
|
+
--el-border-color: var(--mci-border-color);
|
|
865
|
+
--el-border-color-light: var(--mci-border-color);
|
|
866
|
+
--el-border-color-lighter: var(--mci-border-color);
|
|
867
|
+
--el-border-radius-base: var(--mci-radius-md);
|
|
868
|
+
|
|
869
|
+
--el-box-shadow: var(--mci-shadow-md);
|
|
870
|
+
--el-box-shadow-light: var(--mci-shadow-sm);
|
|
871
|
+
--el-font-family: var(--mci-font-family);
|
|
872
|
+
}
|
|
873
|
+
|
|
874
|
+
.el-dialog {
|
|
875
|
+
border-radius: var(--mci-radius-2xl) !important;
|
|
876
|
+
background: var(--mci-bg-elevated) !important;
|
|
877
|
+
box-shadow: var(--mci-shadow-dialog) !important;
|
|
878
|
+
border: 1px solid var(--mci-border-color) !important;
|
|
879
|
+
overflow: hidden;
|
|
880
|
+
}
|
|
881
|
+
```
|
|
882
|
+
|
|
883
|
+
---
|
|
884
|
+
|
|
885
|
+
## 移动端专用规范
|
|
886
|
+
|
|
887
|
+
### 1. 视口设置
|
|
888
|
+
|
|
889
|
+
```html
|
|
890
|
+
<meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, minimum-scale=1, user-scalable=no, viewport-fit=cover">
|
|
891
|
+
```
|
|
892
|
+
|
|
893
|
+
### 2. 状态栏 / 安全区适配
|
|
894
|
+
|
|
895
|
+
移动端页面必须同时考虑 iPhone 刘海屏/Dynamic Island/Home Indicator、Android 状态栏/虚拟导航栏/手势条、不同 WebView 容器和横竖屏差异。不要用固定像素硬顶或硬底来“凑”安全区。
|
|
896
|
+
|
|
897
|
+
```scss
|
|
898
|
+
.mci-mobile-page {
|
|
899
|
+
min-height: 100vh;
|
|
900
|
+
padding-top: var(--mci-safe-top);
|
|
901
|
+
padding-bottom: var(--mci-safe-bottom);
|
|
902
|
+
padding-left: var(--mci-safe-left);
|
|
903
|
+
padding-right: var(--mci-safe-right);
|
|
904
|
+
background: var(--mci-bg-base);
|
|
905
|
+
background-image: var(--mci-gradient-bg);
|
|
906
|
+
}
|
|
907
|
+
```
|
|
908
|
+
|
|
909
|
+
落地要求:
|
|
910
|
+
|
|
911
|
+
- HTML/H5 必须设置 `viewport-fit=cover`,否则 iOS 的 `env(safe-area-inset-*)` 不会按预期生效。
|
|
912
|
+
- uni-app 页面需要结合 `uni.getSystemInfoSync().statusBarHeight` 或平台导航栏高度,状态栏高度用于占位,内容安全边距仍使用 `env(safe-area-inset-*)` 兜底。
|
|
913
|
+
- 微信小程序中 `env()` 可能返回 `0`,不得把它作为唯一安全区来源;优先读取 `uni.getWindowInfo()` 并把真实值注入页面壳变量。
|
|
914
|
+
- 自定义导航必须读取微信胶囊矩形并预留右侧空间,任何标题、登录、分享或状态按钮都不能与胶囊区域重叠。
|
|
915
|
+
- 全屏弹层、沉浸式工作台和独立工具页同样属于自定义导航场景。右侧存在两个以上操作按钮且无法在胶囊左侧完整容纳时,必须把整组标题与操作区放到 `capsule.top + capsule.height` 下方,禁止把关闭、新建、历史等按钮塞到胶囊背后。
|
|
916
|
+
- 顶部 fixed/sticky 导航使用 `padding-top: max(var(--mci-safe-top), statusBarHeight)` 的等价实现;返回按钮触摸区域要随顶部安全区整体下移。
|
|
917
|
+
- 底部 fixed 操作栏和 tabBar 使用 `padding-bottom: calc(var(--mci-safe-bottom) + 8px)` 或项目等价间距,页面主体同步预留底部高度,避免按钮遮挡列表最后一项。
|
|
918
|
+
- 多层页面必须定义返回优先级:先关闭键盘/确认框,再关闭抽屉/筛选层,再退出全屏工具页,最后才返回底层业务路由。需要支持手机侧滑返回的全屏功能优先实现为独立路由,不能只做覆盖当前页的普通 `fixed` 蒙层。
|
|
919
|
+
- 安卓三键导航、手势导航和 iOS Safari/PWA/WebView 都要截图验收;不能只在 PC 模拟器或单一 iPhone 尺寸上看起来正常。
|
|
920
|
+
|
|
921
|
+
### 3. 底部 TabBar
|
|
922
|
+
|
|
923
|
+
```scss
|
|
924
|
+
.mci-tabbar {
|
|
925
|
+
position: fixed;
|
|
926
|
+
bottom: 0;
|
|
927
|
+
left: 0;
|
|
928
|
+
right: 0;
|
|
929
|
+
display: flex;
|
|
930
|
+
background: var(--mci-bg-elevated);
|
|
931
|
+
border-top: 1px solid var(--mci-border-color);
|
|
932
|
+
box-shadow: 0 -4px 20px rgba(0, 0, 0, 0.3);
|
|
933
|
+
padding-bottom: var(--mci-safe-bottom);
|
|
934
|
+
z-index: 100;
|
|
935
|
+
}
|
|
936
|
+
|
|
937
|
+
.mci-tabbar__item {
|
|
938
|
+
flex: 1;
|
|
939
|
+
display: flex;
|
|
940
|
+
flex-direction: column;
|
|
941
|
+
align-items: center;
|
|
942
|
+
justify-content: center;
|
|
943
|
+
min-height: var(--mci-touch-target);
|
|
944
|
+
padding: 8px 0;
|
|
945
|
+
color: var(--mci-text-tertiary);
|
|
946
|
+
font-size: var(--mci-text-xs);
|
|
947
|
+
transition: color var(--mci-duration-fast) var(--mci-ease-out);
|
|
948
|
+
|
|
949
|
+
&--active {
|
|
950
|
+
color: var(--mci-color-primary-light);
|
|
951
|
+
}
|
|
952
|
+
&:active {
|
|
953
|
+
transform: scale(0.92);
|
|
954
|
+
}
|
|
955
|
+
}
|
|
956
|
+
```
|
|
957
|
+
|
|
958
|
+
### 4. 顶部导航栏
|
|
959
|
+
|
|
960
|
+
```scss
|
|
961
|
+
.mci-navbar {
|
|
962
|
+
position: sticky;
|
|
963
|
+
top: 0;
|
|
964
|
+
z-index: 50;
|
|
965
|
+
display: flex;
|
|
966
|
+
align-items: center;
|
|
967
|
+
height: 48px;
|
|
968
|
+
padding: 0 var(--mci-space-4);
|
|
969
|
+
padding-top: var(--mci-safe-top);
|
|
970
|
+
background: var(--mci-bg-elevated);
|
|
971
|
+
box-shadow: var(--mci-shadow-sm);
|
|
972
|
+
}
|
|
973
|
+
|
|
974
|
+
.mci-navbar__title {
|
|
975
|
+
flex: 1;
|
|
976
|
+
text-align: center;
|
|
977
|
+
font-size: var(--mci-text-lg);
|
|
978
|
+
font-weight: var(--mci-font-semibold);
|
|
979
|
+
color: var(--mci-text-primary);
|
|
980
|
+
}
|
|
981
|
+
```
|
|
982
|
+
|
|
983
|
+
### 5. 列表项(cell)
|
|
984
|
+
|
|
985
|
+
```scss
|
|
986
|
+
.mci-cell {
|
|
987
|
+
display: flex;
|
|
988
|
+
align-items: center;
|
|
989
|
+
min-height: 56px;
|
|
990
|
+
padding: var(--mci-space-3) var(--mci-space-4);
|
|
991
|
+
background: var(--mci-bg-card);
|
|
992
|
+
border-bottom: 1px solid var(--mci-border-color);
|
|
993
|
+
transition: background var(--mci-duration-fast) var(--mci-ease-out);
|
|
994
|
+
|
|
995
|
+
&:active { background: var(--mci-bg-card-hover); }
|
|
996
|
+
|
|
997
|
+
&__title { flex: 1; color: var(--mci-text-primary); }
|
|
998
|
+
&__value { color: var(--mci-text-secondary); margin-right: var(--mci-space-2); }
|
|
999
|
+
&__arrow {
|
|
1000
|
+
color: var(--mci-text-tertiary);
|
|
1001
|
+
transition: transform var(--mci-duration-base) var(--mci-ease-out);
|
|
1002
|
+
}
|
|
1003
|
+
}
|
|
1004
|
+
```
|
|
1005
|
+
|
|
1006
|
+
### 6. 移动端禁用项清单
|
|
1007
|
+
|
|
1008
|
+
- ❌ `:hover` 单独使用(用 `@media (hover: hover)` 包裹)
|
|
1009
|
+
- ❌ 大面积 `backdrop-filter: blur()`
|
|
1010
|
+
- ❌ JS 随机装饰点(Canvas/WebGL)
|
|
1011
|
+
- ❌ 实时阴影动画
|
|
1012
|
+
- ❌ 复杂的 `filter` 动画(`blur`, `drop-shadow` 不要在动画中切换)
|
|
1013
|
+
- ❌ 自动播放视频背景
|
|
1014
|
+
|
|
1015
|
+
---
|
|
1016
|
+
|
|
1017
|
+
## 装饰性背景(低性能消耗方案)
|
|
1018
|
+
|
|
1019
|
+
### 结构化背景
|
|
1020
|
+
|
|
1021
|
+
Microi 背景必须服务内容层级,不能喧宾夺主。优先使用网格、细线、低透明纹理、扫光和内容相关图片;不要使用离散光球、模糊色块堆叠、密集散点噪声作为主要视觉。
|
|
1022
|
+
|
|
1023
|
+
```scss
|
|
1024
|
+
.mci-page-bg {
|
|
1025
|
+
position: fixed;
|
|
1026
|
+
inset: 0;
|
|
1027
|
+
z-index: -1;
|
|
1028
|
+
overflow: hidden;
|
|
1029
|
+
pointer-events: none;
|
|
1030
|
+
background:
|
|
1031
|
+
linear-gradient(135deg, rgba(181,18,32,.06), transparent 32%),
|
|
1032
|
+
linear-gradient(180deg, var(--mci-bg-base), var(--mci-bg-page));
|
|
1033
|
+
}
|
|
1034
|
+
|
|
1035
|
+
.mci-page-bg::before {
|
|
1036
|
+
content: '';
|
|
1037
|
+
position: absolute;
|
|
1038
|
+
inset: 0;
|
|
1039
|
+
background-image:
|
|
1040
|
+
linear-gradient(rgba(31,41,55,.06) 1px, transparent 1px),
|
|
1041
|
+
linear-gradient(90deg, rgba(31,41,55,.06) 1px, transparent 1px);
|
|
1042
|
+
background-size: 56px 56px;
|
|
1043
|
+
mask-image: linear-gradient(180deg, rgba(0,0,0,.75), transparent 78%);
|
|
1044
|
+
}
|
|
1045
|
+
|
|
1046
|
+
.mci-page-bg::after {
|
|
1047
|
+
content: '';
|
|
1048
|
+
position: absolute;
|
|
1049
|
+
top: 0;
|
|
1050
|
+
left: -30%;
|
|
1051
|
+
width: 38%;
|
|
1052
|
+
height: 100%;
|
|
1053
|
+
background: linear-gradient(90deg, transparent, rgba(255,255,255,.20), transparent);
|
|
1054
|
+
transform: skewX(-18deg);
|
|
1055
|
+
animation: mciBackgroundSweep 8s ease-in-out infinite;
|
|
1056
|
+
}
|
|
1057
|
+
|
|
1058
|
+
@keyframes mciBackgroundSweep {
|
|
1059
|
+
0%, 18% { transform: translateX(0) skewX(-18deg); opacity: 0; }
|
|
1060
|
+
30% { opacity: .72; }
|
|
1061
|
+
54%, 100% { transform: translateX(360%) skewX(-18deg); opacity: 0; }
|
|
1062
|
+
}
|
|
1063
|
+
|
|
1064
|
+
@media (prefers-reduced-motion: reduce) {
|
|
1065
|
+
.mci-page-bg::after { animation: none; }
|
|
1066
|
+
}
|
|
1067
|
+
```
|
|
1068
|
+
|
|
1069
|
+
### 背景层级排查
|
|
1070
|
+
|
|
1071
|
+
- 装饰背景必须 `pointer-events:none` 且位于内容下方。全屏 `position:fixed` 背景如果 `z-index >= 0`,会覆盖无 z-index 的普通文字。
|
|
1072
|
+
- 如果标题/副标题发灰、按钮文字却正常,先临时隐藏背景层验证,不要只改文字颜色。
|
|
1073
|
+
- 推荐修复方式:背景 `z-index:-1`;页面根容器 `position:relative`;所有内容区域保持正常堆叠上下文。
|
|
1074
|
+
|
|
1075
|
+
### 网格背景
|
|
1076
|
+
|
|
1077
|
+
```scss
|
|
1078
|
+
.mci-grid-bg {
|
|
1079
|
+
background-image:
|
|
1080
|
+
linear-gradient(var(--mci-border-color) 1px, transparent 1px),
|
|
1081
|
+
linear-gradient(90deg, var(--mci-border-color) 1px, transparent 1px);
|
|
1082
|
+
background-size: 60px 60px;
|
|
1083
|
+
}
|
|
1084
|
+
```
|
|
1085
|
+
|
|
1086
|
+
---
|
|
1087
|
+
|
|
1088
|
+
## 性能检查清单
|
|
1089
|
+
|
|
1090
|
+
- [ ] 动画只使用 `transform` / `opacity`
|
|
1091
|
+
- [ ] `box-shadow` 变化用伪元素 opacity 切换
|
|
1092
|
+
- [ ] `backdrop-filter` 仅用于小面积元素,移动端有降级
|
|
1093
|
+
- [ ] `will-change` 未在静态元素上使用
|
|
1094
|
+
- [ ] 装饰性动画使用 CSS 而非 JS
|
|
1095
|
+
- [ ] 列表渲染使用虚拟滚动(超过 50 项时)
|
|
1096
|
+
- [ ] 图片使用 `loading="lazy"`
|
|
1097
|
+
- [ ] 复杂动画帧率 > 30fps
|
|
1098
|
+
- [ ] 提供 `prefers-reduced-motion` 无动画回退
|
|
1099
|
+
- [ ] 移动端:`:hover` 用 `@media (hover: hover)` 包裹
|
|
1100
|
+
- [ ] 移动端:所有可点击元素 ≥ 44×44px
|
|
1101
|
+
- [ ] 移动端:背景装饰不使用密集随机点或大面积模糊色块
|
|
1102
|
+
- [ ] 动态数据页:首屏使用骨架屏,不用 spinner/“加载中”文案代替
|
|
1103
|
+
- [ ] 移动端:使用 `env(safe-area-inset-*)` 适配安全区,顶部/底部 fixed 区域在 iOS 与 Android 均不遮挡内容
|
|
1104
|
+
- [ ] 官网/网站首页:导航栏背景、文字、搜索框与首屏背景截图检查,不能出现浅灰导航压在深色英雄区上导致不协调
|
|
1105
|
+
- [ ] 官网/网站首页:所有主按钮、胶囊按钮截图检查文字上下居中,长文字按钮不截断、不贴边、不漂移
|
|
1106
|
+
- [ ] 官网/网站首页:产品卡、助手卡、价格卡等展示卡与页面主背景一致,不能出现孤立的灰白卡片破坏整体视觉
|
|
1107
|
+
- [ ] 全自动化测试:涉及 UI/前端改动时必须生成并检查截图,覆盖关键按钮/胶囊按钮的上下左右居中、空态/未登录态、代表性卡片、安全区和底部栏;构建通过不等于视觉通过
|
|
1108
|
+
- [ ] 提示与确认:源码不存在原生 `alert/confirm/prompt`;长弹窗滚到顶部、中部、底部时,错误提示和确认层都在当前视口正中央且不被宿主遮挡
|
|
1109
|
+
- [ ] 组件复用:同类结构出现两处及以上时必须抽成 `Mci*` 或项目级 `mci-*` 组件,业务页只传文案、图标、状态、动作和少量变体
|
|
1110
|
+
|
|
1111
|
+
---
|
|
1112
|
+
|
|
1113
|
+
## 主题切换实现
|
|
1114
|
+
|
|
1115
|
+
### 首选:Microi.UI 运行时
|
|
1116
|
+
|
|
1117
|
+
```js
|
|
1118
|
+
import { initMciDesign, setMciPalette, setMciShape, setMciTheme } from '@microi/mci-ui/runtime';
|
|
1119
|
+
|
|
1120
|
+
initMciDesign({
|
|
1121
|
+
theme: 'light', // light | dark
|
|
1122
|
+
palette: 'red', // black | white | red | orange | yellow | green | cyan | blue | purple
|
|
1123
|
+
shape: 'rounded', // rounded | flat
|
|
1124
|
+
motion: 'full' // full | reduced
|
|
1125
|
+
});
|
|
1126
|
+
|
|
1127
|
+
setMciPalette('blue');
|
|
1128
|
+
setMciShape('flat');
|
|
1129
|
+
setMciTheme('dark');
|
|
1130
|
+
```
|
|
1131
|
+
|
|
1132
|
+
业务页面只允许调用运行时或项目级主题服务,不要在页面里散写 `document.documentElement.setAttribute(...)`。
|
|
1133
|
+
|
|
1134
|
+
### 原生 Web 降级实现
|
|
1135
|
+
|
|
1136
|
+
```js
|
|
1137
|
+
const PALETTES = ['black','white','red','orange','yellow','green','cyan','blue','purple'];
|
|
1138
|
+
function setTheme(theme) {
|
|
1139
|
+
document.documentElement.setAttribute('data-theme', theme);
|
|
1140
|
+
try { localStorage.setItem('mci-theme', theme); } catch(e) {}
|
|
1141
|
+
}
|
|
1142
|
+
function setPalette(palette) {
|
|
1143
|
+
const next = PALETTES.includes(palette) ? palette : 'red';
|
|
1144
|
+
document.documentElement.setAttribute('data-mci-palette', next);
|
|
1145
|
+
try { localStorage.setItem('mci-palette', next); } catch(e) {}
|
|
1146
|
+
}
|
|
1147
|
+
|
|
1148
|
+
const saved = (() => { try { return localStorage.getItem('mci-theme'); } catch(e) { return null; } })();
|
|
1149
|
+
const savedPalette = (() => { try { return localStorage.getItem('mci-palette'); } catch(e) { return null; } })();
|
|
1150
|
+
const prefersDark = window.matchMedia('(prefers-color-scheme: dark)').matches;
|
|
1151
|
+
// 默认亮色多彩主题,仅当系统明确设置为深色或用户主动选择深色时启用 dark
|
|
1152
|
+
setTheme(saved || (prefersDark ? 'dark' : 'light'));
|
|
1153
|
+
setPalette(savedPalette || 'red');
|
|
1154
|
+
|
|
1155
|
+
// 监听系统主题变化
|
|
1156
|
+
window.matchMedia('(prefers-color-scheme: dark)').addEventListener('change', e => {
|
|
1157
|
+
if (!localStorage.getItem('mci-theme')) setTheme(e.matches ? 'dark' : 'light');
|
|
1158
|
+
});
|
|
1159
|
+
```
|
|
1160
|
+
|
|
1161
|
+
### uni-app(H5/小程序通用)主题切换
|
|
1162
|
+
|
|
1163
|
+
uni-app 中没有 `document` 对象(小程序端),所以推荐两套方案并存:
|
|
1164
|
+
|
|
1165
|
+
**方案A · H5 只操作 html/body 安全外壳**
|
|
1166
|
+
|
|
1167
|
+
H5 端只能把主题状态写到 `html`、`body` 的 `data-*` 属性、主题 class 和 CSS 变量,再让 `uni-page-body`、页面根和 fixed 组件通过变量继承。不要用 `querySelectorAll('.mci-page')`、`MutationObserver`、定时扫描或“延迟补 class”去修改 `.mci-page`、`uni-page-body`、`uni-page`、`RouterView` 下的节点,这些节点由 Vue/uni-app 管理,切主题后导航时可能触发 `Cannot assign to read only property '_'`、`Cannot read properties of null (reading 'type')`、`parentNode`、`scheduler flush` 等错误。
|
|
1168
|
+
|
|
1169
|
+
```scss
|
|
1170
|
+
/* 在 mci-design.scss 加暗色定义 */
|
|
1171
|
+
html.theme-dark,
|
|
1172
|
+
body.theme-dark,
|
|
1173
|
+
html.theme-dark uni-page-body,
|
|
1174
|
+
body.theme-dark uni-page-body,
|
|
1175
|
+
page.theme-dark,
|
|
1176
|
+
.theme-dark {
|
|
1177
|
+
--mci-color-primary: #8B5CF6;
|
|
1178
|
+
--mci-bg-base: #0B0B1F;
|
|
1179
|
+
--mci-bg-card: rgba(28, 28, 60, 0.85);
|
|
1180
|
+
--mci-text-primary: #F5F5FF;
|
|
1181
|
+
--mci-text-secondary: #B8B8D8;
|
|
1182
|
+
--mci-border-color: rgba(255, 255, 255, 0.08);
|
|
1183
|
+
--mci-shadow-md: 0 8rpx 24rpx rgba(0, 0, 0, 0.5);
|
|
1184
|
+
}
|
|
1185
|
+
@media (prefers-color-scheme: dark) {
|
|
1186
|
+
page.theme-auto, :root.theme-auto {
|
|
1187
|
+
/* 同上,跟随系统 */
|
|
1188
|
+
}
|
|
1189
|
+
}
|
|
1190
|
+
```
|
|
1191
|
+
|
|
1192
|
+
```js
|
|
1193
|
+
// utils/theme.js(无 Microi.UI 运行时时的降级写法)
|
|
1194
|
+
const THEME_KEY = 'mci_theme';
|
|
1195
|
+
const PALETTE_KEY = 'mci_palette';
|
|
1196
|
+
const PALETTES = ['black','white','red','orange','yellow','green','cyan','blue','purple'];
|
|
1197
|
+
function applyClass(theme) {
|
|
1198
|
+
if (typeof document !== 'undefined' && document.documentElement) {
|
|
1199
|
+
[document.documentElement, document.body].forEach(function(el) {
|
|
1200
|
+
if (!el) return;
|
|
1201
|
+
el.classList.remove('theme-light', 'theme-dark', 'theme-auto');
|
|
1202
|
+
el.classList.add('theme-' + theme);
|
|
1203
|
+
el.setAttribute('data-mci-theme', theme);
|
|
1204
|
+
});
|
|
1205
|
+
}
|
|
1206
|
+
}
|
|
1207
|
+
function applyPalette(palette) {
|
|
1208
|
+
if (typeof document !== 'undefined' && document.documentElement) {
|
|
1209
|
+
document.documentElement.setAttribute('data-mci-palette', palette);
|
|
1210
|
+
}
|
|
1211
|
+
}
|
|
1212
|
+
export function getTheme() { try { return uni.getStorageSync(THEME_KEY) || 'light'; } catch (e) { return 'light'; } }
|
|
1213
|
+
export function getPalette() { try { return uni.getStorageSync(PALETTE_KEY) || 'red'; } catch (e) { return 'red'; } }
|
|
1214
|
+
export function setTheme(theme) {
|
|
1215
|
+
if (!['light','dark','auto'].includes(theme)) theme = 'light';
|
|
1216
|
+
try { uni.setStorageSync(THEME_KEY, theme); } catch(e) {}
|
|
1217
|
+
applyClass(theme); return theme;
|
|
1218
|
+
}
|
|
1219
|
+
export function setPalette(palette) {
|
|
1220
|
+
if (!PALETTES.includes(palette)) palette = 'red';
|
|
1221
|
+
try { uni.setStorageSync(PALETTE_KEY, palette); } catch(e) {}
|
|
1222
|
+
applyPalette(palette); return palette;
|
|
1223
|
+
}
|
|
1224
|
+
export function toggleTheme() { return setTheme(getTheme() === 'dark' ? 'light' : 'dark'); }
|
|
1225
|
+
export function initTheme() { applyClass(getTheme()); applyPalette(getPalette()); }
|
|
1226
|
+
```
|
|
1227
|
+
|
|
1228
|
+
```vue
|
|
1229
|
+
// App.vue
|
|
1230
|
+
<script>
|
|
1231
|
+
import { initTheme } from '@/utils/theme.js';
|
|
1232
|
+
export default { onLaunch() { initTheme(); } };
|
|
1233
|
+
</script>
|
|
1234
|
+
```
|
|
1235
|
+
|
|
1236
|
+
```vue
|
|
1237
|
+
// 页面里加切换按钮
|
|
1238
|
+
<button @click="toggle">切换主题</button>
|
|
1239
|
+
<script setup>
|
|
1240
|
+
import { toggleTheme, getTheme } from '@/utils/theme.js';
|
|
1241
|
+
const cur = ref(getTheme());
|
|
1242
|
+
function toggle() { cur.value = toggleTheme(); uni.showToast({ title: '已切换为' + (cur.value==='dark'?'暗色':'亮色') }); }
|
|
1243
|
+
</script>
|
|
1244
|
+
```
|
|
1245
|
+
|
|
1246
|
+
**方案B · 小程序端通过 `<page-meta>` + `root-font-size`**(如需小程序原生暗色,否则推荐 wx 的 `themeChange` 事件)
|
|
1247
|
+
|
|
1248
|
+
```vue
|
|
1249
|
+
<template>
|
|
1250
|
+
<page-meta :root-class="themeClass">
|
|
1251
|
+
<view class="content">...</view>
|
|
1252
|
+
</page-meta>
|
|
1253
|
+
</template>
|
|
1254
|
+
```
|
|
1255
|
+
|
|
1256
|
+
### 主题切换 UI 入口规范
|
|
1257
|
+
|
|
1258
|
+
- 入口位置:「我的」页面服务菜单 / 顶部状态栏图标 / 设置页第一项
|
|
1259
|
+
- 形式:明暗模式用图标 + 文案(暗色 / 亮色 / 跟随系统),主色用色板按钮(黑、白、红、橙、黄、绿、青、蓝、紫),点击后立即生效,弹 Toast 反馈。
|
|
1260
|
+
- 色板必须有选中态、无障碍名称和足够触摸面积;白色色板必须有边框,黄色色板文字必须深色。
|
|
1261
|
+
- 切换后立刻持久化(uni.setStorageSync),下次启动 App 在 `onLaunch` 自动 `initTheme()` 应用
|
|
1262
|
+
- H5 fixed 底部导航、固定提交栏和悬浮操作条优先吃 `--mci-*` CSS 变量,不要在主题切换时让组件自己订阅 store 后动态切换根 class。若切主题后点击导航报 Vue scheduler、`parentNode`、`read only property '_'` 或 `null (reading 'type')`,说明主题实现改动了 Vue/uni 托管节点,必须改为 html/body 变量方案。
|
|
1263
|
+
- 骨架屏、加载过渡、报告详情、英文小标题、印章/水印、状态胶囊、摘要卡和富文本容器也属于主题范围。每个主题切换后都要重新触发 loading 态并打开至少一个详情页截图,不能只看首页。
|
|
1264
|
+
|
|
1265
|
+
### 主题颜色变量必须用 var(--mci-*) 而非硬编码
|
|
1266
|
+
|
|
1267
|
+
设计页面时所有颜色、阴影、边框 **强制用变量**,否则切到暗色后只换底色不换文字,会出现"白底白字"。常见违规:
|
|
1268
|
+
|
|
1269
|
+
```scss
|
|
1270
|
+
/* ❌ 错误 */
|
|
1271
|
+
.card { background: #fff; color: #333; box-shadow: 0 8rpx 20rpx rgba(0,0,0,0.05); }
|
|
1272
|
+
|
|
1273
|
+
/* ✅ 正确 */
|
|
1274
|
+
.card {
|
|
1275
|
+
background: var(--mci-bg-card);
|
|
1276
|
+
color: var(--mci-text-primary);
|
|
1277
|
+
box-shadow: var(--mci-shadow-md);
|
|
1278
|
+
}
|
|
1279
|
+
```
|
|
1280
|
+
|
|
1281
|
+
### 渐变色处理
|
|
1282
|
+
|
|
1283
|
+
渐变色在暗色下需要重新调色(亮色用 #FF8A5C → 暗色 #B14CA0 之类),定义 `--mci-gradient-*` 变量并在 `.theme-dark` 下覆盖。
|
|
1284
|
+
|
|
1285
|
+
---
|
|
1286
|
+
|
|
1287
|
+
|
|
1288
|
+
## 命名规范
|
|
1289
|
+
|
|
1290
|
+
- CSS 变量前缀:`--mci-`
|
|
1291
|
+
- 组件类名前缀:`.mci-`
|
|
1292
|
+
- 动画 keyframe 前缀:`mci`(如 `mciFadeUp`、`mciNeonPulse`)
|
|
1293
|
+
- Vue Transition name 前缀:`mci-`
|
|
1294
|
+
- 修饰符使用 BEM:`.mci-card--active`、`.mci-btn--outline`
|
|
1295
|
+
- JS 全局变量前缀:`MCI_`(如 `MCI_THEME`)
|
|
1296
|
+
|
|
1297
|
+
---
|
|
1298
|
+
|
|
1299
|
+
## 速查:从头搭建一个移动端页面
|
|
1300
|
+
|
|
1301
|
+
```vue
|
|
1302
|
+
<template>
|
|
1303
|
+
<div class="mci-mobile-page">
|
|
1304
|
+
<!-- 顶部导航 -->
|
|
1305
|
+
<header class="mci-navbar">
|
|
1306
|
+
<h1 class="mci-navbar__title">{{ title }}</h1>
|
|
1307
|
+
</header>
|
|
1308
|
+
|
|
1309
|
+
<!-- 主内容 -->
|
|
1310
|
+
<main class="page-content">
|
|
1311
|
+
<section
|
|
1312
|
+
v-for="(item, i) in list"
|
|
1313
|
+
:key="item.id"
|
|
1314
|
+
class="mci-card mci-stagger-item"
|
|
1315
|
+
:style="{ '--mci-index': i }"
|
|
1316
|
+
>
|
|
1317
|
+
<span class="mci-tag mci-tag--hot">HOT</span>
|
|
1318
|
+
<h3>{{ item.name }}</h3>
|
|
1319
|
+
<p class="mci-text-gradient price">{{ item.price }}</p>
|
|
1320
|
+
<button class="mci-btn">立即查看</button>
|
|
1321
|
+
</section>
|
|
1322
|
+
</main>
|
|
1323
|
+
|
|
1324
|
+
<!-- 底部 Tabbar -->
|
|
1325
|
+
<nav class="mci-tabbar">
|
|
1326
|
+
<a class="mci-tabbar__item mci-tabbar__item--active"><svg class="mci-tabbar__icon" aria-hidden="true"><use href="#icon-home" /></svg><span>首页</span></a>
|
|
1327
|
+
<a class="mci-tabbar__item"><svg class="mci-tabbar__icon" aria-hidden="true"><use href="#icon-message" /></svg><span>消息</span></a>
|
|
1328
|
+
<a class="mci-tabbar__item"><svg class="mci-tabbar__icon" aria-hidden="true"><use href="#icon-user" /></svg><span>我的</span></a>
|
|
1329
|
+
</nav>
|
|
1330
|
+
</div>
|
|
1331
|
+
</template>
|
|
1332
|
+
|
|
1333
|
+
<style lang="scss" scoped>
|
|
1334
|
+
.page-content {
|
|
1335
|
+
padding: var(--mci-space-4);
|
|
1336
|
+
padding-bottom: calc(var(--mci-touch-target) + var(--mci-safe-bottom) + var(--mci-space-8));
|
|
1337
|
+
display: flex;
|
|
1338
|
+
flex-direction: column;
|
|
1339
|
+
gap: var(--mci-space-4);
|
|
1340
|
+
}
|
|
1341
|
+
.price {
|
|
1342
|
+
font-size: var(--mci-text-2xl);
|
|
1343
|
+
font-weight: var(--mci-font-bold);
|
|
1344
|
+
}
|
|
1345
|
+
</style>
|
|
1346
|
+
```
|
|
1347
|
+
|
|
1348
|
+
|
|
1349
|
+
---
|
|
1350
|
+
|
|
1351
|
+
## 🚨 移动端低代码项目落地踩坑(必读,2026.5)
|
|
1352
|
+
|
|
1353
|
+
实战中频繁出现的 7 类问题,统一按以下规则处理。
|
|
1354
|
+
|
|
1355
|
+
### 1. 路由前缀不要硬编码租户名
|
|
1356
|
+
|
|
1357
|
+
- 错误:在 `manifest.json` 写死 `"router": { "base": "/fixed-tenant/" }`。
|
|
1358
|
+
- 正确:默认使用 `"router": { "base": "/" }`;租户由运行配置、`OsClient` 和请求头/参数确定。
|
|
1359
|
+
- 不要自行把租户名拼进 API 路径。平台接口使用 `/api/...`、`/apiengine/...` 等标准路由。
|
|
1360
|
+
|
|
1361
|
+
### 2. tabBar 使用本地静态 PNG 图标
|
|
1362
|
+
|
|
1363
|
+
- uni-app/微信小程序 tabBar 的 `iconPath`、`selectedIconPath` 使用项目内静态 PNG。
|
|
1364
|
+
- 不使用 emoji、字体图标、远程 URL;SVG 仅在目标端明确支持并已做真实设备验证时使用。
|
|
1365
|
+
- 普通态与选中态保持相同画布和轮廓,推荐 60×60 至 81×81 px,并验证深浅色背景可读性。
|
|
1366
|
+
|
|
1367
|
+
### 3. 字号样式不要通配所有 `text`
|
|
1368
|
+
|
|
1369
|
+
Scoped SCSS 中的 `.entry text { font-size: 40rpx; }` 会同时放大图标文字和子标签。图标、标题、说明必须使用独立 class:
|
|
1370
|
+
|
|
1371
|
+
```scss
|
|
1372
|
+
.entry .entry-icon { font-size: 40rpx; }
|
|
1373
|
+
.entry .entry-label { font-size: 22rpx; }
|
|
1374
|
+
```
|
|
1375
|
+
|
|
1376
|
+
### 4. 个人中心/详情入口按信息层级选布局
|
|
1377
|
+
|
|
1378
|
+
- 高频资产、订单状态、服务入口适合 4~5 列网格。
|
|
1379
|
+
- 设置、安全、协议等低频入口适合纵向列表。
|
|
1380
|
+
- 单元格须有稳定触控区域、清晰标签和一致间距;不要为了追求密度牺牲可读性。
|
|
1381
|
+
|
|
1382
|
+
### 5. 每个可点击元素都要有反馈
|
|
1383
|
+
|
|
1384
|
+
```scss
|
|
1385
|
+
.cell, .entry-item, .product-card, .zone-card {
|
|
1386
|
+
position: relative;
|
|
1387
|
+
transition: transform .2s ease, box-shadow .2s ease;
|
|
1388
|
+
}
|
|
1389
|
+
.cell:active, .entry-item:active {
|
|
1390
|
+
transform: scale(.94);
|
|
1391
|
+
}
|
|
1392
|
+
@keyframes fadein-up {
|
|
1393
|
+
from { opacity: 0; transform: translateY(16rpx); }
|
|
1394
|
+
to { opacity: 1; transform: translateY(0); }
|
|
1395
|
+
}
|
|
1396
|
+
.animate-fadein { animation: fadein-up .45s ease both; }
|
|
1397
|
+
@media (prefers-reduced-motion: reduce) {
|
|
1398
|
+
.animate-fadein { animation: none; }
|
|
1399
|
+
}
|
|
1400
|
+
```
|
|
1401
|
+
|
|
1402
|
+
动效只表达状态,不承担业务完成事实;提交、支付、安装等动作仍以服务端返回和可恢复状态为准。
|
|
1403
|
+
|
|
1404
|
+
### 6. 品牌名和 Logo 的用户可见位置保持一致
|
|
1405
|
+
|
|
1406
|
+
同步检查 `manifest.json` 的 `name/h5.title`、`pages.json` 的导航标题、登录/注册/首页品牌区、空状态和分享标题。控制台中的技术标识可保留,但用户可见文案必须统一。
|
|
1407
|
+
|
|
1408
|
+
### 7. 接口地址由标准引擎工具维护
|
|
1409
|
+
|
|
1410
|
+
- `microi_create_engine`/`microi_upsert_engine` 会维护 `ApiEngineKey`、`ApiAddress` 和路由缓存。
|
|
1411
|
+
- 写入超时先用标准 get/list 工具回读,不得立即重复创建。
|
|
1412
|
+
- 禁止通过手工 SQL、直接修改 `sys_apiengine` 或自行拼 Redis Key 修补路由;这会绕过租户、审计、缓存失效和控制面权限。
|
|
1413
|
+
- 长任务使用后台任务并持久化进度;普通接口写入后以远端回读为最终依据。
|
|
1414
|
+
|
|
1415
|
+
## 🔗 关联字段:保存真实 Id,界面展示可读标签
|
|
1416
|
+
|
|
1417
|
+
关联字段的数据库事实值通常是 `XxxId`。表单使用 `JoinForm`、`OpenTable` 或带数据源的 `Select` 显示名称,`SelectSaveField` 保存 `Id`,`SelectLabel` 展示名称。不要因为列表默认显示 Id,就强制所有业务表冗余一对可编辑的 `XxxId/XxxName` 字段。
|
|
1418
|
+
|
|
1419
|
+
### Select 数据源示例
|
|
1420
|
+
|
|
1421
|
+
```json
|
|
1422
|
+
{
|
|
1423
|
+
"DataSource": "Sql",
|
|
1424
|
+
"Sql": "select Id, Name from mall_category where Name like '%$Keyword$%' limit 0,20",
|
|
1425
|
+
"SelectLabel": "Name",
|
|
1426
|
+
"SelectSaveField": "Id",
|
|
1427
|
+
"SelectSaveFormat": "Text",
|
|
1428
|
+
"EnableSearch": true,
|
|
1429
|
+
"DataSourceSqlRemote": true
|
|
1430
|
+
}
|
|
1431
|
+
```
|
|
1432
|
+
|
|
1433
|
+
- `$Keyword$` 是平台数据源占位符,不要把浏览器输入直接拼进任意 SQL。
|
|
1434
|
+
- 关联表、字段和数据源必须来自当前租户,并受当前表单/菜单的授权与数据范围约束。
|
|
1435
|
+
- 大表使用远程搜索和分页,不一次性把全表拉到浏览器。
|
|
1436
|
+
- 列表展示名称优先配置 Join/模块关联字段或受控数据源,不把隐藏 Id 暴露给用户。
|
|
1437
|
+
|
|
1438
|
+
### 什么时候增加 `XxxName` 快照字段
|
|
1439
|
+
|
|
1440
|
+
只有在业务明确要求“保存当时名称”、离线展示、历史审计或高频报表需要时才增加 `XxxName`。它是快照/冗余字段,不是外键事实源,并遵守:
|
|
1441
|
+
|
|
1442
|
+
1. 后端 SubmitBefore/接口引擎在同一事务内根据 `XxxId` 校验并写入名称。
|
|
1443
|
+
2. 前端 V8 可以即时回显,但不能作为唯一一致性保障。
|
|
1444
|
+
3. 关联名称后续变化时,先明确历史快照是否应随之更新。
|
|
1445
|
+
4. 批量回填必须参数化、可恢复、可幂等,并经过明确写入确认。
|
|
1446
|
+
|
|
1447
|
+
### MCP 建模流程
|
|
1448
|
+
|
|
1449
|
+
1. 先用 `microi_get_db_schema` 获取真实表和字段。
|
|
1450
|
+
2. 使用 `microi_build_field_config` 生成 JoinForm/OpenTable/Select 配置。
|
|
1451
|
+
3. 使用 `microi_add_field` 或 `microi_update_field` 写入字段。
|
|
1452
|
+
4. 修改 KeyValue/Config 后回读 `microi_get_field_list`,并执行 `microi_refresh_schema_cache`。
|
|
1453
|
+
5. 在真实菜单下验证普通角色能看到标签,但不能借数据源越权读取其它表或行。
|
|
1454
|
+
---
|
|
1455
|
+
|
|
1456
|
+
## 表单布局规范(Column)
|
|
1457
|
+
|
|
1458
|
+
> 平台默认设计标准:所有 `diy_table` **应使用双列布局** (`Column = 2`),更紧凑现代,符合主流后台 SaaS 视觉密度。
|
|
1459
|
+
|
|
1460
|
+
### 创建表时
|
|
1461
|
+
|
|
1462
|
+
```jsonc
|
|
1463
|
+
microi_create_table {
|
|
1464
|
+
"name": "Crm_Customer",
|
|
1465
|
+
"description": "客户",
|
|
1466
|
+
"column": 2 // ✅ 默认就是 2,无需显式传,但推荐写明
|
|
1467
|
+
}
|
|
1468
|
+
```
|
|
1469
|
+
|
|
1470
|
+
### 修复存量表(一次性把所有 `Column=null` 改成 2)
|
|
1471
|
+
|
|
1472
|
+
```jsonc
|
|
1473
|
+
microi_update_table {
|
|
1474
|
+
"name": "Crm_Customer",
|
|
1475
|
+
"column": 2
|
|
1476
|
+
}
|
|
1477
|
+
```
|
|
1478
|
+
|
|
1479
|
+
### 何时使用 Column=1(单列)
|
|
1480
|
+
|
|
1481
|
+
- 工作流审批表单(字段少且需要专注)
|
|
1482
|
+
- 移动端优先表单(手机宽度不够双列)
|
|
1483
|
+
- 含大量富文本/长文本字段的内容编辑表
|
|
1484
|
+
|
|
1485
|
+
### 何时使用 Column=3(三列)
|
|
1486
|
+
|
|
1487
|
+
- 字段≥18 的"基础档案"类大表(员工、商品 SKU、设备清单)
|
|
1488
|
+
- 桌面分辨率≥1920px 的内部管理后台
|
|
1489
|
+
|
|
1490
|
+
> 修改 `Column` 后会自动清缓存(`microi_update_table` 后端走 `UptFormData('diy_table')` + 主动 `RefreshSchemaCache`),前端硬刷新(Ctrl+Shift+R)即可看到效果。
|
|
1491
|
+
|
|
1492
|
+
---
|
|
1493
|
+
|
|
1494
|
+
## 表单分组规范:Tabs vs CollapseGroup(强制)
|
|
1495
|
+
|
|
1496
|
+
> **核心原则**:默认**不分组** → 小业务域用 **`CollapseGroup` 折叠分组** → 只有足够长或强任务隔离的业务域才用 **`Tabs` 分页**。禁止只按字段数判断:双列布局中 8 个短字段约占 4 行,仍不应独占 Tab;普通业务域通常达到 6 个有效表单行才考虑 Tab。
|
|
1497
|
+
|
|
1498
|
+
### 三种分组方式
|
|
1499
|
+
|
|
1500
|
+
| 方式 | 存储位置 | 控件 | 适用场景 |
|
|
1501
|
+
|------|---------|------|---------|
|
|
1502
|
+
| **A. 表级 Tab** | `diy_table.Tabs` + 字段 `Tab` | 表单顶部 Tab 条 | 大表单拆 2~5 个业务域,每域通常 ≥6 个有效表单行,或属于扫码/子表/代码编辑等强任务模式 |
|
|
1503
|
+
| **B. 字段级 CollapseGroup** | `diy_field.Component='CollapseGroup'` + `Config.CollapseGroup` | 折叠面板标题 | 小业务域(≤5 个有效表单行),**所有分组同屏可见、可同时展开** |
|
|
1504
|
+
| **C. 字段级 Tabs 控件** | `diy_field.Component='Tabs'` + `Config.FieldTabs` | 字段是 Tab 容器 | 嵌套 Tab 场景(不推荐优先用) |
|
|
1505
|
+
|
|
1506
|
+
### 表单规模与分组决策表
|
|
1507
|
+
|
|
1508
|
+
| 有效表单行与任务特征 | 推荐方案 |
|
|
1509
|
+
|---------|---------|
|
|
1510
|
+
| ≤ 6 行且无复杂控件 | **不分组**(直接平铺) |
|
|
1511
|
+
| 7 ~ 12 行且无强任务隔离 | `CollapseGroup` 收起次要字段,或直接平铺 |
|
|
1512
|
+
| > 12 行且至少两个业务域各 ≥ 6 行 | `diy_table.Tabs`(大域)或混合(Tab + 嵌套 CollapseGroup) |
|
|
1513
|
+
| 扫码、报工、大型子表、代码编辑等强任务模式 | 可独立使用 `diy_table.Tabs`,不受普通行数阈值限制 |
|
|
1514
|
+
|
|
1515
|
+
### CollapseGroup Config 示例
|
|
1516
|
+
|
|
1517
|
+
```jsonc
|
|
1518
|
+
// diy_field 必要字段
|
|
1519
|
+
{
|
|
1520
|
+
"Component": "CollapseGroup",
|
|
1521
|
+
"Type": "varchar(50)",
|
|
1522
|
+
"Visible": 1,
|
|
1523
|
+
"AppVisible": 1,
|
|
1524
|
+
"Config": "{\"CollapseGroup\":{\"DefaultCollapsed\":false,\"ScopeMode\":\"UntilNextGroup\",\"Description\":\"MRP 运算状态、批次号与时间\",\"Icon\":\"fas fa-calculator\",\"Theme\":\"primary\",\"ShowFieldCount\":true}}"
|
|
1525
|
+
}
|
|
1526
|
+
```
|
|
1527
|
+
|
|
1528
|
+
### 必做与禁止
|
|
1529
|
+
|
|
1530
|
+
- ✅ 任何 Tab / CollapseGroup 必须有 `Description` 解释分组用途。
|
|
1531
|
+
- ✅ CollapseGroup 必须设 `Icon`(如 `fas fa-calculator`、`fas fa-info-circle`),不默认空白。
|
|
1532
|
+
- ✅ 修改 Tab/CollapseGroup 配置后必须 `microi_refresh_schema_cache`。
|
|
1533
|
+
- ❌ **禁止**为 ≤5 个有效表单行的业务域单独建 Tab;8~10 个双列短字段通常也应使用 CollapseGroup。
|
|
1534
|
+
- ❌ **禁止**仅凭 13~30 个原始字段决定平铺或分 Tab;总有效行超过 6 且存在明确业务域时,至少使用 CollapseGroup 分组。
|
|
1535
|
+
- ❌ **禁止**给 Tabs/CollapseGroup/Divider/Alert 等布局控件设 `FormWidth=24`(天然占整行)。
|
|
1536
|
+
- ❌ **禁止**只创建 Tab 不写字段的 `Tab` 归属。
|
|
1537
|
+
- ❌ 布局优化不得顺带覆盖字段 `Config/V8Code/KeyupV8Code` 或表级 V8 事件;修改前后必须回读比较,发现 Tab 显隐 API 时先适配再迁移。
|
|
1538
|
+
|
|
1539
|
+
完整规范、Config JSON 模板、回读验收清单和反例参考见 `microi-form-layout/SKILL.md`。
|
|
1540
|
+
|
|
1541
|
+
---
|
|
1542
|
+
|
|
1543
|
+
## 缓存刷新(解决"我改了字段但页面不变"问题)
|
|
1544
|
+
|
|
1545
|
+
平台对 `diy_field` 的字段列表有 Redis 缓存,键格式 `Microi:{OsClient}:FormData:diy_table_field_list:{TableId|TableName}`。
|
|
1546
|
+
|
|
1547
|
+
**何时缓存会失效**:
|
|
1548
|
+
- ✅ 通过 `microi_add_field` / `microi_update_field` / `microi_update_table` 走原生 API → 自动清
|
|
1549
|
+
- ✅ 通过低代码后台界面操作(diy_table 表单事件触发)→ 自动清
|
|
1550
|
+
- ❌ 直接 `V8.FormEngine.UptFormData('diy_field', ...)` → **不会触发清缓存**(这是历史 bug)
|
|
1551
|
+
|
|
1552
|
+
**何时手动清**:
|
|
1553
|
+
```jsonc
|
|
1554
|
+
microi_refresh_schema_cache { "tables": ["mall_address", "mall_member"] }
|
|
1555
|
+
```
|
|
1556
|
+
该工具会清除每张表的 6 个 key 变种(`diy_table` / `Diy_Table` / `diy_table_field_list` × `id|name`)。
|
|
1557
|
+
|
|
1558
|
+
---
|
|
1559
|
+
|
|
1560
|
+
## 接口引擎匿名访问
|
|
1561
|
+
|
|
1562
|
+
登录、注册、首页公共数据等接口必须 `AllowAnonymous=1`,否则未登录用户调用会拿到 `null`:
|
|
1563
|
+
|
|
1564
|
+
```jsonc
|
|
1565
|
+
microi_set_engine_anonymous {
|
|
1566
|
+
"apiEngineKeys": ["mall_member_login", "mall_member_register", "mall_home_data"],
|
|
1567
|
+
"allowAnonymous": 1
|
|
1568
|
+
}
|
|
1569
|
+
```
|
|
1570
|
+
|
|
1571
|
+
|
|
1572
|
+
## MCI-UI 与第三方组件库策略
|
|
1573
|
+
|
|
1574
|
+
Microi 的 UI 规范不应该只停留在 skills 文档。面向品牌长期建设时,应形成可复用的 MCI-UI 体系:设计变量、基础样式、组件约定、示例站点、移动端与 PC 网站组件库。
|
|
1575
|
+
|
|
1576
|
+
- **默认规则**:当用户没有主动指定 UI 风格、UI 库或品牌视觉时,AI 必须默认采用 Microi吾码UI(Microi.UI / MCI-UI)作为移动端、PC 官网、企业网站、产品站、活动页和响应式网站的设计基础。
|
|
1577
|
+
- **自动识别**:只要项目属于 Microi 生态、吾码源码、吾码客户项目,或需求中出现“移动端项目、网站、企业站、商城、会员中心、资产页、官网、H5、uni-app、Vue3”等关键词,即使用户没有单独说明 UI 风格,也应自动套用本规范与 `Microi.UI/` 组件。
|
|
1578
|
+
- **落地要求**:业务页面优先使用 `MciPage`、`MciSection`、`MciButton`、`MciCard`、`MciCell`、`MciTabs`、`MciSkeleton`、`MciDataState`、`MciThemePanel` 等组件或项目级 `mci-*` 封装;不要重新发明一套分散样式。
|
|
1579
|
+
- **例外场景**:后台管理系统继续使用 Element Plus + Microi theme;强行业 UI 或客户指定视觉可以定制主题 token,但仍优先保留 `--mci-*` 变量、骨架屏、安全区和动效规范。
|
|
1580
|
+
- UniApp 项目不强制业务页面直接依赖某一个第三方 UI 库。推荐把 `uni-ui` 作为官方跨端基础组件底座之一,但业务视觉必须通过 `MCI-UI Mobile` 或项目级 `mci-*` 组件封装承载,避免页面直接散落 `uni-ui/uView/FirstUI/TDesign` 风格。
|
|
1581
|
+
- PC 后台管理系统继续使用 Element Plus,不替换选型;但主题变量、间距、骨架屏、空态、安全区、表单密度和品牌色必须服从 `--mci-*` 设计变量。
|
|
1582
|
+
- PC 官网、产品站、文档站、营销页和响应式网站应优先使用 `MCI-UI Web` 的设计变量与轻量组件。只有当页面是强表单、强数据录入或后台化工具时,才引入 Element Plus、TDesign Vue、Naive UI、Arco Design Vue 等成熟组件库作为底座。
|
|
1583
|
+
- MCI-UI 应分层建设:`@microi/theme` 负责 tokens;`@microi/v8` 负责前端 SDK;`@microi/ui-mobile` 面向 UniApp;`@microi/ui-web` 面向官网和响应式站点;`Microi.Client` 后台则用 Element Plus + MCI theme。
|
|
1584
|
+
- `microi.doc` 作为 VitePress 官方文档站,应逐步成为 MCI-UI 的展示入口:组件演示、设计变量、移动端骨架屏、安全区、富文本、上传资源、主题切换都应该有可查看示例,而不是只写在 skill 中。
|
|
1585
|
+
|
|
1586
|
+
## MCI-UI 源码落地位置
|
|
1587
|
+
|
|
1588
|
+
MCI-UI 已在吾码源码根目录落地:`Microi.UI/`。
|
|
1589
|
+
|
|
1590
|
+
- 新的移动端 UniApp/H5 项目应优先使用 `Microi.UI/src/uniapp` 中的 `MciPage`、`MciNavbar`、`MciButton`、`MciCard`、`MciCell`、`MciSection`、`MciTabs`、`MciMetricCard`、`MciActionBar`、`MciAvatar`、`MciProductCard`、`MciSkeleton`、`MciDataState`、`MciRichText`,再按业务补项目组件。
|
|
1591
|
+
- 新的 PC 官网、产品站、文档站、响应式网站应优先使用 `Microi.UI/src/web` 和 `Microi.UI/src/theme`,不要直接套后台 Element Plus 风格。
|
|
1592
|
+
- `Microi.UI/src/theme/tokens.css` 是品牌 token 源头;新组件颜色、圆角、阴影、间距、安全区、骨架屏都必须走 `--mci-*` 变量。
|
|
1593
|
+
- `Microi.UI/src/theme/runtime.js` 是主题运行时入口;项目应通过 `initMciDesign()`、`setMciPalette()`、`setMciShape()`、`setMciTheme()` 统一设置黑白红橙黄绿青蓝紫主色、圆角/扁平、亮暗主题和动效偏好。
|
|
1594
|
+
- `MciPage` 默认带页面入场动效;业务页如果有特殊路由转场,可以关闭 `animated` 后使用项目级转场,但不能让动态页面无反馈地直接闪现。
|
|
1595
|
+
- `MciButton`、`MciCard` 必须保留 hover/pressed/focus/sheen 等基础反馈;业务组件可以封装样式,但不能删掉交互状态。
|
|
1596
|
+
- 第三方 UI 库只能作为底层能力或局部补充,不能绕过 MCI-UI 直接决定产品视觉。
|