React表单数据处理与条件路由跳转问题求助
React问卷表单提交后跳转对应页面解决方案
问题概述
- 开发React问卷表单项目,提交时仅将答案打印到控制台,无法根据表单数据通过if/else逻辑跳转至对应页面
- 曾出现错误:
Uncaught TypeError: props.getData is not a function - 示例需求:提交
{"gender": "male","userAge": "young","goals": "active"}后跳转至对应页面
解决方案步骤
1. 状态提升(解决props调用错误)
将表单数据的状态从子组件Questions提升到App组件的封装层,统一管理数据与路由跳转逻辑,避免未定义props调用报错。
2. 使用React Router v6导航API
通过useNavigate钩子实现页面跳转,这是React Router v6的标准导航方式,替代旧版history.push。
3. 添加条件跳转逻辑
在提交回调中,通过if/else(或switch)判断表单字段值,匹配对应跳转路径。
修改后的代码示例
App.js
import React, { useState } from 'react'; import Introduction from './components/introduction'; import Questions from './components/beginning'; import Male from './components/questions'; import PersonalExercise from './components/personalExercise'; // 修复组件名首字母大写规范 import { BrowserRouter as Router, Route, Routes, useNavigate } from 'react-router-dom'; // 封装带状态与导航逻辑的内层组件 function AppWrapper() { const [formData, setFormData] = useState({ gender: "", userAge: "", goals:"", }); const navigate = useNavigate(); // 同步子组件的表单数据更新 const updateFormData = (newData) => { setFormData(prev => ({...prev, ...newData})); }; // 提交后的条件跳转逻辑 const handleFormSubmit = (data) => { // 示例条件分支,可根据实际需求扩展 if (data.gender === "male" && data.userAge === "young" && data.goals === "active") { navigate("/personalExercise"); } else if (data.gender === "female" && data.userAge === "senior" && data.goals === "weight") { navigate("/questions"); } // 更多跳转规则... }; return ( <Routes> <Route path="/" element={<Introduction />} /> <Route path="/beginning" element={<Questions updateFormData={updateFormData} handleSubmit={handleFormSubmit} />} /> <Route path="/personalExercise" element={<PersonalExercise />} /> <Route path="/questions" element={<Male />} /> </Routes> ); } export default function App() { return ( <Router> <AppWrapper /> </Router> ); }
Questions.js(表单组件)
import React, { useState } from 'react'; import Form from 'react-bootstrap/Form'; export default function Questions({ updateFormData, handleSubmit }) { const[formData, setFormData] = useState({ gender: "", userAge: "", goals:"", }); function handleChange(event) { const { name, value, type, checked } = event.target; const newData = { [name]: type === 'checkbox' ? checked : value }; setFormData(prev => ({...prev, ...newData})); updateFormData(newData); // 同步数据到父组件 } function handleFormSubmit(event) { event.preventDefault(); console.log(formData); handleSubmit(formData); // 触发父组件的跳转逻辑 } return ( <> <header>Questions</header> <Form onSubmit={handleFormSubmit}> <fieldset> <legend>What was your gender at birth</legend> <input type='radio' id='male' name='gender' value='male' checked={formData.gender === "male"} onChange={handleChange} /> <label htmlFor="male"> Male </label> <br /> <input type='radio' id='female' name='gender' value='female' checked={formData.gender === "female"} onChange={handleChange} /> <label htmlFor="female"> Female </label> <br /> </fieldset> <fieldset> <legend>How old are you?</legend> <input type='radio' id="young" name="userAge" value="young" checked={formData.userAge === "young"} onChange={handleChange} /> <label htmlFor="young"> 18-28 </label> <br /> <input type='radio' id="middleAged" name="userAge" value="middleAged" checked={formData.userAge === "middleAged"} onChange={handleChange} /> <label htmlFor="middleAged"> 29-39 </label> <br /> <input type='radio' id="older" name="userAge" value="older" checked={formData.userAge === "older"} onChange={handleChange} /> <label htmlFor="older"> 40-50 </label> <br /> <input type='radio' id="senior" name="userAge" value="senior" checked={formData.userAge === "senior"} onChange={handleChange} /> <label htmlFor="senior"> 51+ </label> <br /> </fieldset> <br /> <fieldset> <legend>What kind of fitness would you prefer?</legend> <input type="radio" id="active" name="goals" value="active" checked={formData.goals === "active"} onChange={handleChange} /> <label htmlFor='active'>To stay active!</label> <br /> <input type="radio" id="weight" name="goals" value="weight" checked={formData.goals === "weight"} onChange={handleChange} /> <label htmlFor="weight"> To loose weight</label> </fieldset> <br /> <button>Submit</button> </Form> </> ) }
关键说明
- 状态提升:将表单数据统一管理在路由层级,避免跨组件props传递混乱
- 导航逻辑:
useNavigate是React Router v6推荐的导航方式,兼容性更好 - 条件判断:if/else适合分支较少的场景,若跳转规则复杂,可改用switch语句或配置映射表优化
- 组件规范:修复了组件名首字母小写的问题,React组件必须遵循首字母大写命名规则
内容的提问来源于stack exchange,提问作者user12761285
相关产品推荐
相关产品推荐

