/// /** * FormLabel Component - Lynx 版 MUI FormLabel * 100% 一比一复刻 MUI FormLabel * * 对应 MUI: packages/mui-material/src/FormLabel/FormLabel.js */ import './FormLabel.css' import formLabelClasses, { getFormLabelUtilityClass } from './formLabelClasses' import { useFormControl, formControlState } from '../FormControl' export { formLabelClasses, getFormLabelUtilityClass } // ============================================= // 类型定义 // ============================================= export type FormLabelColor = 'primary' | 'secondary' | 'error' | 'info' | 'success' | 'warning' export interface FormLabelProps { /** 子元素 */ children?: any /** 自定义类名 */ className?: string /** 样式类覆盖 */ classes?: Partial /** 颜色 */ color?: FormLabelColor /** 是否禁用 */ disabled?: boolean /** 是否错误状态 */ error?: boolean /** 是否已填充 */ filled?: boolean /** 是否聚焦 */ focused?: boolean /** 是否必填 */ required?: boolean /** 内联样式 */ style?: Record /** sx 属性 */ sx?: Record } // ============================================= // 辅助函数 // ============================================= function capitalize(str: string): string { return str.charAt(0).toUpperCase() + str.slice(1) } function composeClasses( slots: Record, getUtilityClass: (slot: string) => string, classes?: Record ): Record { const output: Record = {} Object.keys(slots).forEach((slot) => { output[slot] = slots[slot] .filter(Boolean) .map((key) => { if (classes && classes[key as string]) { return `${getUtilityClass(key as string)} ${classes[key as string]}` } return getUtilityClass(key as string) }) .join(' ') }) return output } // ============================================= // useUtilityClasses // ============================================= interface OwnerState extends FormLabelProps {} function useUtilityClasses(ownerState: OwnerState) { const { classes, color, disabled, error, filled, focused, required } = ownerState const slots = { root: [ 'root', color === 'secondary' && 'colorSecondary', disabled && 'disabled', error && 'error', filled && 'filled', focused && 'focused', required && 'required', ], asterisk: ['asterisk', error && 'error'], } return composeClasses(slots, getFormLabelUtilityClass, classes) } // ============================================= // FormLabel 组件 // ============================================= export function FormLabel(props: FormLabelProps) { const { children, className, classes: classesProp, color, disabled, error, filled, focused, required, style, sx, ...other } = props const muiFormControl = useFormControl() const fcs = formControlState({ props, muiFormControl, states: ['color', 'disabled', 'error', 'filled', 'focused', 'required'], }) const ownerState: OwnerState = { ...props, color: fcs.color || 'primary', disabled: fcs.disabled, error: fcs.error, filled: fcs.filled, focused: fcs.focused, required: fcs.required, } const classes = useUtilityClasses(ownerState) // 构建类名 const rootClasses = [ classes.root, className, fcs.disabled && 'Mui-disabled', fcs.error && 'Mui-error', fcs.focused && 'Mui-focused', fcs.required && 'Mui-required', ].filter(Boolean).join(' ') return ( {children} {fcs.required && ( * )} ) } export default FormLabel