複数の入力
入力欄が増えても考え方は同じ
お問い合わせフォームには、名前のほかに「ご用件」の選択肢と「本文」の欄が要ります。増えるのは欄の数だけで、やることは前回と変わりません。欄 1 つにつき state 1 つ、value と onChange を 1 組、これを繰り返します。
const [name, setName] = useState("");
const [kind, setKind] = useState("仕事のご依頼");
const [body, setBody] = useState("");textarea は中身を value で渡す
素の HTML では、textarea の初期値を開始タグと終了タグのあいだに書きました。React ではそう書きません。input と同じく value を使います。
<textarea id="body" value={body} onChange={(e) => setBody(e.target.value)} />書き方をそろえたのは React の設計上の判断です。おかげで input でも textarea でも、覚えることは value と onChange の 1 組だけで済みます。
select も selected ではなく value
素の HTML では、選ばれている項目に selected を付けました。React では select 自体に value を持たせ、その値と一致する option が選択状態になります。
<select id="kind" value={kind} onChange={(e) => setKind(e.target.value)}>
<option value="仕事のご依頼">仕事のご依頼</option>
<option value="勉強会のお誘い">勉強会のお誘い</option>
<option value="その他">その他</option>
</select>選ばれるのは option の value なので、state の初期値も option のどれかの value と同じ文字列にします。ここがずれていると、最初は何も選ばれていない状態で表示されます。
変更の受け取り方は 3 つとも同じ
input でも textarea でも select でも、onChange のハンドラで見るのは e.target.value です。チェックボックスだけは例外で、こちらは e.target.checked を見ます。真偽値だからです。
つまずきどころ
- textarea を
<textarea>{body}</textarea>と書くと React が警告を出します。value で渡します - option 側に selected を書くと警告になります。select の value で決めます
- state を 1 つにまとめてオブジェクトで持つやり方もありますが、まずは欄ごとに分けるほうが読みやすいです
演習
ご用件の選択と本文の欄を、state とつなぎます。