Functional Componentにおける複数のonChangeハンドラを一元的に処理するコールバック関数をお伝えしたい。
まずフォーム項目の操作は、onChangeハンドラが必要で、記述がなければwarningが発生するケースもある。input要素を有するコンテンツに限れば、必須イベントハンドラといえる。
そしてinput要素がひとつということも考えにくく、複数のinput要素から構成されることが予想される。たとえばログインフォームにしても、メールアドレスとパスワード、ログイン保持などが考えられるが、そのどれもstate変化によって成り立つ。
すなわちonChangeハンドラが必要となるが、それぞれでコールバック関数を定義していては効率が悪い。複数input要素があっても、ひとつのコールバック関数が処理できれば、もっとも効率がよいというものだろう。
コールバック関数の書き方
さて主題が、React Hooksを活用したコンポーネントにおける複数onChangeハンドラを処理する書き方だった。
React Hooksでstate管理するならば、おのずとFunctional Component設計になる。React Hooksは、旬なアーキテクチャであるが、Class componentで設計しなければならないケースもあることだろう。
したがってFunctional componentとClass componentの書き方を用意することにした。興味があれば目を通してみてほしい。
Class component
class App extends React.Component {
constructor(props) {
super(props);
this.state = {
user_name: "",
email: ""
};
this.handleInputChange = this.handleInputChange.bind(this);
}
handleInputChange(e) {
const target = e.target;
const value = target.type === "checkbox" ? target.checked : target.value;
const name = target.name;
this.setState({
[name]: value
});
}
render() {
const { user_name, email } = this.state;
return (
<>
<input
type="text"
name="user_name"
defaultValue={user_name}
onChange={this.handleInputChange}
/>
<input
type="text"
name="email"
defaultValue={email}
onChange={this.handleInputChange}
/>
</>
);
}
}
Functional component
function App() {
const [values, setValues] = useState({
user_name: "",
email: ""
});
function handleInputChange(e) {
const target = e.target;
const value = target.type === "checkbox" ? target.checked : target.value;
const name = target.name;
setValues({ ...values, [name]: value });
}
return (
<>
<input
type="text"
name="user_name"
defaultValue={values.user_name}
onChange={handleInputChange}
/>
<input
type="text"
name="email"
defaultValue={values.email}
onChange={handleInputChange}
/>
</>
);
}
まとめ
Class component、Functional componentともに、大した差はないことが分かると思う。
イベントが発生したinput要素のname属性をstate名として、value属性をstate値として扱っている。果たして、stateを一元処理することになるわけである。
このエントリーが、あなたのクリエイティビティを刺激するものであると期待したい。