@icen.ai/ui 0.9.0 → 0.11.0

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.
Files changed (431) hide show
  1. package/AGENTS.md +82 -254
  2. package/LICENSE +21 -0
  3. package/README.md +60 -96
  4. package/dist/base.css +258 -188
  5. package/dist/behaviors/accordion.mjs +8 -8
  6. package/dist/behaviors/ai-branch.d.mts +1 -1
  7. package/dist/behaviors/ai-branch.mjs +1011 -94
  8. package/dist/behaviors/ai-chat.d.mts +9 -9
  9. package/dist/behaviors/ai-chat.mjs +1122 -169
  10. package/dist/behaviors/ai-composer.d.mts +47 -15
  11. package/dist/behaviors/ai-composer.mjs +2018 -534
  12. package/dist/behaviors/ai-core.d.mts +1 -1
  13. package/dist/behaviors/ai-core.mjs +1017 -107
  14. package/dist/behaviors/ai-diff.mjs +1020 -127
  15. package/dist/behaviors/ai-feedback.d.mts +1 -1
  16. package/dist/behaviors/ai-feedback.mjs +1036 -126
  17. package/dist/behaviors/ai-panel.d.mts +10 -10
  18. package/dist/behaviors/ai-panel.mjs +1285 -266
  19. package/dist/behaviors/ai-provider.d.mts +1 -1
  20. package/dist/behaviors/ai-provider.mjs +1004 -101
  21. package/dist/behaviors/ai-threads.d.mts +1 -1
  22. package/dist/behaviors/ai-threads.mjs +1069 -154
  23. package/dist/behaviors/ai-tool.d.mts +3 -3
  24. package/dist/behaviors/ai-tool.mjs +2087 -413
  25. package/dist/behaviors/ai-tools.d.mts +89 -16
  26. package/dist/behaviors/ai-tools.mjs +5365 -380
  27. package/dist/behaviors/autocomplete.d.mts +53 -0
  28. package/dist/behaviors/autocomplete.mjs +1601 -0
  29. package/dist/behaviors/back-top.d.mts +1 -1
  30. package/dist/behaviors/back-top.mjs +952 -14
  31. package/dist/behaviors/carousel.d.mts +1 -1
  32. package/dist/behaviors/carousel.mjs +914 -12
  33. package/dist/behaviors/cascader.d.mts +48 -0
  34. package/dist/behaviors/cascader.mjs +1867 -0
  35. package/dist/behaviors/charts.d.mts +72 -8
  36. package/dist/behaviors/charts.mjs +1953 -272
  37. package/dist/behaviors/code-block.d.mts +36 -0
  38. package/dist/behaviors/code-block.mjs +1619 -0
  39. package/dist/behaviors/command-palette.d.mts +9 -6
  40. package/dist/behaviors/command-palette.mjs +164 -62
  41. package/dist/behaviors/context-menu.d.mts +10 -9
  42. package/dist/behaviors/context-menu.mjs +1113 -44
  43. package/dist/behaviors/controls.d.mts +21 -21
  44. package/dist/behaviors/controls.mjs +1024 -134
  45. package/dist/behaviors/copy.d.mts +21 -2
  46. package/dist/behaviors/copy.mjs +1207 -42
  47. package/dist/behaviors/datatable.d.mts +55 -5
  48. package/dist/behaviors/datatable.mjs +2033 -212
  49. package/dist/behaviors/date-picker.d.mts +0 -1
  50. package/dist/behaviors/date-picker.mjs +1341 -293
  51. package/dist/behaviors/design.d.mts +54 -0
  52. package/dist/behaviors/design.mjs +109 -0
  53. package/dist/behaviors/dropdown.d.mts +5 -6
  54. package/dist/behaviors/dropdown.mjs +262 -110
  55. package/dist/behaviors/events.d.mts +127 -10
  56. package/dist/behaviors/events.mjs +58 -3
  57. package/dist/behaviors/feedback.d.mts +30 -0
  58. package/dist/behaviors/feedback.mjs +296 -0
  59. package/dist/behaviors/focus.d.mts +8 -0
  60. package/dist/behaviors/focus.mjs +24 -0
  61. package/dist/behaviors/form-validate.d.mts +111 -0
  62. package/dist/behaviors/form-validate.mjs +1746 -0
  63. package/dist/behaviors/i18n.d.mts +790 -0
  64. package/dist/behaviors/i18n.mjs +1713 -0
  65. package/dist/behaviors/icons.d.mts +93 -0
  66. package/dist/behaviors/icons.mjs +113 -0
  67. package/dist/behaviors/input.d.mts +9 -1
  68. package/dist/behaviors/input.mjs +1059 -60
  69. package/dist/behaviors/kb-access.d.mts +3 -3
  70. package/dist/behaviors/kb-access.mjs +2135 -239
  71. package/dist/behaviors/kb-acl.d.mts +8 -8
  72. package/dist/behaviors/kb-acl.mjs +1120 -179
  73. package/dist/behaviors/kb-answer.d.mts +2 -2
  74. package/dist/behaviors/kb-answer.mjs +2120 -435
  75. package/dist/behaviors/kb-audit.d.mts +3 -3
  76. package/dist/behaviors/kb-audit.mjs +1077 -154
  77. package/dist/behaviors/kb-canvas.d.mts +3 -3
  78. package/dist/behaviors/kb-canvas.mjs +1101 -177
  79. package/dist/behaviors/kb-chain.d.mts +2 -2
  80. package/dist/behaviors/kb-chain.mjs +1023 -100
  81. package/dist/behaviors/kb-checkpoint.d.mts +3 -3
  82. package/dist/behaviors/kb-checkpoint.mjs +1320 -169
  83. package/dist/behaviors/kb-chunks.d.mts +2 -2
  84. package/dist/behaviors/kb-chunks.mjs +1153 -213
  85. package/dist/behaviors/kb-citation.d.mts +3 -3
  86. package/dist/behaviors/kb-citation.mjs +1221 -185
  87. package/dist/behaviors/kb-clarify.d.mts +2 -2
  88. package/dist/behaviors/kb-clarify.mjs +1059 -130
  89. package/dist/behaviors/kb-conflict.d.mts +2 -2
  90. package/dist/behaviors/kb-conflict.mjs +1042 -119
  91. package/dist/behaviors/kb-connector.d.mts +2 -2
  92. package/dist/behaviors/kb-connector.mjs +1105 -176
  93. package/dist/behaviors/kb-core.d.mts +7 -2
  94. package/dist/behaviors/kb-core.mjs +1078 -162
  95. package/dist/behaviors/kb-eval.d.mts +2 -2
  96. package/dist/behaviors/kb-eval.mjs +1977 -144
  97. package/dist/behaviors/kb-explain.d.mts +3 -3
  98. package/dist/behaviors/kb-explain.mjs +1037 -104
  99. package/dist/behaviors/kb-filter.d.mts +2 -2
  100. package/dist/behaviors/kb-filter.mjs +2014 -178
  101. package/dist/behaviors/kb-gap.d.mts +3 -3
  102. package/dist/behaviors/kb-gap.mjs +1044 -121
  103. package/dist/behaviors/kb-hittest.d.mts +3 -3
  104. package/dist/behaviors/kb-hittest.mjs +1095 -151
  105. package/dist/behaviors/kb-metadata.mjs +1058 -130
  106. package/dist/behaviors/kb-passage.d.mts +4 -4
  107. package/dist/behaviors/kb-passage.mjs +1102 -161
  108. package/dist/behaviors/kb-pipeline.d.mts +4 -4
  109. package/dist/behaviors/kb-pipeline.mjs +1083 -162
  110. package/dist/behaviors/kb-qa.mjs +1089 -160
  111. package/dist/behaviors/kb-rerank.d.mts +2 -2
  112. package/dist/behaviors/kb-rerank.mjs +1048 -114
  113. package/dist/behaviors/kb-retrieval.d.mts +2 -2
  114. package/dist/behaviors/kb-retrieval.mjs +2079 -226
  115. package/dist/behaviors/kb-review.d.mts +2 -2
  116. package/dist/behaviors/kb-review.mjs +1996 -159
  117. package/dist/behaviors/kb-sandbox.d.mts +3 -3
  118. package/dist/behaviors/kb-sandbox.mjs +1033 -105
  119. package/dist/behaviors/kb-segment.d.mts +2 -2
  120. package/dist/behaviors/kb-segment.mjs +1112 -179
  121. package/dist/behaviors/kb-select.d.mts +24 -0
  122. package/dist/behaviors/kb-select.mjs +1995 -0
  123. package/dist/behaviors/kb-sources.d.mts +3 -3
  124. package/dist/behaviors/kb-sources.mjs +1085 -170
  125. package/dist/behaviors/kb-sql.d.mts +3 -3
  126. package/dist/behaviors/kb-sql.mjs +1144 -226
  127. package/dist/behaviors/kb-trace.d.mts +3 -3
  128. package/dist/behaviors/kb-trace.mjs +1051 -131
  129. package/dist/behaviors/kb-visibility.d.mts +2 -2
  130. package/dist/behaviors/kb-visibility.mjs +1087 -158
  131. package/dist/behaviors/kb-who-can.d.mts +2 -2
  132. package/dist/behaviors/kb-who-can.mjs +1980 -137
  133. package/dist/behaviors/mentions.d.mts +93 -0
  134. package/dist/behaviors/mentions.mjs +2153 -0
  135. package/dist/behaviors/modal.d.mts +4 -3
  136. package/dist/behaviors/modal.mjs +1056 -33
  137. package/dist/behaviors/nav.d.mts +1 -1
  138. package/dist/behaviors/nav.mjs +6 -6
  139. package/dist/behaviors/notification.d.mts +16 -8
  140. package/dist/behaviors/notification.mjs +1629 -268
  141. package/dist/behaviors/panel.d.mts +4 -0
  142. package/dist/behaviors/panel.mjs +995 -0
  143. package/dist/behaviors/popover.d.mts +28 -5
  144. package/dist/behaviors/popover.mjs +225 -24
  145. package/dist/behaviors/scroll-area.d.mts +17 -0
  146. package/dist/behaviors/scroll-area.mjs +59 -0
  147. package/dist/behaviors/select.d.mts +5 -2
  148. package/dist/behaviors/select.mjs +1416 -117
  149. package/dist/behaviors/sidebar.d.mts +1 -1
  150. package/dist/behaviors/sidebar.mjs +13 -13
  151. package/dist/behaviors/slider.d.mts +1 -1
  152. package/dist/behaviors/slider.mjs +12 -12
  153. package/dist/behaviors/split-pane.d.mts +1 -1
  154. package/dist/behaviors/split-pane.mjs +9 -7
  155. package/dist/behaviors/suggestions.d.mts +27 -0
  156. package/dist/behaviors/suggestions.mjs +1090 -0
  157. package/dist/behaviors/svg-parse.d.mts +14 -0
  158. package/dist/behaviors/svg-parse.mjs +37 -0
  159. package/dist/behaviors/tabs.d.mts +2 -2
  160. package/dist/behaviors/tabs.mjs +35 -25
  161. package/dist/behaviors/tag-input.d.mts +23 -5
  162. package/dist/behaviors/tag-input.mjs +1360 -104
  163. package/dist/behaviors/theme-switcher.d.mts +24 -0
  164. package/dist/behaviors/theme-switcher.mjs +1996 -0
  165. package/dist/behaviors/theme.d.mts +15 -8
  166. package/dist/behaviors/theme.mjs +406 -30
  167. package/dist/behaviors/toast.d.mts +24 -25
  168. package/dist/behaviors/toast.mjs +1267 -88
  169. package/dist/behaviors/tooltip.d.mts +4 -0
  170. package/dist/behaviors/tooltip.mjs +378 -0
  171. package/dist/behaviors/tree-select.d.mts +69 -0
  172. package/dist/behaviors/tree-select.mjs +1921 -0
  173. package/dist/behaviors/tree.d.mts +1 -1
  174. package/dist/behaviors/tree.mjs +18 -18
  175. package/dist/behaviors/upload.d.mts +3 -2
  176. package/dist/behaviors/upload.mjs +1077 -66
  177. package/dist/behaviors/url-safety.d.mts +8 -0
  178. package/dist/behaviors/url-safety.mjs +11 -0
  179. package/dist/cli.mjs +5 -6
  180. package/dist/components/accordion.d.mts +2 -0
  181. package/dist/components/ai-branch.d.mts +2 -0
  182. package/dist/components/ai-chat.css +682 -582
  183. package/dist/components/ai-chat.d.mts +2 -0
  184. package/dist/components/ai-composer.d.mts +2 -0
  185. package/dist/components/ai-context.d.mts +2 -0
  186. package/dist/components/ai-context.mjs +1 -0
  187. package/dist/components/ai-diff.css +153 -132
  188. package/dist/components/ai-diff.d.mts +2 -0
  189. package/dist/components/ai-feedback.d.mts +2 -0
  190. package/dist/components/ai-files.d.mts +2 -0
  191. package/dist/components/ai-message.d.mts +2 -0
  192. package/dist/components/ai-panel.css +353 -343
  193. package/dist/components/ai-reasoning.d.mts +2 -0
  194. package/dist/components/ai-subagent.d.mts +2 -0
  195. package/dist/components/ai-subagent.mjs +1 -0
  196. package/dist/components/ai-threads.d.mts +2 -0
  197. package/dist/components/ai-todo.d.mts +2 -0
  198. package/dist/components/ai-todo.mjs +1 -0
  199. package/dist/components/ai-tool-call.d.mts +2 -0
  200. package/dist/components/ai-tool-call.mjs +1 -0
  201. package/dist/components/ai-tool.css +397 -242
  202. package/dist/components/ai-usage.d.mts +2 -0
  203. package/dist/components/alert.d.mts +2 -0
  204. package/dist/components/autocomplete.css +61 -0
  205. package/dist/components/autocomplete.d.mts +2 -0
  206. package/dist/components/autocomplete.mjs +3 -0
  207. package/dist/components/avatar.d.mts +2 -0
  208. package/dist/components/back-top.css +74 -40
  209. package/dist/components/back-top.d.mts +2 -0
  210. package/dist/components/badge.css +44 -41
  211. package/dist/components/badge.d.mts +2 -0
  212. package/dist/components/breadcrumb.css +85 -46
  213. package/dist/components/breadcrumb.d.mts +2 -0
  214. package/dist/components/btn.css +105 -94
  215. package/dist/components/btn.d.mts +2 -0
  216. package/dist/components/card.css +124 -113
  217. package/dist/components/card.d.mts +2 -0
  218. package/dist/components/carousel.d.mts +2 -0
  219. package/dist/components/cascader.css +332 -0
  220. package/dist/components/cascader.d.mts +2 -0
  221. package/dist/components/cascader.mjs +3 -0
  222. package/dist/components/chart-area.css +54 -2
  223. package/dist/components/chart-area.d.mts +2 -0
  224. package/dist/components/chart-bar.css +147 -38
  225. package/dist/components/chart-bar.d.mts +2 -0
  226. package/dist/components/chart-calendar.d.mts +2 -0
  227. package/dist/components/chart-gauge.css +36 -13
  228. package/dist/components/chart-gauge.d.mts +2 -0
  229. package/dist/components/chart-graph.css +35 -20
  230. package/dist/components/chart-graph.d.mts +2 -0
  231. package/dist/components/chart-heatmap.css +67 -39
  232. package/dist/components/chart-heatmap.d.mts +2 -0
  233. package/dist/components/chart-line.css +62 -3
  234. package/dist/components/chart-line.d.mts +2 -0
  235. package/dist/components/chart-map.d.mts +2 -0
  236. package/dist/components/chart-pie.css +38 -6
  237. package/dist/components/chart-pie.d.mts +2 -0
  238. package/dist/components/chart-radar.css +57 -5
  239. package/dist/components/chart-radar.d.mts +2 -0
  240. package/dist/components/chart-scatter.css +47 -7
  241. package/dist/components/chart-scatter.d.mts +2 -0
  242. package/dist/components/chart-sparkline.css +25 -2
  243. package/dist/components/chart-sparkline.d.mts +2 -0
  244. package/dist/components/chart-stack.css +27 -13
  245. package/dist/components/chart-stack.d.mts +2 -0
  246. package/dist/components/charts.css +220 -84
  247. package/dist/components/charts.d.mts +2 -0
  248. package/dist/components/code-block.css +420 -0
  249. package/dist/components/code-block.d.mts +2 -0
  250. package/dist/components/code-block.mjs +4 -0
  251. package/dist/components/command-palette.css +150 -122
  252. package/dist/components/command-palette.d.mts +2 -0
  253. package/dist/components/content.css +274 -263
  254. package/dist/components/context-menu.d.mts +2 -0
  255. package/dist/components/copy.css +73 -45
  256. package/dist/components/copy.d.mts +2 -0
  257. package/dist/components/datatable.css +457 -202
  258. package/dist/components/datatable.d.mts +2 -0
  259. package/dist/components/date-picker.css +136 -105
  260. package/dist/components/date-picker.d.mts +2 -0
  261. package/dist/components/desc.d.mts +2 -0
  262. package/dist/components/dropdown.d.mts +2 -0
  263. package/dist/components/empty.css +72 -69
  264. package/dist/components/empty.d.mts +2 -0
  265. package/dist/components/feedback.css +211 -191
  266. package/dist/components/form-validate.css +134 -0
  267. package/dist/components/form-validate.d.mts +2 -0
  268. package/dist/components/form-validate.mjs +3 -0
  269. package/dist/components/form.css +157 -131
  270. package/dist/components/form.d.mts +2 -0
  271. package/dist/components/icon.css +113 -0
  272. package/dist/components/icon.d.mts +2 -0
  273. package/dist/components/icon.mjs +3 -0
  274. package/dist/components/input.css +163 -108
  275. package/dist/components/input.d.mts +2 -0
  276. package/dist/components/kb-access.d.mts +2 -0
  277. package/dist/components/kb-acl.d.mts +2 -0
  278. package/dist/components/kb-agent.css +300 -206
  279. package/dist/components/kb-answer.d.mts +2 -0
  280. package/dist/components/kb-audit.d.mts +2 -0
  281. package/dist/components/kb-canvas.d.mts +2 -0
  282. package/dist/components/kb-chain.d.mts +2 -0
  283. package/dist/components/kb-checkpoint.d.mts +2 -0
  284. package/dist/components/kb-chunks.d.mts +2 -0
  285. package/dist/components/kb-citation.d.mts +2 -0
  286. package/dist/components/kb-clarify.d.mts +2 -0
  287. package/dist/components/kb-conflict.d.mts +2 -0
  288. package/dist/components/kb-connector.d.mts +2 -0
  289. package/dist/components/kb-data.css +431 -315
  290. package/dist/components/kb-eval.d.mts +2 -0
  291. package/dist/components/kb-explain.d.mts +2 -0
  292. package/dist/components/kb-filter.d.mts +2 -0
  293. package/dist/components/kb-gap.d.mts +2 -0
  294. package/dist/components/kb-ground.css +333 -229
  295. package/dist/components/kb-hittest.d.mts +2 -0
  296. package/dist/components/kb-ingest.css +613 -434
  297. package/dist/components/kb-metadata.d.mts +2 -0
  298. package/dist/components/kb-ops.css +422 -302
  299. package/dist/components/kb-passage.d.mts +2 -0
  300. package/dist/components/kb-perm.css +374 -314
  301. package/dist/components/kb-pipeline.d.mts +2 -0
  302. package/dist/components/kb-qa.d.mts +2 -0
  303. package/dist/components/kb-rerank.d.mts +2 -0
  304. package/dist/components/kb-retrieval.d.mts +2 -0
  305. package/dist/components/kb-review.d.mts +2 -0
  306. package/dist/components/kb-sandbox.d.mts +2 -0
  307. package/dist/components/kb-search.css +653 -459
  308. package/dist/components/kb-segment.d.mts +2 -0
  309. package/dist/components/kb-sources.d.mts +2 -0
  310. package/dist/components/kb-sql.d.mts +2 -0
  311. package/dist/components/kb-trace.d.mts +2 -0
  312. package/dist/components/kb-visibility.d.mts +2 -0
  313. package/dist/components/kb-who-can.d.mts +2 -0
  314. package/dist/components/kb.css +170 -135
  315. package/dist/components/kb.d.mts +2 -0
  316. package/dist/components/kbd.d.mts +2 -0
  317. package/dist/components/layout.css +86 -83
  318. package/dist/components/layout.d.mts +2 -0
  319. package/dist/components/list.d.mts +2 -0
  320. package/dist/components/material-chinese.css +83 -0
  321. package/dist/components/material-soviet.css +86 -0
  322. package/dist/components/material.css +318 -0
  323. package/dist/components/media-card.d.mts +2 -0
  324. package/dist/components/media.css +225 -176
  325. package/dist/components/mentions.css +190 -0
  326. package/dist/components/mentions.d.mts +2 -0
  327. package/dist/components/mentions.mjs +3 -0
  328. package/dist/components/menu.css +121 -109
  329. package/dist/components/modal.css +116 -118
  330. package/dist/components/modal.d.mts +2 -0
  331. package/dist/components/nav.css +136 -129
  332. package/dist/components/nav.d.mts +2 -0
  333. package/dist/components/notification.css +247 -177
  334. package/dist/components/notification.d.mts +2 -0
  335. package/dist/components/pagination.css +62 -57
  336. package/dist/components/pagination.d.mts +2 -0
  337. package/dist/components/panel.css +70 -68
  338. package/dist/components/panel.d.mts +2 -0
  339. package/dist/components/panel.mjs +1 -0
  340. package/dist/components/pill.css +83 -72
  341. package/dist/components/pill.d.mts +2 -0
  342. package/dist/components/popover.css +80 -57
  343. package/dist/components/popover.d.mts +2 -0
  344. package/dist/components/progress.d.mts +2 -0
  345. package/dist/components/rating.d.mts +2 -0
  346. package/dist/components/result.d.mts +2 -0
  347. package/dist/components/scroll-area.css +29 -54
  348. package/dist/components/scroll-area.d.mts +2 -0
  349. package/dist/components/scroll-area.mjs +1 -0
  350. package/dist/components/segmented.css +167 -146
  351. package/dist/components/segmented.d.mts +2 -0
  352. package/dist/components/select.css +250 -191
  353. package/dist/components/select.d.mts +2 -0
  354. package/dist/components/sidebar.css +157 -143
  355. package/dist/components/sidebar.d.mts +2 -0
  356. package/dist/components/skeleton.d.mts +2 -0
  357. package/dist/components/slider.css +135 -128
  358. package/dist/components/slider.d.mts +2 -0
  359. package/dist/components/spinner.d.mts +2 -0
  360. package/dist/components/split-pane.css +120 -108
  361. package/dist/components/split-pane.d.mts +2 -0
  362. package/dist/components/stat.css +116 -109
  363. package/dist/components/stat.d.mts +2 -0
  364. package/dist/components/steps.css +114 -108
  365. package/dist/components/steps.d.mts +2 -0
  366. package/dist/components/switch.css +192 -149
  367. package/dist/components/switch.d.mts +2 -0
  368. package/dist/components/table.css +158 -112
  369. package/dist/components/table.d.mts +2 -0
  370. package/dist/components/tabs.css +143 -116
  371. package/dist/components/tabs.d.mts +2 -0
  372. package/dist/components/tag-input.css +52 -133
  373. package/dist/components/tag-input.d.mts +2 -0
  374. package/dist/components/tag.css +90 -72
  375. package/dist/components/tag.d.mts +2 -0
  376. package/dist/components/theme-switcher.css +105 -0
  377. package/dist/components/theme-switcher.d.mts +2 -0
  378. package/dist/components/theme-switcher.mjs +3 -0
  379. package/dist/components/timeline.d.mts +2 -0
  380. package/dist/components/toast.css +115 -97
  381. package/dist/components/toast.d.mts +2 -0
  382. package/dist/components/toolbar.css +47 -43
  383. package/dist/components/toolbar.d.mts +2 -0
  384. package/dist/components/tooltip.css +103 -43
  385. package/dist/components/tooltip.d.mts +2 -0
  386. package/dist/components/tooltip.mjs +1 -0
  387. package/dist/components/tree-select.css +439 -0
  388. package/dist/components/tree-select.d.mts +2 -0
  389. package/dist/components/tree-select.mjs +3 -0
  390. package/dist/components/tree.d.mts +2 -0
  391. package/dist/components/upload.css +138 -97
  392. package/dist/components/upload.d.mts +2 -0
  393. package/dist/fonts/LICENSES/ark-pixel/OFL.txt +96 -0
  394. package/dist/fonts/LICENSES/cubic-11/OFL.txt +108 -0
  395. package/dist/fonts/LICENSES/galmuri/LICENSE.txt +93 -0
  396. package/dist/fonts/OFL.txt +96 -0
  397. package/dist/fonts/README.md +14 -0
  398. package/dist/fonts/fusion-pixel-12px-zh-hans.woff2 +0 -0
  399. package/dist/index.d.mts +85 -70
  400. package/dist/index.mjs +17330 -5773
  401. package/dist/react.d.mts +91 -0
  402. package/dist/react.mjs +8307 -0
  403. package/dist/registry.json +918 -70
  404. package/dist/tokens/chinese.css +44 -0
  405. package/dist/tokens/colors.css +371 -1222
  406. package/dist/tokens/design.css +209 -0
  407. package/dist/tokens/dtcg.json +15926 -0
  408. package/dist/tokens/figma.variables.json +10779 -0
  409. package/dist/tokens/icon-masks.css +78 -0
  410. package/dist/tokens/pixel.css +53 -0
  411. package/dist/tokens/scrollbars.css +40 -0
  412. package/dist/tokens/soviet.css +44 -0
  413. package/dist/tokens/style-profiles.css +36 -547
  414. package/dist/tokens/themes.json +308 -0
  415. package/dist/tokens/tokens-studio.json +11648 -0
  416. package/dist/tokens/typography.css +21 -18
  417. package/dist/tokens.css +1783 -1806
  418. package/dist/ui.css +14796 -10750
  419. package/dist/vue.d.mts +344 -0
  420. package/dist/vue.mjs +7876 -0
  421. package/docs/spec/ai-input-experience.md +75 -0
  422. package/docs/spec/ai-native.md +238 -147
  423. package/docs/spec/design-philosophy.md +189 -0
  424. package/docs/spec/design-primitives.md +196 -0
  425. package/docs/spec/kb-family.md +147 -115
  426. package/docs/spec/scrollbars.md +46 -0
  427. package/package.json +56 -8
  428. package/dist/retro-effects.css +0 -255
  429. package/dist/tokens/retro-effects.css +0 -255
  430. package/docs/research/2026-10-03-ai-kb-components.md +0 -392
  431. package/docs/research/2026-10-03-kb-permissions.md +0 -992
