@autional/ui 0.1.0-rc.43 → 0.1.0-rc.44

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@autional/ui",
3
- "version": "0.1.0-rc.43",
3
+ "version": "0.1.0-rc.44",
4
4
  "description": "Autional shared React component library (atoms + molecules) — the canonical home of the component layer",
5
5
  "license": "AGPL-3.0",
6
6
  "main": "./src/index.ts",
@@ -82,7 +82,7 @@
82
82
  "react-i18next": "17.0.7",
83
83
  "typescript": "5.8.3",
84
84
  "vitest": "3.2.0",
85
- "@autional/tokens": "0.1.0-rc.11"
85
+ "@autional/tokens": "0.1.0-rc.12"
86
86
  },
87
87
  "scripts": {
88
88
  "typecheck": "tsc --noEmit",
@@ -1,16 +1,49 @@
1
1
  import * as React from 'react';
2
2
  import { fieldControlClass, fieldControlHeight } from '../internal/field-styles';
3
3
 
4
- export interface InputProps extends React.InputHTMLAttributes<HTMLInputElement> {
4
+ // 注:`prefix` 与 HTML 自带的 `prefix` 属性同名(后者在 <input> 上没有意义,TS 会报
5
+ // 「ReactNode 不能赋给 string」)。所以这里显式 Omit 掉它再重定义 —— 保住最自然的调用名。
6
+ export interface InputProps extends Omit<React.InputHTMLAttributes<HTMLInputElement>, 'prefix'> {
5
7
  error?: string;
8
+ /**
9
+ * 前缀槽:图标或极短的单位符号(如货币符号)。
10
+ *
11
+ * 为什么要有它(第 59 轮):舰队里 5 个站在手写同一个模式 ——
12
+ * 一个 `relative` 容器 + 绝对定位的图标 + **算出来的**左内边距(`pl-9` = 12 起点 + 16 图标 + 8 间隙 = 36px)。
13
+ * 那是同一个几何被抄了 6 遍,而且抄出来的值不在档位上。
14
+ * 这里用 **flex 排布**而不是绝对定位:图标占真实布局空间,于是
15
+ * **不需要任何魔法内边距**,也不挑图标尺寸。
16
+ *
17
+ * 图标请守图标纪律:默认 `size="1em"`,显式字号时 `size={N}`。
18
+ */
19
+ prefix?: React.ReactNode;
20
+ /** 后缀槽:清除按钮、单位后缀一类。同样占真实布局空间。 */
21
+ suffix?: React.ReactNode;
6
22
  }
7
23
 
8
24
  // 外观来自 ../internal/field-styles —— 与 @autional/ui/rhf 的绑定控件同一份,不各自维护。
25
+ //
26
+ // 两种渲染形态(**无槽时逐字节不变**,既有消费方零影响):
27
+ // · 无 prefix/suffix:只有一个 <input>,外框在它自己身上(原样);
28
+ // · 有槽:外框交给 wrapper,<input> 变透明并占满剩余宽度 —— 高度/圆角由调用方
29
+ // 原有的 className 决定(舰队里搜索框有三种几何:py-2 / py-2.5 / py-3.5 rounded-full),
30
+ // 所以这一层**不替调用方决定尺寸**。
9
31
  export const Input = React.forwardRef<HTMLInputElement, InputProps>(
10
- ({ className = '', error, ...props }, ref) => {
32
+ ({ className = '', error, prefix, suffix, ...props }, ref) => {
33
+ const hasSlot = prefix != null || suffix != null;
11
34
  return (
12
35
  <div className="w-full">
13
- <input ref={ref} className={fieldControlClass(!!error, fieldControlHeight + ' ' + className)} {...props} />
36
+ {hasSlot ? (
37
+ <div className={fieldControlClass(!!error, 'flex items-center gap-2 ' + className)}>
38
+ {prefix != null && (
39
+ <span className="shrink-0 text-[var(--color-text-muted)]" aria-hidden="true">{prefix}</span>
40
+ )}
41
+ <input ref={ref} className="min-w-0 flex-1 bg-transparent p-0 text-inherit outline-none placeholder:text-[var(--color-text-muted)]" {...props} />
42
+ {suffix != null && <span className="shrink-0">{suffix}</span>}
43
+ </div>
44
+ ) : (
45
+ <input ref={ref} className={fieldControlClass(!!error, fieldControlHeight + ' ' + className)} {...props} />
46
+ )}
14
47
  {error && <p className="mt-1 text-xs text-[var(--color-danger)]">{error}</p>}
15
48
  </div>
16
49
  );