React中基于state渲染的按钮事件冲突,状态无法切换问题求解
问题解决思路及修复代码
核心问题分析
- 事件绑定错误:按钮元素不存在
onSubmit属性,你给「save change」按钮绑定的onSubmit不会生效,应该用onClick; - 表单默认行为干扰:如果按钮在
<form>标签内,type="submit"的按钮点击会触发表单默认提交行为,导致页面刷新,isEdit状态被重置回初始值true,所以看起来状态无法切换; - 初始写法逻辑冲突:你最初的单按钮写法里用了两个并列的
if,但React状态更新是异步的,同一事件周期内状态不会立即更新,容易导致逻辑混乱。
修复方案一:修复条件渲染代码
如果不需要提交表单,直接把「save change」按钮的type改为button,并替换onSubmit为onClick:
const [isEdit, setIsEdit] = useState(true) return( // 若按钮在form内,需给form添加阻止默认提交的逻辑 <form onSubmit={(e) => e.preventDefault()}> {isEdit ? ( <button className="btn btn--fill-primary" type="button" // 改为button类型,避免触发表单默认提交 disabled={isLoading} onClick={() => { console.log("submit") setIsEdit(false) }} > save change </button> ) : ( <button className="btn btn--fill-black" type="button" disabled={isLoading} onClick={() => { console.log("click") setIsEdit(true) }} > edit </button> )} </form> )
如果确实需要提交表单,保留type="submit",但在<form>的onSubmit中处理提交逻辑并阻止默认行为:
const [isEdit, setIsEdit] = useState(true) const handleSubmit = (e) => { e.preventDefault() console.log("submit") setIsEdit(false) } return( <form onSubmit={handleSubmit}> {isEdit ? ( <button className="btn btn--fill-primary" type="submit" disabled={isLoading} > save change </button> ) : ( <button className="btn btn--fill-black" type="button" disabled={isLoading} onClick={() => { console.log("click") setIsEdit(true) }} > edit </button> )} </form> )
修复方案二:修复单按钮写法
把并列的if改成if-else避免逻辑冲突,同时处理表单默认行为:
const [isEdit, setIsEdit] = useState(true) return( <form onSubmit={(e) => e.preventDefault()}> <button className={`btn btn--fill-${isEdit ? "primary" : "black"}`} type={isEdit ? "button" : "button"} // 不需要提交表单就统一用button类型 disabled={isLoading} onClick={() => { if (isEdit) { console.log('submit') setIsEdit(false) } else { // 用else替代第二个if,避免逻辑冲突 console.log('click') setIsEdit(true) } }} > {isEdit ? "save change" : "edit"} </button> </form> )
内容的提问来源于stack exchange,提问作者Joe
相关产品推荐
相关产品推荐