@@ -1,172 +1,173 @@
1
+ @layer icen.components {
1
2
  /*
2
3
  * @icen.ai/ui — Component: ai-panel(AI 任务面板族:todo / context / usage,与 behaviors/ai-panel.ts 配套)
3
4
  *
4
5
  * 完整 DOM 契约(类名与规格 §4.8/§4.9/§4.10 一致):
5
- * <div class="ai-todo" [.is-complete] [data-ai-todo-interactive]>
6
- * <div class="ai-todo-head">
7
- * <span class="ai-todo-progress">2/5</span>
8
- * <div class="ai-todo-bar" role="progressbar" …><i style="width:40%"></i></div>
6
+ * <div class="icen-ai-todo" [.is-complete] [data-icen-ai-todo-interactive]>
7
+ * <div class="icen-ai-todo-head">
8
+ * <span class="icen-ai-todo-progress">2/5</span>
9
+ * <div class="icen-ai-todo-bar" role="progressbar" …><i style="width:40%"></i></div>
9
10
  * </div>
10
- * <div class="ai-todo-item is-pending|running|streaming|approval|done|error|cancelled
11
- * [role="button" tabindex="0"]" data-index="0">
12
- * <span class="ai-item-status"></span> <!-- 状态点,纯 CSS 由 .is-* 驱动 -->
13
- * <span class="ai-todo-text">实现登录页</span>
14
- * <span class="ai-todo-active">正在实现登录页…</span> <!-- is-running 时替换 text(CSS 驱动) -->
11
+ * <div class="icen-ai-todo-item is-pending|running|streaming|approval|done|error|cancelled
12
+ * [role="button" tabindex="0"]" data-icen-index="0">
13
+ * <span class="icen-ai-item-status"></span> <!-- 状态点,纯 CSS 由 .is-* 驱动 -->
14
+ * <span class="icen-ai-todo-text">实现登录页</span>
15
+ * <span class="icen-ai-todo-active">正在实现登录页…</span> <!-- is-running 时替换 text(CSS 驱动) -->
15
16
  * </div>
16
17
  * </div>
17
18
  *
18
- * <div class="ai-usage">
19
- * <div class="ai-usage-bar" role="img" aria-label="…">
20
- * <i class="ai-usage-seg ai-usage-seg--input|output|cache-read|cache-write|reasoning" style="width:35%"></i>…
19
+ * <div class="icen-ai-usage">
20
+ * <div class="icen-ai-usage-bar" role="img" aria-label="…">
21
+ * <i class="icen-ai-usage-seg icen-ai-usage-seg--input|output|cache-read|cache-write|reasoning" style="width:35%"></i>…
21
22
  * </div>
22
- * <div class="ai-usage-legend">
23
- * <span class="ai-usage-legend-item">
24
- * <i class="ai-usage-dot ai-usage-seg--input"></i>
25
- * <span class="ai-usage-legend-label">输入</span> <span class="ai-usage-legend-value">35k</span>
23
+ * <div class="icen-ai-usage-legend">
24
+ * <span class="icen-ai-usage-legend-item">
25
+ * <i class="icen-ai-usage-dot icen-ai-usage-seg--input"></i>
26
+ * <span class="icen-ai-usage-legend-label">输入</span> <span class="icen-ai-usage-legend-value">35k</span>
26
27
  * </span>…
27
28
  * </div>
28
- * <div class="ai-usage-total">82k / 200k · 41%</div>
29
+ * <div class="icen-ai-usage-total">82k / 200k · 41%</div>
29
30
  * </div>
30
31
  *
31
- * <aside class="ai-context [.ai-context--inline]" hidden role="dialog" aria-label="上下文">
32
- * <div class="ai-context-head"><span>上下文</span>
33
- * <button type="button" data-ai-context-close aria-label="关闭">×</button></div>
34
- * <section class="ai-context-section"><h3>…</h3>
35
- * <div class="ai-context-section-body">…renderAiContext 产物…</div> <!-- 可选包裹,亦可直接放内容 -->
32
+ * <aside class="icen-ai-context [.icen-ai-context--inline]" hidden role="dialog" aria-label="上下文">
33
+ * <div class="icen-ai-context-head"><span>上下文</span>
34
+ * <button type="button" data-icen-ai-context-close aria-label="关闭">×</button></div>
35
+ * <section class="icen-ai-context-section"><h3>…</h3>
36
+ * <div class="icen-ai-context-section-body">…renderAiContext 产物…</div> <!-- 可选包裹,亦可直接放内容 -->
36
37
  * </section>…
37
38
  * </aside>
38
39
  *
39
- * .ai-item 行(MCP / Skills,规格 §2 基元):
40
- * <div class="ai-item is-done|is-error" style="--ai-item-tint: var(--token-accent)">
41
- * <span class="ai-item-icon">…svg…</span>
42
- * <span class="ai-item-main">
43
- * <span class="ai-item-title">github</span><span class="ai-item-sub">…</span>
40
+ * .icen-ai-item 行(MCP / Skills,规格 §2 基元):
41
+ * <div class="icen-ai-item is-done|is-error" style="--ai-item-tint: var(--icen-token-accent)">
42
+ * <span class="icen-ai-item-icon">…svg…</span>
43
+ * <span class="icen-ai-item-main">
44
+ * <span class="icen-ai-item-title">github</span><span class="icen-ai-item-sub">…</span>
44
45
  * </span>
45
- * <span class="ai-item-side"><span class="ai-item-status"></span><span class="ai-item-meta">12 工具</span></span>
46
+ * <span class="icen-ai-item-side"><span class="icen-ai-item-status"></span><span class="icen-ai-item-meta">12 工具</span></span>
46
47
  * </div>
47
48
  *
48
49
  * 依赖说明:
49
- * - .ai-item 完整版在 ai-tool.css(S2)。此处按任务约定重新声明最小骨架(含 --ai-item-tint
50
+ * - .icen-ai-item 完整版在 ai-tool.css(S2)。此处按任务约定重新声明最小骨架(含 --ai-item-tint
50
51
  * 局部变量与状态点),保证 ai-panel.css 单独引入时 todo/context 可用;两边类名/语义一致,
51
52
  * 同页面共存时后加载者覆盖同款属性,视觉不冲突。
52
53
  * - keyframes ai-status-pulse 为组件局部定义(等同 pill.css 的 pill-pulse),
53
54
  * 时长走 var(--pill-pulse-duration, 1.5s):pill.css 在场时与其同步,否则自洽。
54
- * - blink keyframes 来自 tokens/colors.css(.animate-blink 同款,共享复用)。
55
- * - base.css:--z-chrome / --icen-tx-* / --icen-ring。只消费 --token-* / --density-* / --radius-*。
55
+ * - icen-blink keyframes 来自 base.css(共享复用)。
56
+ * - base.css:--icen-z-chrome / --icen-tx-* / --icen-ring。只消费 --icen-token-* / --icen-density-* / --icen-radius-*。
56
57
  */
57
58
 
58
- /* ══════════════ .ai-item 最小基元(自包含,兼容 ai-tool.css 完整版) ══════════════ */
59
+ /* ══════════════ .icen-ai-item 最小基元(自包含,兼容 ai-tool.css 完整版) ══════════════ */
59
60
 
60
- .ai-item {
61
- --ai-item-tint: var(--token-accent);
61
+ .icen-ai-item {
62
+ --ai-item-tint: var(--icen-token-accent);
62
63
  display: flex;
63
64
  align-items: center;
64
- gap: var(--density-space-sm);
65
- padding: var(--density-space-xs) var(--density-space-sm);
66
- border-radius: var(--radius-sm);
67
- font-size: var(--density-font-size-sm);
65
+ gap: var(--icen-density-space-sm);
66
+ padding: var(--icen-density-space-xs) var(--icen-density-space-sm);
67
+ border-radius: var(--icen-radius-sm);
68
+ font-size: var(--icen-density-font-size-sm);
68
69
  min-width: 0;
69
70
  align-self: stretch; /* 宽度自稳定:宿主 flex/grid 居中时不 shrink-wrap */
70
71
  }
71
72
 
72
- .ai-item-icon {
73
+ .icen-ai-item-icon {
73
74
  flex-shrink: 0;
74
75
  display: inline-flex;
75
76
  color: var(--ai-item-tint);
76
77
  }
77
- .ai-item-icon svg {
78
+ .icen-ai-item-icon svg {
78
79
  width: 15px;
79
80
  height: 15px;
80
81
  }
81
82
 
82
- .ai-item-main {
83
+ .icen-ai-item-main {
83
84
  flex: 1;
84
85
  min-width: 0;
85
86
  display: flex;
86
87
  flex-direction: column;
87
88
  gap: 1px;
88
89
  }
89
- .ai-item-title {
90
- color: var(--token-text);
90
+ .icen-ai-item-title {
91
+ color: var(--icen-token-text);
91
92
  line-height: 1.4;
92
93
  overflow: hidden;
93
94
  text-overflow: ellipsis;
94
95
  white-space: nowrap;
95
96
  }
96
- .ai-item-sub {
97
- font-size: var(--density-font-size-xs);
98
- color: var(--token-text-muted);
97
+ .icen-ai-item-sub {
98
+ font-size: var(--icen-density-font-size-xs);
99
+ color: var(--icen-token-text-muted);
99
100
  overflow: hidden;
100
101
  text-overflow: ellipsis;
101
102
  white-space: nowrap;
102
103
  }
103
104
 
104
- .ai-item-side {
105
+ .icen-ai-item-side {
105
106
  flex-shrink: 0;
106
107
  display: inline-flex;
107
108
  align-items: center;
108
- gap: var(--density-space-xs);
109
+ gap: var(--icen-density-space-xs);
109
110
  }
110
- .ai-item-meta {
111
- font-size: var(--density-font-size-xs);
112
- color: var(--token-text-faint);
111
+ .icen-ai-item-meta {
112
+ font-size: var(--icen-density-font-size-xs);
113
+ color: var(--icen-token-text-faint);
113
114
  font-variant-numeric: tabular-nums;
114
115
  }
115
116
 
116
- /* ── 状态点 .ai-item-status:纯 CSS 圆点,由 .is-* 驱动(ai-item 与 ai-todo-item 共用) ── */
117
+ /* ── 状态点 .icen-ai-item-status:纯 CSS 圆点,由 .is-* 驱动(ai-item 与 ai-todo-item 共用) ── */
117
118
 
118
- .ai-item-status {
119
+ .icen-ai-item-status {
119
120
  flex-shrink: 0;
120
121
  width: 8px;
121
122
  height: 8px;
122
- border-radius: var(--radius-full);
123
- border: 1.5px solid var(--token-text-faint);
123
+ border-radius: var(--icen-radius-full);
124
+ border: 1.5px solid var(--icen-token-text-faint);
124
125
  background: transparent;
125
126
  }
126
127
 
127
128
  /* pending:faint 空心点(默认态即空心) */
128
- .ai-item.is-pending > .ai-item-status,
129
- .ai-todo-item.is-pending > .ai-item-status { }
129
+ .icen-ai-item.is-pending > .icen-ai-item-status,
130
+ .icen-ai-todo-item.is-pending > .icen-ai-item-status { }
130
131
 
131
132
  /* running / streaming:accent 脉冲点 */
132
- .ai-item.is-running > .ai-item-status,
133
- .ai-todo-item.is-running > .ai-item-status,
134
- .ai-item.is-streaming > .ai-item-status,
135
- .ai-todo-item.is-streaming > .ai-item-status {
136
- border-color: var(--token-accent);
137
- background: var(--token-accent);
133
+ .icen-ai-item.is-running > .icen-ai-item-status,
134
+ .icen-ai-todo-item.is-running > .icen-ai-item-status,
135
+ .icen-ai-item.is-streaming > .icen-ai-item-status,
136
+ .icen-ai-todo-item.is-streaming > .icen-ai-item-status {
137
+ border-color: var(--icen-token-accent);
138
+ background: var(--icen-token-accent);
138
139
  animation: ai-status-pulse var(--pill-pulse-duration, 1.5s) ease-in-out infinite;
139
140
  }
140
141
 
141
142
  /* approval:warning 点 */
142
- .ai-item.is-approval > .ai-item-status,
143
- .ai-todo-item.is-approval > .ai-item-status {
144
- border-color: var(--token-warning);
145
- background: var(--token-warning);
143
+ .icen-ai-item.is-approval > .icen-ai-item-status,
144
+ .icen-ai-todo-item.is-approval > .icen-ai-item-status {
145
+ border-color: var(--icen-token-warning);
146
+ background: var(--icen-token-warning);
146
147
  }
147
148
 
148
149
  /* done:success 点 */
149
- .ai-item.is-done > .ai-item-status,
150
- .ai-todo-item.is-done > .ai-item-status {
151
- border-color: var(--token-success);
152
- background: var(--token-success);
150
+ .icen-ai-item.is-done > .icen-ai-item-status,
151
+ .icen-ai-todo-item.is-done > .icen-ai-item-status {
152
+ border-color: var(--icen-token-success);
153
+ background: var(--icen-token-success);
153
154
  }
154
155
 
155
156
  /* error:error 点 */
156
- .ai-item.is-error > .ai-item-status,
157
- .ai-todo-item.is-error > .ai-item-status {
158
- border-color: var(--token-error);
159
- background: var(--token-error);
157
+ .icen-ai-item.is-error > .icen-ai-item-status,
158
+ .icen-ai-todo-item.is-error > .icen-ai-item-status {
159
+ border-color: var(--icen-token-error);
160
+ background: var(--icen-token-error);
160
161
  }
161
162
 
162
163
  /* cancelled:faint 实心点 + 标题删除线(规格 §1) */
163
- .ai-item.is-cancelled > .ai-item-status,
164
- .ai-todo-item.is-cancelled > .ai-item-status {
165
- border-color: var(--token-text-faint);
166
- background: var(--token-text-faint);
164
+ .icen-ai-item.is-cancelled > .icen-ai-item-status,
165
+ .icen-ai-todo-item.is-cancelled > .icen-ai-item-status {
166
+ border-color: var(--icen-token-text-faint);
167
+ background: var(--icen-token-text-faint);
167
168
  }
168
- .ai-item.is-cancelled .ai-item-title,
169
- .ai-todo-item.is-cancelled .ai-todo-text {
169
+ .icen-ai-item.is-cancelled .icen-ai-item-title,
170
+ .icen-ai-todo-item.is-cancelled .icen-ai-todo-text {
170
171
  text-decoration: line-through;
171
172
  }
172
173
 
@@ -178,71 +179,71 @@
178
179
 
179
180
  /* ══════════════ ai-todo · 任务清单(§4.8) ══════════════ */
180
181
 
181
- .ai-todo {
182
+ .icen-ai-todo {
182
183
  display: flex;
183
184
  flex-direction: column;
184
- gap: var(--density-space-xs);
185
- font-size: var(--density-font-size-sm);
185
+ gap: var(--icen-density-space-xs);
186
+ font-size: var(--icen-density-font-size-sm);
186
187
  min-width: 0;
187
188
  align-self: stretch; /* 输出容器宽度自稳定 */
188
189
  }
189
190
 
190
- .ai-todo-head {
191
+ .icen-ai-todo-head {
191
192
  display: flex;
192
193
  align-items: center;
193
- gap: var(--density-space-sm);
194
+ gap: var(--icen-density-space-sm);
194
195
  min-width: 0;
195
196
  }
196
197
 
197
- .ai-todo-progress {
198
+ .icen-ai-todo-progress {
198
199
  flex-shrink: 0;
199
- font-size: var(--density-font-size-xs);
200
- color: var(--token-text-muted);
200
+ font-size: var(--icen-density-font-size-xs);
201
+ color: var(--icen-token-text-muted);
201
202
  font-variant-numeric: tabular-nums;
202
203
  }
203
204
 
204
205
  /* 进度条:feedback progress 视觉(token 消费) */
205
- .ai-todo-bar {
206
+ .icen-ai-todo-bar {
206
207
  flex: 1;
207
208
  height: 4px;
208
- border-radius: var(--radius-full);
209
+ border-radius: var(--icen-radius-full);
209
210
  overflow: hidden;
210
- background: color-mix(in srgb, var(--token-line-soft) 40%, transparent);
211
+ background: var(--icen-token-fill-2);
211
212
  }
212
- .ai-todo-bar > i {
213
+ .icen-ai-todo-bar > i {
213
214
  display: block;
214
215
  height: 100%;
215
- border-radius: var(--radius-full);
216
- background: var(--token-accent);
216
+ border-radius: var(--icen-radius-full);
217
+ background: var(--icen-token-accent-strong);
217
218
  transition: width var(--icen-tx-slow);
218
219
  }
219
- .ai-todo.is-complete .ai-todo-bar > i {
220
- background: var(--token-success);
220
+ .icen-ai-todo.is-complete .icen-ai-todo-bar > i {
221
+ background: var(--icen-token-success);
221
222
  }
222
223
 
223
- .ai-todo-item {
224
+ .icen-ai-todo-item {
224
225
  display: flex;
225
226
  align-items: center;
226
- gap: var(--density-space-sm);
227
- padding: 3px var(--density-space-xs);
228
- border-radius: var(--radius-xs);
227
+ gap: var(--icen-density-space-sm);
228
+ padding: 3px var(--icen-density-space-xs);
229
+ border-radius: var(--icen-radius-xs);
229
230
  min-width: 0;
230
231
  }
231
232
 
232
233
  /* 交互模式(initAiTodo 升级 role=button) */
233
- .ai-todo-item[role='button'] {
234
+ .icen-ai-todo-item[role='button'] {
234
235
  cursor: pointer;
235
236
  transition: background-color var(--icen-tx-fast);
236
237
  }
237
- .ai-todo-item[role='button']:hover {
238
- background: var(--token-fill-1);
238
+ .icen-ai-todo-item[role='button']:hover {
239
+ background: var(--icen-token-fill-hover);
239
240
  }
240
- .ai-todo-item:focus-visible {
241
+ .icen-ai-todo-item:focus-visible {
241
242
  outline: none;
242
243
  box-shadow: var(--icen-ring);
243
244
  }
244
245
 
245
- .ai-todo-text {
246
+ .icen-ai-todo-text {
246
247
  min-width: 0;
247
248
  overflow: hidden;
248
249
  text-overflow: ellipsis;
@@ -250,45 +251,45 @@
250
251
  }
251
252
 
252
253
  /* activeForm:运行中替换式强调(Claude Code 模式) */
253
- .ai-todo-active {
254
+ .icen-ai-todo-active {
254
255
  display: none;
255
256
  min-width: 0;
256
257
  overflow: hidden;
257
258
  text-overflow: ellipsis;
258
259
  white-space: nowrap;
259
- color: var(--token-accent-deep);
260
+ color: var(--icen-token-accent-deep);
260
261
  }
261
- .ai-todo-item.is-running .ai-todo-text { display: none; }
262
- .ai-todo-item.is-running .ai-todo-active { display: inline; }
262
+ .icen-ai-todo-item.is-running .icen-ai-todo-text { display: none; }
263
+ .icen-ai-todo-item.is-running .icen-ai-todo-active { display: inline; }
263
264
 
264
265
  /* done/cancelled:淡化 + 删除线 */
265
- .ai-todo-item.is-done .ai-todo-text,
266
- .ai-todo-item.is-cancelled .ai-todo-text {
267
- color: var(--token-text-faint);
266
+ .icen-ai-todo-item.is-done .icen-ai-todo-text,
267
+ .icen-ai-todo-item.is-cancelled .icen-ai-todo-text {
268
+ color: var(--icen-token-text-faint);
268
269
  text-decoration: line-through;
269
270
  }
270
271
 
271
272
  /* ══════════════ ai-usage · 用量条(§4.9) ══════════════ */
272
273
 
273
- .ai-usage {
274
+ .icen-ai-usage {
274
275
  display: flex;
275
276
  flex-direction: column;
276
- gap: var(--density-space-xs);
277
- font-size: var(--density-font-size-xs);
278
- color: var(--token-text-muted);
277
+ gap: var(--icen-density-space-xs);
278
+ font-size: var(--icen-density-font-size-xs);
279
+ color: var(--icen-token-text-muted);
279
280
  min-width: 0;
280
281
  align-self: stretch; /* 输出容器宽度自稳定 */
281
282
  }
282
283
 
283
- .ai-usage-bar {
284
+ .icen-ai-usage-bar {
284
285
  display: flex;
285
286
  height: 6px;
286
- border-radius: var(--radius-full);
287
+ border-radius: var(--icen-radius-full);
287
288
  overflow: hidden;
288
- background: color-mix(in srgb, var(--token-line-soft) 40%, transparent);
289
+ background: color-mix(in srgb, var(--icen-token-line-soft) 40%, transparent);
289
290
  }
290
291
 
291
- .ai-usage-seg {
292
+ .icen-ai-usage-seg {
292
293
  display: block;
293
294
  height: 100%;
294
295
  min-width: 0;
@@ -296,41 +297,41 @@
296
297
  }
297
298
 
298
299
  /* 配色契约:input=accent / output=success / cacheRead=info / cacheWrite=warning / reasoning=faint */
299
- .ai-usage-seg--input { background: var(--token-accent); }
300
- .ai-usage-seg--output { background: var(--token-success); }
301
- .ai-usage-seg--cache-read { background: var(--token-info); }
302
- .ai-usage-seg--cache-write { background: var(--token-warning); }
303
- .ai-usage-seg--reasoning { background: var(--token-text-faint); }
300
+ .icen-ai-usage-seg--input { background: var(--icen-token-accent); }
301
+ .icen-ai-usage-seg--output { background: var(--icen-token-success); }
302
+ .icen-ai-usage-seg--cache-read { background: var(--icen-token-info); }
303
+ .icen-ai-usage-seg--cache-write { background: var(--icen-token-warning); }
304
+ .icen-ai-usage-seg--reasoning { background: var(--icen-token-text-faint); }
304
305
 
305
306
  /* 图例:色点 + 标签 + 数值(缓存分列,计费诚实) */
306
- .ai-usage-legend {
307
+ .icen-ai-usage-legend {
307
308
  display: flex;
308
309
  flex-wrap: wrap;
309
- gap: var(--density-space-xs) var(--density-space-sm);
310
+ gap: var(--icen-density-space-xs) var(--icen-density-space-sm);
310
311
  }
311
- .ai-usage-legend-item {
312
+ .icen-ai-usage-legend-item {
312
313
  display: inline-flex;
313
314
  align-items: center;
314
315
  gap: 5px;
315
316
  font-variant-numeric: tabular-nums;
316
317
  }
317
- .ai-usage-dot {
318
+ .icen-ai-usage-dot {
318
319
  flex-shrink: 0;
319
320
  width: 8px;
320
321
  height: 8px;
321
- border-radius: var(--radius-full);
322
+ border-radius: var(--icen-radius-full);
322
323
  }
323
- .ai-usage-legend-label { color: var(--token-text-muted); }
324
- .ai-usage-legend-value { color: var(--token-text); font-weight: 500; }
324
+ .icen-ai-usage-legend-label { color: var(--icen-token-text-muted); }
325
+ .icen-ai-usage-legend-value { color: var(--icen-token-text); font-weight: 500; }
325
326
 
326
- .ai-usage-total {
327
+ .icen-ai-usage-total {
327
328
  font-variant-numeric: tabular-nums;
328
- color: var(--token-text-muted);
329
+ color: var(--icen-token-text-muted);
329
330
  }
330
331
 
331
332
  /* ══════════════ ai-usage-ring · 上下文窗口环形指示器(点击弹出完整分解) ══════════════ */
332
333
 
333
- .ai-usage-ring {
334
+ .icen-ai-usage-ring {
334
335
  position: relative;
335
336
  display: inline-flex;
336
337
  align-items: center;
@@ -340,48 +341,48 @@
340
341
  padding: 0;
341
342
  border: 0;
342
343
  background: transparent;
343
- border-radius: var(--radius-full);
344
- color: var(--token-text-muted);
344
+ border-radius: var(--icen-radius-full);
345
+ color: var(--icen-token-text-muted);
345
346
  cursor: pointer;
346
347
  flex-shrink: 0;
347
348
  transition:
348
349
  color var(--icen-tx-fast),
349
350
  background-color var(--icen-tx-fast);
350
351
  }
351
- .ai-usage-ring:hover {
352
- background: var(--token-fill-1);
353
- color: var(--token-text);
352
+ .icen-ai-usage-ring:hover {
353
+ background: var(--icen-token-fill-1);
354
+ color: var(--icen-token-text);
354
355
  }
355
- .ai-usage-ring:focus-visible {
356
+ .icen-ai-usage-ring:focus-visible {
356
357
  outline: none;
357
358
  box-shadow: var(--icen-ring);
358
359
  }
359
360
 
360
- .ai-usage-ring > svg {
361
+ .icen-ai-usage-ring > svg {
361
362
  position: absolute;
362
363
  inset: 0;
363
364
  width: 100%;
364
365
  height: 100%;
365
366
  transform: rotate(-90deg); /* 12 点起笔 */
366
367
  }
367
- .ai-usage-ring-track {
368
+ .icen-ai-usage-ring-track {
368
369
  fill: none;
369
- stroke: var(--token-fill-2);
370
+ stroke: var(--icen-token-fill-2);
370
371
  stroke-width: 3;
371
372
  }
372
- .ai-usage-ring-fill {
373
+ .icen-ai-usage-ring-fill {
373
374
  fill: none;
374
- stroke: var(--token-accent);
375
+ stroke: var(--icen-token-accent);
375
376
  stroke-width: 3;
376
377
  stroke-linecap: round;
377
378
  transition:
378
379
  stroke-dasharray var(--icen-tx-slow),
379
380
  stroke var(--icen-tx-fast);
380
381
  }
381
- /* 状态档:<60% ok(accent)/ 60–85% warn / >85% hot */
382
- .ai-usage-ring.is-warn .ai-usage-ring-fill { stroke: var(--token-warning); }
383
- .ai-usage-ring.is-hot .ai-usage-ring-fill { stroke: var(--token-error); }
384
- .ai-usage-ring.is-hot {
382
+ /* 状态档:<60% ok(icen-accent)/ 60–85% warn / >85% hot */
383
+ .icen-ai-usage-ring.is-warn .icen-ai-usage-ring-fill { stroke: var(--icen-token-warning); }
384
+ .icen-ai-usage-ring.is-hot .icen-ai-usage-ring-fill { stroke: var(--icen-token-error); }
385
+ .icen-ai-usage-ring.is-hot {
385
386
  animation: ai-usage-ring-pulse var(--ai-usage-ring-pulse-duration, 1.6s) ease-in-out infinite;
386
387
  }
387
388
  @keyframes ai-usage-ring-pulse {
@@ -389,9 +390,9 @@
389
390
  50% { opacity: 0.55; }
390
391
  }
391
392
 
392
- .ai-usage-ring-pct {
393
+ .icen-ai-usage-ring-pct {
393
394
  position: relative;
394
- font-family: var(--font-mono);
395
+ font-family: var(--icen-font-mono);
395
396
  font-size: 9px;
396
397
  font-weight: 600;
397
398
  letter-spacing: -0.02em;
@@ -400,84 +401,87 @@
400
401
  }
401
402
 
402
403
  /* 大号变体(消费方变体,常驻头部大号环;behavior 不产出,由使用方手写标记) */
403
- .ai-usage-ring--lg {
404
+ .icen-ai-usage-ring--lg {
404
405
  width: 44px;
405
406
  height: 44px;
406
407
  }
407
- .ai-usage-ring--lg .ai-usage-ring-pct { font-size: 10px; }
408
+ .icen-ai-usage-ring--lg .icen-ai-usage-ring-pct { font-size: 10px; }
408
409
 
409
- /* 弹层(复用 .popover 基座,内容区只补间距) */
410
- .ai-usage-popover {
410
+ /* 弹层(复用 .icen-popover 基座,内容区只补间距) */
411
+ .icen-ai-usage-popover {
411
412
  display: flex;
412
413
  flex-direction: column;
413
- gap: var(--density-space-sm);
414
- padding: var(--density-space-md);
414
+ gap: var(--icen-density-space-sm);
415
+ padding: var(--icen-density-space-md);
415
416
  }
416
- .ai-usage-popover-title {
417
- font-size: var(--density-font-size-sm);
417
+ .icen-ai-usage-popover-title {
418
+ font-size: var(--icen-density-font-size-sm);
418
419
  font-weight: 600;
419
- color: var(--token-text);
420
+ color: var(--icen-token-text);
420
421
  }
421
422
 
422
423
  @media (prefers-reduced-motion: reduce) {
423
- .ai-usage-ring.is-hot { animation: none; }
424
- .ai-usage-ring-fill { transition: none; }
424
+ .icen-ai-usage-ring.is-hot { animation: none; }
425
+ .icen-ai-usage-ring-fill { transition: none; }
425
426
  }
426
427
 
427
428
  /* ══════════════ ai-context · 上下文抽屉(§4.10) ══════════════ */
428
429
 
429
- .ai-context {
430
+ .icen-ai-context {
430
431
  position: fixed;
431
- inset: 0 0 0 auto;
432
- width: min(360px, 92vw);
433
- z-index: var(--z-chrome);
432
+ inset-block: 0;
433
+ inset-inline-end: 0; /* 贴视口行内末端侧(LTR 右侧 / RTL 镜像左侧) */
434
+ inline-size: min(360px, 92vw);
435
+ z-index: var(--icen-z-chrome);
434
436
  display: flex;
435
437
  flex-direction: column;
436
- background: var(--token-surface);
437
- border-left: 1px solid var(--token-line-soft);
438
- box-shadow: var(--token-shadow-overlay);
439
- transform: translateX(100%);
440
- transition: transform var(--ai-context-duration, var(--duration-normal)) var(--ease-out);
438
+ background: var(--icen-token-surface);
439
+ border-inline-start: 1px solid var(--icen-token-separator);
440
+ box-shadow: var(--icen-token-shadow-overlay);
441
+ transform: translateX(100%); /* guard:allow-physical 隐藏位沿物理右缘滑出(LTR 抽屉侧),RTL 镜像规则翻为 translateX(-100%) */
442
+ transition: transform var(--ai-context-duration, var(--icen-duration-normal)) var(--icen-ease-out);
441
443
  overflow-y: auto;
442
444
  }
443
- .ai-context[hidden] {
445
+ .icen-ai-context[hidden] {
444
446
  display: none;
445
447
  }
446
- .ai-context.is-open {
448
+ .icen-ai-context.is-open {
447
449
  transform: translateX(0);
448
450
  }
449
451
 
450
452
  /* 页面流内嵌变体:不做 fixed、不滑入 */
451
- .ai-context--inline {
453
+ .icen-ai-context--inline {
452
454
  position: static;
453
455
  inset: auto;
454
456
  width: auto;
455
457
  z-index: auto;
456
458
  transform: none;
457
459
  transition: none;
458
- border: 1px solid var(--token-line-soft);
459
- border-radius: var(--radius-md);
460
- box-shadow: var(--token-shadow-elevated);
460
+ border: 1px solid var(--icen-token-separator-soft);
461
+ border-radius: var(--icen-control-radius-lg);
462
+ box-shadow: none;
461
463
  overflow-y: visible;
462
464
  }
463
465
 
464
- .ai-context-head {
466
+ .icen-ai-context-head {
465
467
  position: sticky;
466
468
  top: 0;
467
469
  z-index: 1;
468
470
  display: flex;
469
471
  align-items: center;
470
472
  justify-content: space-between;
471
- gap: var(--density-space-sm);
472
- padding: var(--density-space-sm) var(--density-space-md);
473
- background: var(--token-surface);
474
- border-bottom: 1px solid var(--token-line-soft);
475
- font-size: var(--density-font-size-sm);
473
+ gap: var(--icen-density-space-sm);
474
+ min-block-size: 42px;
475
+ padding: 8px 12px;
476
+ background: var(--icen-token-surface-chrome);
477
+ border-bottom: 1px solid var(--icen-token-separator-soft);
478
+ border-bottom: 1px solid var(--icen-token-line-soft);
479
+ font-size: var(--icen-density-font-size-sm);
476
480
  font-weight: 600;
477
- color: var(--token-text);
481
+ color: var(--icen-token-text);
478
482
  }
479
483
 
480
- .ai-context-head [data-ai-context-close] {
484
+ .icen-ai-context-head [data-icen-ai-context-close] {
481
485
  flex-shrink: 0;
482
486
  display: inline-flex;
483
487
  align-items: center;
@@ -486,9 +490,9 @@
486
490
  height: 26px;
487
491
  padding: 0;
488
492
  border: 0;
489
- border-radius: var(--radius-xs);
493
+ border-radius: var(--icen-radius-xs);
490
494
  background: none;
491
- color: var(--token-text-faint);
495
+ color: var(--icen-token-text-faint);
492
496
  font-size: 16px;
493
497
  line-height: 1;
494
498
  cursor: pointer;
@@ -496,233 +500,233 @@
496
500
  background-color var(--icen-tx-fast),
497
501
  color var(--icen-tx-fast);
498
502
  }
499
- .ai-context-head [data-ai-context-close]:hover {
500
- color: var(--token-text);
501
- background: var(--token-fill-1);
503
+ .icen-ai-context-head [data-icen-ai-context-close]:hover {
504
+ color: var(--icen-token-text);
505
+ background: var(--icen-token-fill-1);
502
506
  }
503
- .ai-context-head [data-ai-context-close]:focus-visible {
507
+ .icen-ai-context-head [data-icen-ai-context-close]:focus-visible {
504
508
  outline: none;
505
509
  box-shadow: var(--icen-ring);
506
510
  }
507
511
 
508
- .ai-context-section {
512
+ .icen-ai-context-section {
509
513
  display: flex;
510
514
  flex-direction: column;
511
- gap: var(--density-space-xs);
512
- padding: var(--density-space-sm) var(--density-space-md);
515
+ gap: var(--icen-density-space-xs);
516
+ padding: var(--icen-density-space-sm) var(--icen-density-space-md);
513
517
  min-width: 0;
514
518
  }
515
- .ai-context-section ~ .ai-context-section {
516
- border-top: 1px solid var(--token-line-soft);
519
+ .icen-ai-context-section ~ .icen-ai-context-section {
520
+ border-top: 1px solid var(--icen-token-line-soft);
517
521
  }
518
- .ai-context-section h3 {
522
+ .icen-ai-context-section h3 {
519
523
  margin: 0;
520
- font-size: var(--density-font-size-xs);
524
+ font-size: var(--icen-density-font-size-xs);
521
525
  font-weight: 600;
522
- color: var(--token-text-muted);
526
+ color: var(--icen-token-text-muted);
523
527
  }
524
- .ai-context-section-body {
528
+ .icen-ai-context-section-body {
525
529
  display: flex;
526
530
  flex-direction: column;
527
- gap: var(--density-space-xs);
531
+ gap: var(--icen-density-space-xs);
528
532
  min-width: 0;
529
533
  }
530
534
 
531
535
  /* ══════════════ ai-audit(renderAiAudit,规格 §12.2) ══════════════ */
532
536
 
533
537
  /*
534
- * <div class="ai-audit">
535
- * <div class="ai-audit-totals"><span class="ai-audit-totals-text">12 次请求 · 1 失败 · 1.2M tok · $0.42 · TTFT 240ms</span></div>
536
- * <div class="ai-audit-models">
537
- * <div class="ai-audit-model-row"><span class="ai-audit-model-name">kimi/kimi-k3</span>
538
- * <span class="ai-audit-model-meta">8 次 · 900k tok · $0.31</span></div>…
538
+ * <div class="icen-ai-audit">
539
+ * <div class="ai-audit-totals"><span class="icen-ai-audit-totals-text">12 次请求 · 1 失败 · 1.2M tok · $0.42 · TTFT 240ms</span></div>
540
+ * <div class="icen-ai-audit-models">
541
+ * <div class="icen-ai-audit-model-row"><span class="icen-ai-audit-model-name">kimi/kimi-k3</span>
542
+ * <span class="icen-ai-audit-model-meta">8 次 · 900k tok · $0.31</span></div>…
539
543
  * </div>
540
- * <div class="ai-audit-list">
541
- * <div class="ai-audit-item is-done|is-error">
542
- * <span class="ai-audit-dot"></span>
543
- * <span class="ai-audit-item-main"><span class="ai-audit-item-model">kimi · kimi-k3</span>
544
- * <span class="ai-audit-item-meta">14:03 · 1.2s · TTFT 240ms · 12.3k tok</span></span>
545
- * <span class="ai-audit-item-error">网络请求失败:…</span> <!-- 仅 is-error -->
544
+ * <div class="icen-ai-audit-list">
545
+ * <div class="icen-ai-audit-item is-done|is-error">
546
+ * <span class="icen-ai-audit-dot"></span>
547
+ * <span class="icen-ai-audit-item-main"><span class="icen-ai-audit-item-model">kimi · kimi-k3</span>
548
+ * <span class="icen-ai-audit-item-meta">14:03 · 1.2s · TTFT 240ms · 12.3k tok</span></span>
549
+ * <span class="icen-ai-audit-item-error">网络请求失败:…</span> <!-- 仅 is-error -->
546
550
  * </div>…
547
551
  * </div>
548
- * <button class="btn btn-sm ai-audit-clear">清除审计</button>
552
+ * <button class="icen-btn icen-btn-sm icen-ai-audit-clear">清除审计</button>
549
553
  * </div>
550
554
  */
551
555
 
552
- .ai-audit {
556
+ .icen-ai-audit {
553
557
  display: flex;
554
558
  flex-direction: column;
555
- gap: var(--density-space-sm);
559
+ gap: var(--icen-density-space-sm);
556
560
  align-self: stretch;
557
561
  min-width: 0;
558
- font-size: var(--density-font-size-sm);
562
+ font-size: var(--icen-density-font-size-sm);
559
563
  }
560
- .ai-audit-empty {
561
- padding: var(--density-space-md);
564
+ .icen-ai-audit-empty {
565
+ padding: var(--icen-density-space-md);
562
566
  text-align: center;
563
- color: var(--token-text-faint);
564
- font-size: var(--density-font-size-xs);
567
+ color: var(--icen-token-text-faint);
568
+ font-size: var(--icen-density-font-size-xs);
565
569
  }
566
570
 
567
571
  /* totals 行:等宽数字,faint 汇总 */
568
- .ai-audit-totals-text {
572
+ .icen-ai-audit-totals-text {
569
573
  display: block;
570
- font-family: var(--font-mono);
571
- font-size: var(--density-font-size-xs);
572
- color: var(--token-text-faint);
574
+ font-family: var(--icen-font-mono);
575
+ font-size: var(--icen-density-font-size-xs);
576
+ color: var(--icen-token-text-faint);
573
577
  font-variant-numeric: tabular-nums;
574
578
  }
575
579
 
576
580
  /* byModel 分组行 */
577
- .ai-audit-models {
581
+ .icen-ai-audit-models {
578
582
  display: flex;
579
583
  flex-direction: column;
580
584
  gap: 2px;
581
585
  }
582
- .ai-audit-model-row {
586
+ .icen-ai-audit-model-row {
583
587
  display: flex;
584
588
  align-items: baseline;
585
589
  justify-content: space-between;
586
- gap: var(--density-space-sm);
590
+ gap: var(--icen-density-space-sm);
587
591
  min-width: 0;
588
592
  }
589
- .ai-audit-model-name {
590
- font-family: var(--font-mono);
591
- font-size: var(--density-font-size-xs);
592
- color: var(--token-text);
593
+ .icen-ai-audit-model-name {
594
+ font-family: var(--icen-font-mono);
595
+ font-size: var(--icen-density-font-size-xs);
596
+ color: var(--icen-token-text);
593
597
  overflow: hidden;
594
598
  text-overflow: ellipsis;
595
599
  white-space: nowrap;
596
600
  }
597
- .ai-audit-model-meta {
601
+ .icen-ai-audit-model-meta {
598
602
  flex-shrink: 0;
599
- font-family: var(--font-mono);
600
- font-size: var(--density-font-size-2xs);
601
- color: var(--token-text-faint);
603
+ font-family: var(--icen-font-mono);
604
+ font-size: var(--icen-density-font-size-2xs);
605
+ color: var(--icen-token-text-faint);
602
606
  font-variant-numeric: tabular-nums;
603
607
  }
604
608
 
605
609
  /* 最近条目(最新在前) */
606
- .ai-audit-list {
610
+ .icen-ai-audit-list {
607
611
  display: flex;
608
612
  flex-direction: column;
609
613
  gap: 2px;
610
614
  max-height: 280px;
611
615
  overflow-y: auto;
612
616
  }
613
- .ai-audit-item {
617
+ .icen-ai-audit-item {
614
618
  display: flex;
615
619
  align-items: baseline;
616
- gap: var(--density-space-xs);
617
- padding: 2px var(--density-space-xs);
618
- border-radius: var(--radius-xs);
620
+ gap: var(--icen-density-space-xs);
621
+ padding: 2px var(--icen-density-space-xs);
622
+ border-radius: var(--icen-radius-xs);
619
623
  min-width: 0;
620
624
  }
621
- .ai-audit-item:hover {
622
- background: var(--token-fill-1);
625
+ .icen-ai-audit-item:hover {
626
+ background: var(--icen-token-fill-1);
623
627
  }
624
- .ai-audit-dot {
628
+ .icen-ai-audit-dot {
625
629
  flex-shrink: 0;
626
630
  width: 6px;
627
631
  height: 6px;
628
632
  border-radius: 50%;
629
- background: var(--token-text-faint);
633
+ background: var(--icen-token-text-faint);
630
634
  }
631
- .ai-audit-item.is-done .ai-audit-dot {
632
- background: var(--token-success);
635
+ .icen-ai-audit-item.is-done .icen-ai-audit-dot {
636
+ background: var(--icen-token-success);
633
637
  }
634
- .ai-audit-item.is-error .ai-audit-dot {
635
- background: var(--token-error);
638
+ .icen-ai-audit-item.is-error .icen-ai-audit-dot {
639
+ background: var(--icen-token-error);
636
640
  }
637
- .ai-audit-item-main {
641
+ .icen-ai-audit-item-main {
638
642
  display: flex;
639
643
  flex-direction: column;
640
644
  min-width: 0;
641
645
  flex: 1;
642
646
  }
643
- .ai-audit-item-model {
644
- font-family: var(--font-mono);
645
- font-size: var(--density-font-size-2xs);
646
- color: var(--token-text);
647
+ .icen-ai-audit-item-model {
648
+ font-family: var(--icen-font-mono);
649
+ font-size: var(--icen-density-font-size-2xs);
650
+ color: var(--icen-token-text);
647
651
  overflow: hidden;
648
652
  text-overflow: ellipsis;
649
653
  white-space: nowrap;
650
654
  }
651
- .ai-audit-item-meta {
652
- font-family: var(--font-mono);
653
- font-size: var(--density-font-size-2xs);
654
- color: var(--token-text-faint);
655
+ .icen-ai-audit-item-meta {
656
+ font-family: var(--icen-font-mono);
657
+ font-size: var(--icen-density-font-size-2xs);
658
+ color: var(--icen-token-text-faint);
655
659
  font-variant-numeric: tabular-nums;
656
660
  }
657
- .ai-audit-item-error {
661
+ .icen-ai-audit-item-error {
658
662
  flex-shrink: 0;
659
663
  max-width: 45%;
660
- font-size: var(--density-font-size-2xs);
661
- color: var(--token-error);
664
+ font-size: var(--icen-density-font-size-2xs);
665
+ color: var(--icen-token-error);
662
666
  overflow: hidden;
663
667
  text-overflow: ellipsis;
664
668
  white-space: nowrap;
665
669
  }
666
- .ai-audit-item.is-error .ai-audit-item-model {
667
- color: var(--token-error);
670
+ .icen-ai-audit-item.is-error .icen-ai-audit-item-model {
671
+ color: var(--icen-token-error);
668
672
  }
669
673
 
670
- /* 清除钮(右对齐;视觉复用 .btn .btn-sm) */
671
- .ai-audit-clear {
674
+ /* 清除钮(右对齐;视觉复用 .icen-btn .icen-btn-sm) */
675
+ .icen-ai-audit-clear {
672
676
  align-self: flex-end;
673
677
  }
674
678
 
675
679
  /* ── 动效守卫 ── */
676
680
 
677
681
  @media (prefers-reduced-motion: reduce) {
678
- .ai-todo-bar > i,
679
- .ai-usage-seg { transition: none; }
680
- .ai-context { transition: none; }
681
- .ai-item-status { animation: none; }
682
+ .icen-ai-todo-bar > i,
683
+ .icen-ai-usage-seg { transition: none; }
684
+ .icen-ai-context { transition: none; }
685
+ .icen-ai-item-status { animation: none; }
682
686
  }
683
687
 
684
688
  /* ══════════════ ai-feedback · 回答反馈(§5.27,behaviors/ai-feedback.ts) ══════════════ */
685
689
 
686
690
  /*
687
- * <div class="ai-feedback [.is-done]">
688
- * <div class="ai-feedback-votes">
689
- * <button class="ai-feedback-vote is-up [.is-picked]" aria-pressed>svg</button>
690
- * <button class="ai-feedback-vote is-down [.is-picked]" aria-pressed>svg</button>
691
+ * <div class="icen-ai-feedback [.is-done]">
692
+ * <div class="icen-ai-feedback-votes">
693
+ * <button class="icen-ai-feedback-vote is-up [.is-picked]" aria-pressed>svg</button>
694
+ * <button class="icen-ai-feedback-vote is-down [.is-picked]" aria-pressed>svg</button>
691
695
  * </div>
692
- * <div class="ai-feedback-reasons" hidden>
693
- * <button class="ai-feedback-chip [.is-picked]">答案有误</button>…
694
- * <button class="ai-feedback-submit">提交</button>
696
+ * <div class="icen-ai-feedback-reasons" hidden>
697
+ * <button class="icen-ai-feedback-chip [.is-picked]">答案有误</button>…
698
+ * <button class="icen-ai-feedback-submit">提交</button>
695
699
  * </div>
696
- * <div class="ai-feedback-done" hidden>感谢反馈,已关联到该条回答的追踪记录</div>
700
+ * <div class="icen-ai-feedback-done" hidden>感谢反馈,已关联到该条回答的追踪记录</div>
697
701
  * </div>
698
702
  * 双钮 28px;is-picked accent 边;.is-done 终态隐藏控件只留小字感谢文案。
699
703
  */
700
704
 
701
- .ai-feedback {
705
+ .icen-ai-feedback {
702
706
  display: inline-flex;
703
707
  flex-wrap: wrap;
704
708
  align-items: center;
705
- gap: var(--density-space-sm);
709
+ gap: var(--icen-density-space-sm);
706
710
  min-width: 0;
707
711
  }
708
712
 
709
- .ai-feedback-votes {
713
+ .icen-ai-feedback-votes {
710
714
  display: inline-flex;
711
715
  gap: 4px;
712
716
  }
713
717
 
714
718
  /* 双钮:28px 方形图标钮 */
715
- .ai-feedback-vote {
719
+ .icen-ai-feedback-vote {
716
720
  display: inline-flex;
717
721
  align-items: center;
718
722
  justify-content: center;
719
723
  width: 28px;
720
724
  height: 28px;
721
725
  padding: 0;
722
- border: 1px solid var(--token-line-soft);
723
- border-radius: var(--radius-sm);
726
+ border: 1px solid var(--icen-token-line-soft);
727
+ border-radius: var(--icen-radius-sm);
724
728
  background: transparent;
725
- color: var(--token-text-muted);
729
+ color: var(--icen-token-text-muted);
726
730
  cursor: pointer;
727
731
  transition:
728
732
  color var(--icen-tx-fast),
@@ -730,50 +734,50 @@
730
734
  background-color var(--icen-tx-fast),
731
735
  opacity var(--icen-tx-fast);
732
736
  }
733
- .ai-feedback-vote svg {
737
+ .icen-ai-feedback-vote svg {
734
738
  width: 14px;
735
739
  height: 14px;
736
740
  }
737
- .ai-feedback-vote:hover {
738
- color: var(--token-text);
741
+ .icen-ai-feedback-vote:hover {
742
+ color: var(--icen-token-text);
739
743
  border-color: var(--icen-hover-border);
740
- background: var(--token-fill-1);
744
+ background: var(--icen-token-fill-1);
741
745
  }
742
- .ai-feedback-vote:focus-visible {
746
+ .icen-ai-feedback-vote:focus-visible {
743
747
  outline: none;
744
748
  box-shadow: var(--icen-ring);
745
749
  }
746
750
  /* 锁定:对侧禁用降透明;选中侧 accent 边 + 浅 accent 底 */
747
- .ai-feedback-vote:disabled {
751
+ .icen-ai-feedback-vote:disabled {
748
752
  opacity: 0.45;
749
753
  cursor: default;
750
754
  background: transparent;
751
- border-color: var(--token-line-soft);
755
+ border-color: var(--icen-token-line-soft);
752
756
  }
753
- .ai-feedback-vote.is-picked {
754
- color: var(--token-accent);
755
- border-color: var(--token-accent);
756
- background: color-mix(in srgb, var(--token-accent) 10%, transparent);
757
+ .icen-ai-feedback-vote.is-picked {
758
+ color: var(--icen-token-accent);
759
+ border-color: var(--icen-token-accent);
760
+ background: color-mix(in srgb, var(--icen-token-accent) 10%, transparent);
757
761
  }
758
762
 
759
763
  /* 踩因枚举 chips + 提交(点 👎 展开) */
760
- .ai-feedback-reasons {
764
+ .icen-ai-feedback-reasons {
761
765
  display: inline-flex;
762
766
  flex-wrap: wrap;
763
767
  align-items: center;
764
- gap: var(--density-space-xs);
768
+ gap: var(--icen-density-space-xs);
765
769
  min-width: 0;
766
770
  }
767
- .ai-feedback-reasons[hidden] {
771
+ .icen-ai-feedback-reasons[hidden] {
768
772
  display: none;
769
773
  }
770
- .ai-feedback-chip {
774
+ .icen-ai-feedback-chip {
771
775
  padding: 2px 10px;
772
- border: 1px solid var(--token-line-soft);
773
- border-radius: var(--radius-full);
776
+ border: 1px solid var(--icen-token-line-soft);
777
+ border-radius: var(--icen-radius-full);
774
778
  background: transparent;
775
- color: var(--token-text-muted);
776
- font-size: var(--density-font-size-xs);
779
+ color: var(--icen-token-text-muted);
780
+ font-size: var(--icen-density-font-size-xs);
777
781
  line-height: 1.5;
778
782
  cursor: pointer;
779
783
  transition:
@@ -781,28 +785,28 @@
781
785
  border-color var(--icen-tx-fast),
782
786
  background-color var(--icen-tx-fast);
783
787
  }
784
- .ai-feedback-chip:hover {
785
- color: var(--token-text);
788
+ .icen-ai-feedback-chip:hover {
789
+ color: var(--icen-token-text);
786
790
  border-color: var(--icen-hover-border);
787
791
  }
788
- .ai-feedback-chip:focus-visible {
792
+ .icen-ai-feedback-chip:focus-visible {
789
793
  outline: none;
790
794
  box-shadow: var(--icen-ring);
791
795
  }
792
- .ai-feedback-chip.is-picked {
793
- color: var(--token-accent);
794
- border-color: var(--token-accent);
795
- background: color-mix(in srgb, var(--token-accent) 10%, transparent);
796
+ .icen-ai-feedback-chip.is-picked {
797
+ color: var(--icen-token-accent);
798
+ border-color: var(--icen-token-accent);
799
+ background: color-mix(in srgb, var(--icen-token-accent) 10%, transparent);
796
800
  }
797
801
 
798
802
  /* 提交钮:小号 ghost(accent 留给状态,非主行动不铺实底) */
799
- .ai-feedback-submit {
803
+ .icen-ai-feedback-submit {
800
804
  padding: 2px 12px;
801
- border: 1px solid var(--token-line);
802
- border-radius: var(--radius-full);
805
+ border: 1px solid var(--icen-token-line);
806
+ border-radius: var(--icen-radius-full);
803
807
  background: transparent;
804
- color: var(--token-text);
805
- font-size: var(--density-font-size-xs);
808
+ color: var(--icen-token-text);
809
+ font-size: var(--icen-density-font-size-xs);
806
810
  line-height: 1.5;
807
811
  cursor: pointer;
808
812
  transition:
@@ -810,70 +814,70 @@
810
814
  border-color var(--icen-tx-fast),
811
815
  background-color var(--icen-tx-fast);
812
816
  }
813
- .ai-feedback-submit:hover {
814
- color: var(--token-accent);
815
- border-color: var(--token-accent);
816
- background: color-mix(in srgb, var(--token-accent) 8%, transparent);
817
+ .icen-ai-feedback-submit:hover {
818
+ color: var(--icen-token-accent);
819
+ border-color: var(--icen-token-accent);
820
+ background: color-mix(in srgb, var(--icen-token-accent) 8%, transparent);
817
821
  }
818
- .ai-feedback-submit:focus-visible {
822
+ .icen-ai-feedback-submit:focus-visible {
819
823
  outline: none;
820
824
  box-shadow: var(--icen-ring);
821
825
  }
822
826
 
823
827
  /* 已提交终态:小字感谢文案,控件隐藏 */
824
- .ai-feedback-done {
825
- font-size: var(--density-font-size-2xs);
826
- color: var(--token-text-faint);
828
+ .icen-ai-feedback-done {
829
+ font-size: var(--icen-density-font-size-2xs);
830
+ color: var(--icen-token-text-faint);
827
831
  }
828
- .ai-feedback-done[hidden] {
832
+ .icen-ai-feedback-done[hidden] {
829
833
  display: none;
830
834
  }
831
- .ai-feedback.is-done .ai-feedback-votes,
832
- .ai-feedback.is-done .ai-feedback-reasons {
835
+ .icen-ai-feedback.is-done .icen-ai-feedback-votes,
836
+ .icen-ai-feedback.is-done .icen-ai-feedback-reasons {
833
837
  display: none;
834
838
  }
835
839
 
836
840
  /* ══════════════ ai-usage-metrics · 派生指标明细行(§5.27,renderAiUsage) ══════════════ */
837
841
 
838
842
  /* 图例下 mono 一行:TTFT 0.8s · 42 tok/s · finish: stop */
839
- .ai-usage-metrics {
840
- font-family: var(--font-mono);
843
+ .icen-ai-usage-metrics {
844
+ font-family: var(--icen-font-mono);
841
845
  font-size: 11.5px;
842
- color: var(--token-text-faint);
846
+ color: var(--icen-token-text-faint);
843
847
  font-variant-numeric: tabular-nums;
844
848
  letter-spacing: 0.01em;
845
849
  }
846
850
 
847
851
  /* ══════════════ ai-todo-check · done 描边勾(§5.27,renderAiTodo) ══════════════ */
848
852
 
849
- /* 与 .ai-item-status 同位替换:done 时显勾隐点(:has 守卫——静态手写 DOM 无勾时保留状态点);
853
+ /* 与 .icen-ai-item-status 同位替换:done 时显勾隐点(:has 守卫——静态手写 DOM 无勾时保留状态点);
850
854
  * pathLength=1 → stroke-dasharray 1,.is-anim 做 stroke-dashoffset 描边动画(480ms 一次不循环) */
851
- .ai-todo-check {
855
+ .icen-ai-todo-check {
852
856
  position: relative;
853
857
  display: none;
854
858
  flex-shrink: 0;
855
859
  width: 8px;
856
860
  height: 8px;
857
- color: var(--token-success);
861
+ color: var(--icen-token-success);
858
862
  }
859
- .ai-todo-check svg {
863
+ .icen-ai-todo-check svg {
860
864
  position: absolute;
861
865
  inset: 0;
862
866
  margin: auto;
863
867
  width: 12px;
864
868
  height: 12px;
865
869
  }
866
- .ai-todo-check path {
870
+ .icen-ai-todo-check path {
867
871
  stroke-dasharray: 1;
868
872
  }
869
- .ai-todo-item.is-done .ai-todo-check {
873
+ .icen-ai-todo-item.is-done .icen-ai-todo-check {
870
874
  display: inline-flex;
871
875
  }
872
- .ai-todo-item.is-done:has(.ai-todo-check) > .ai-item-status {
876
+ .icen-ai-todo-item.is-done:has(.icen-ai-todo-check) > .icen-ai-item-status {
873
877
  display: none;
874
878
  }
875
- .ai-todo-check.is-anim path {
876
- animation: ai-todo-check-draw var(--ai-todo-check-duration, 480ms) var(--ease-out) 1 forwards;
879
+ .icen-ai-todo-check.is-anim path {
880
+ animation: ai-todo-check-draw var(--ai-todo-check-duration, 480ms) var(--icen-ease-out) 1 forwards;
877
881
  }
878
882
  @keyframes ai-todo-check-draw {
879
883
  from {
@@ -887,13 +891,19 @@
887
891
  /* ── 动效守卫(§5.27 新增段) ── */
888
892
 
889
893
  @media (prefers-reduced-motion: reduce) {
890
- .ai-feedback-vote,
891
- .ai-feedback-chip,
892
- .ai-feedback-submit {
894
+ .icen-ai-feedback-vote,
895
+ .icen-ai-feedback-chip,
896
+ .icen-ai-feedback-submit {
893
897
  transition: none;
894
898
  }
895
- .ai-todo-check.is-anim path {
899
+ .icen-ai-todo-check.is-anim path {
896
900
  animation: none;
897
901
  stroke-dashoffset: 0;
898
902
  }
899
903
  }
904
+
905
+ /* ── RTL:上下文抽屉隐藏位镜像(抽屉改贴行内末端左侧,滑出方向同步翻转) ── */
906
+ :is([dir='rtl']) .icen-ai-context { transform: translateX(-100%); }
907
+ :is([dir='rtl']) .icen-ai-context.is-open { transform: translateX(0); }
908
+
909
+ }