之前在写from表单组件的时候,调试的时候总会遇到react报错:
Warning: A component is changing an uncontrolled input of type text to be controlled. Input elements should not switch from uncontrolled to controlled (or vice versa). Decide between using a controlled or uncontrolled input element for the lifetime of the component.*
但是这个报错只会在首次渲染组件是出现,在后面调试的时候就没了,所以很迷惑。在查询一番之后,终于了解了根本原因。
这里记录一下,供后面自己查看,也许可以帮到同样遇到这个问题的你
还原报错示例代码:
const Input = () => {
const [val, setVal] = useState();
// code ...
return <input value={val} onChange={(e)=>{setVal(e.target.value)}} />
}
上面代码在渲染后第一次输入时,就会有上面贴出报错。
首先来讲一下原因
我们在val
初始化的时候并没有给值,所以val
的初始化值就是undefined
,这就导致了首次渲染出的input是这样的<input value=undefined/>
,因此react就判定这是一个非受控组件。
而一旦开始输入,触发了onChange
回调,就是给val
赋值,这时input就成为了受控的input。所以我们就会得到一开始贴出的那个错误。从错误的描述也可以很容易发现问题。
A component is changing an uncontrolled input of type text to be controlled.
知道原因了之后,解决问题就很简单了
- 我们可以给
val
一个初始值
const [val, setVal] = useState('');
- 给input的
value
属性一个初始值
<input value={val || ''}/>
总结一下,这个问题出现的根源还是自己对概念理解不够深入,没有理解受控和非受控的本质。