如何在MUI AutoComplete组件中提交选项ID而非显示名称?
解决Autocomplete显示员工姓名但提交员工ID的问题
你当前的问题出在直接给TextField传递register,导致Autocomplete把通过getOptionLabel生成的全名作为表单值提交。要实现显示姓名但提交ID,需要调整Autocomplete和react-hook-form的绑定方式,以下是两种可行方案:
方案1:使用react-hook-form的Controller组件(推荐)
Controller是react-hook-form专门为受控组件设计的包装器,能精准控制表单值的读写。
首先确保导入Controller:
import { Controller } from 'react-hook-form';
然后替换原有的Autocomplete代码:
// 确保你的组件中已调用useForm并获取control const { control, formState: { errors } } = useForm(); <Box component="form" id="applicationForm" noValidate> <Controller name="studentId" control={control} rules={{ required: errorLocales.validation.requiredField }} render={({ field: { onChange, value } }) => ( <Autocomplete options={employees} getOptionLabel={(option: UserModel) => `${option.firstName} ${option.lastName}`} getOptionKey={(option: UserModel) => option.id} id="studentId" isOptionEqualToValue={(option, value) => option.id === value?.id} // 根据表单存储的ID匹配对应的员工对象,确保选中状态正确 value={value ? employees.find(emp => emp.id === value) : null} // 将选中员工的ID传给表单字段 onChange={(event, newValue) => { onChange(newValue ? newValue.id : null); }} renderInput={(params) => ( <TextField {...params} label="Сотрудник" variant="filled" error={!!errors.studentId} /> )} /> )} /> </Box>
方案2:手动用setValue和watch处理
如果不想用Controller,可以通过setValue和watch手动绑定表单值与Autocomplete的选中状态:
const { setValue, watch, formState: { errors } } = useForm(); // 监听表单中studentId字段的当前值 const selectedEmployeeId = watch('studentId'); <Box component="form" id="applicationForm" noValidate> <Autocomplete options={employees} getOptionLabel={(option: UserModel) => `${option.firstName} ${option.lastName}`} getOptionKey={(option: UserModel) => option.id} id="studentId" isOptionEqualToValue={(option, value) => option.id === value?.id} // 根据表单ID匹配员工对象 value={selectedEmployeeId ? employees.find(emp => emp.id === selectedEmployeeId) : null} // 选中时将ID存入表单 onChange={(event, newValue) => { setValue('studentId', newValue ? newValue.id : null); }} renderInput={(params) => ( <TextField {...params} label="Сотрудник" variant="filled" error={!!errors.studentId} /> )} /> </Box>
关键注意点
- 必须移除原
TextField中的{...register('studentId', ...)},避免和新的绑定逻辑冲突。 isOptionEqualToValue要保持基于ID的判断,确保选中状态匹配正确。
内容的提问来源于stack exchange,提问作者quester
相关产品推荐
相关产品推荐

