React中实现表单提交后Modal持续显示的方法
问题原因与解决方法
核心问题
表单提交成功时,浏览器会执行默认的表单提交跳转行为(因表单设置了method="POST"和action),导致页面刷新,刚显示的Modal直接被刷新掉,所以出现闪烁几秒就消失的现象。同时代码里还有几处逻辑错误需要修正。
具体修复步骤
1. 阻止表单默认提交行为(关键)
在提交成功的逻辑分支里添加event.preventDefault(),避免浏览器跳转刷新页面:
if ( enteredName.trim().length > 0 && enteredEmail.trim().length > 0 && enteredMessage.trim().length > 0 ) { event.preventDefault(); // 新增该行,阻止默认跳转 setShowModal({ title: "Thank You", message: "Your form has been submitted", }); props.Contact(enteredName, enteredEmail); setEnteredName(""); setEnteredEmail(""); setEnteredMessage(""); return; }
2. 修正逻辑判断错误
原代码第二个if使用||(或)逻辑,只要有一个字段不为空就触发成功分支,这不符合校验逻辑,应改为&&(且),确保三个字段都有效才进入成功流程。
3. 删除无效代码
函数组件中不能使用this.setState(这是类组件的写法),直接删除以下无效代码:
else { this.setState(true); }
4. 统一Modal状态类型
初始showModal设为false,但后续赋值为对象,建议统一状态类型,将初始值改为null,判断逻辑更一致:
const [showModal, setShowModal] = useState(null);
完整修正后的contactHandler代码
const contactHandler = (event) => { // 空字段校验 if ( enteredName.trim().length === 0 || enteredEmail.trim().length === 0 || enteredMessage.trim().length === 0 ) { event.preventDefault(); setShowModal({ title: "Invalid Input", message: "Please enter a valid name, email and message.", }); return; } // 所有字段有效,执行提交成功逻辑 event.preventDefault(); setShowModal({ title: "Thank You", message: "Your form has been submitted", }); props.Contact(enteredName, enteredEmail); setEnteredName(""); setEnteredEmail(""); setEnteredMessage(""); };
额外说明
如果需要将表单数据发送到action指定的地址,不能依赖浏览器默认提交(阻止默认行为后数据不会自动发送),需改为异步提交方式,示例代码如下:
const contactHandler = async (event) => { event.preventDefault(); // 统一阻止默认行为 // 空字段校验 if ( enteredName.trim().length === 0 || enteredEmail.trim().length === 0 || enteredMessage.trim().length === 0 ) { setShowModal({ title: "Invalid Input", message: "Please enter a valid name, email and message.", }); return; } try { // 异步提交表单数据到目标地址 const response = await fetch("https://getform.io/f/182419e0-81f1-4e7f-a5f6-ed57b3b52dd9", { method: "POST", headers: { "Content-Type": "application/json", }, body: JSON.stringify({ name: enteredName, email: enteredEmail, message: enteredMessage, }), }); if (response.ok) { setShowModal({ title: "Thank You", message: "Your form has been submitted", }); props.Contact(enteredName, enteredEmail); setEnteredName(""); setEnteredEmail(""); setEnteredMessage(""); } else { setShowModal({ title: "Submission Failed", message: "Something went wrong, please try again later.", }); } } catch (error) { setShowModal({ title: "Error", message: "Network error, please check your connection.", }); } };
内容的提问来源于stack exchange,提问作者ChrisWill303
相关产品推荐
相关产品推荐

