使用withFormik
import React from "react";
import { withFormik } from 'formik';
const AddPlayerForm = (props) => {
const { values, handleSubmit, handleChange } = props;
console.log(props)
return (
<form className="form" onSubmit={handleSubmit}>
<fieldset className="form-group">
<label htmlFor="username">Name:</label>
<input
name="name"
type="text"
onChange={handleChange}
value={values.name}
required
className="form-control"
/>
<label htmlFor="team">Team:</label>
<input
name="team"
type="text"
onChange={handleChange}
value={values.team}
required
className="form-control"
/>
</fieldset>
<button type="submit" className="btn btn-primary btn-block">
Save
</button>
</form>
);
};
const EnhancedForm = withFormik({
handleSubmit: (values, functions) => {
setTimeout(() => {
alert(JSON.stringify(values, null, 2));
functions.props.save(values);
}, 1000);
}
})(AddPlayerForm);
export default EnhancedForm;
直接使用Formik标签
import React from "react";
import AlertBox from "./AlertBox";
const AddPlayerForm = ({
errors,
touched,
handleSubmit,
handleChange,
values
}) => {
console.log(errors);
const handleClick = e => {
alert("clicked");
};
return (
<form className="form" onSubmit={handleSubmit}>
<fieldset className="form-group">
<label htmlFor="username">Name:</label>
<input
name="name"
type="text"
onChange={handleChange}
value={values.name}
required
className="form-control"
/>
{errors.name && <AlertBox>{errors.name}</AlertBox>}
<label htmlFor="team">Team:</label>
<input
name="team"
type="text"
onChange={handleChange}
value={values.team}
required
className="form-control"
/>
{errors.team && <AlertBox>{errors.team}</AlertBox>}
</fieldset>
<button type="submit" className="btn btn-primary btn-block">
Save
</button>
</form>
);
};
export default AddPlayerForm;
import React from "react";
import { Formik } from "formik";
import PlayerList from "./components/PlayerList";
import AddPlayerForm from "./components/AddPlayerForm";
class App extends React.Component {
check(players, name) {
const duplicate = players.find(player => {
return player.name === name;
});
return duplicate !== undefined
}
validate = values => {
let errors = {};
if (!values.name) {
errors.name = "Required";
}
if (!values.team) {
errors.team = "Required";
}
if (this.check(this.state.players, values.name)) {
errors.name = "Duplicated";
}
console.log(errors);
errors.messages = JSON.stringify(errors, null, 2);
return errors;
};
state = {
players: [{ name: "Jordan", team: "Bulls" }]
};
addPlayer = player => {
this.setState({ players: [...this.state.players, player] });
};
render() {
const { players } = this.state;
return (
<div>
<h3>Player list ({players.length})</h3>
<PlayerList players={players} />
<h3>Add a player</h3>
<Formik
initialValues={{
name: "",
team: ""
}}
onSubmit={values => {
setTimeout(() => {
alert(JSON.stringify(values, null, 2));
this.addPlayer(values);
}, 500);
}}
validate={this.validate.bind(this)}
render={({ errors, touched, handleSubmit, handleChange, values }) => (
<AddPlayerForm
errors={errors}
touched={touched}
handleSubmit={handleSubmit}
handleChange={handleChange}
values={values}
/>
)}
/>
</div>
);
}
}
export default App;
以下补疑一个特殊写法,如何向formik中的一个stateless组件传值
<Formik onSubmit={onSubmit} initialValues={player}>
{formikProps => <EditPlayerForm {...formikProps} iWantTransferthisValue={"great!"} />}
</Formik>
const EditPlayerForm = props => <PlayerForm {...props} isNewPlayer={false} />;
const PlayerForm = ({
isNewPlayer,
values,
handleSubmit,
handleChange,
isSubmitting,
iWantTransferthisValue
}) => {
console.log(iWantTransferthisValue)
return (
)
}
for submit error
const onSubmit = async (values, { props, setSubmitting, setErrors }) => {
await api.edit(values).then(
values => {
console.log(values),
setSubmitting(false),
history.push("/players")
},
error => {
setSubmitting(false);
setErrors({ general: error.message });
});
};
下面两种写法实际上是相同的
<Formik>
{({ myFormikProps }) => <MyForm extraProp={'nice!'} {...myFormikProps} />}
</Formik>
<Formik>
{withProps({ isNewPlayer: false })(PlayerForm)}
</Formik>