【JS】Reactコンポーネントの引数の書き方いろいろ
こんにちは!お盆はゆっくり過ごせましたか?僕はCoffeeScriptのお墓参りに行ってきました。Mizutani(@sirycity)です。
今日はReactコンポーネントの引数の書き方をいろいろ見ていきます。
Reactのコンポーネントって?
Reactコンポーネントってのはこういうやつね!親コンポーネントと子コンポーネントを書いてみるよ。
import { Child } from './path/to/Child.jsx'
const Parent = () => (
<div>
親です。
<Child />
</div>
)
export const Child = () => <div>子です。</div>
こんな感じ!ただ今回は引数の書き方がテーマだし、関係ない部分は省略して書くね。こんな感じに。
<Child />
const Child = () => <div>子です。</div>
色々な書き方
簡単なやつ
いっちばん簡単な引数の渡し方はこう!簡単だね。
<Child name="たかし" />
const Child = props => <div>僕の名前は{props.name}です!</div>
めっちゃ簡単。親側の引数を定数にしてみよう。こんな風にもできるよ。
const name = 'たかし'
<Child name={name}/>
const Child = props => <div>僕の名前は{props.name}です!</div>
もう少しすっきり書くために子ども側の引数を分割代入で書いてみよう!
const name = 'たかし'
<Child name={name}/>
const Child = ({ name }) => <div>僕の名前は{name}です!</div>
いい感じ!分割代入を完璧に理解すればReactコンポーネントはめっちゃ綺麗に書ける。まじで。
じゃあ次に受け取った引数によって分岐するパターン!これも簡単よ。
const isTakashi = true
<Child isTakashi={isTakashi}/>
const Child = ({ isTakashi }) => (
<div>僕の名前は{isTakashi ? 'たかし' : 'たかしじゃない'}です!</div>
)
ちなみに上の例だと引数がtrueになってるけど、Reactコンポーネントは引数をtrueにするとかなり綺麗に書けるよ!↓この例を見れば一目瞭然。
<Child isTakashi />
const Child = ({ isTakashi }) => (
<div>僕の名前は{isTakashi ? 'たかし' : 'たかしじゃない'}です!</div>
)
今まで親側の引数はconst xxx=yyy
とxxx={xxx}
の2つを書いてたけど、なんと引数がtrueならxxxだけでok!だいぶシンプルになるね!さらに子ども側の書き方をちょっと変えてnullish coalescing(?.みたいなやつ)を使うことで、親側の引数あり/なしで子ども側でbooleanを表現できたりもします。こんな感じ。
<Child isTakashi />
<Child />
const Child = props => (
<div>僕の名前は{props?.isTakashi ? 'たかし' : 'たかしじゃない'}です!</div>
)
そこそこ難しいやつ
引数を配列にしてみます。こんな感じ!
const names = ['かわむら', 'たかし']
<C names={names}/>
const C = ({ names }) => <div>僕の名前は{names[0] + names[1]}です!</div>
特にややこしいこともなく、普通の関数と一緒ですね!名前が名古屋市長になっとるがね
オブジェクトでも同じような感じ!
const names = {
lastName: 'かわむら',
firstName: 'たかし',
}
<C names={names}/>
const C = ({ names }) => (
<div>僕の名前は{names.lastName + names.firstName}です!</div>
)
もう少し簡潔に書くために子ども側をさらに分割代入します。配列とオブジェクトそれぞれこんな感じ!
const names = ['かわむら', 'たかし']
<C names={names}/>
const C = ({ names: [lastName, firstName] }) => (
<div>僕の名前は{lastName + firstName}です!</div>
)
const names = {
lastName: 'かわむら',
firstName: 'たかし',
}
<C names={names}/>
const C = ({ names: { lastName, firstName } }) => (
<div>僕の名前は{lastName + firstName}です!</div>
)
さらにさらに簡潔に!子ども側に別名を付けます。配列とオブジェクトそれぞれこう。
const names = ['かわむら', 'たかし']
<C names={names}/>
const C = ({ names: [l, f] }) => <div>僕の名前は{l + f}です!</div>
const names = {
lastName: 'かわむら',
firstName: 'たかし',
}
<C names={names}/>
const C = ({ names: { lastName: l, firstName: f } }) => (
<div>僕の名前は{l + f}です!</div>
)
もう少し難しいやつ
今までは引数が1つでしたが、↑これらは引数が2つでもいっしょです。今までは河村市長が出てたので大村知事を追加してみましょう。こんなこと現実でやったら大変なことになるね。配列とオブジェクトの2バージョンでどうぞ。
const name1 = ['かわむら', 'たかし']
const name2 = ['おおむら', 'ひであき']
<C name1={name1} name2={name2}/>
const C = ({ name1: [l1, f1], name2: [l2, f2] }) => (
<div>
市長の名前は{l1 + f1}です! 知事の名前は{l2 + f2}です!
</div>
)
const name1 = {
lastName: 'かわむら',
firstName: 'たかし',
}
const name2 = {
lastName: 'おおむら',
firstName: 'ひであき',
}
<C name1={name1} name2={name2}/>
const C = ({
name1: { lastName: l1, firstName: f1 },
name2: { lastName: l2, firstName: f2 },
}) => (
<div>
市長の名前は{l1 + f1}です! 知事の名前は{l2 + f2}です!
</div>
)
うん、だいぶ綺麗になったね!もうこれ以上は綺麗にできないかな?
…そんなことはございません!今までは子ども側を改良してきたけど親側にもう1個無駄っぽい所がありますよね!そう、xxx={xxx}
の所です。キーと値が同じ名前なのにわざわざ2回書くのはめんどくさいですね。最初の方の例で引数がtrueだと簡潔に書けるってのは紹介したけど、普通の引数でもきれいに書きたいよね。
そんな悩みに答えるのがスプレッド構文を利用した書き方。刮目せよ。
const name1 = ['かわむら', 'たかし']
const name2 = ['おおむら', 'ひであき']
<C {... {name1, name2}}/>
// 上と同じなので省略
const name1 = {
lastName: 'かわむら',
firstName: 'たかし',
}
const name2 = {
lastName: 'おおむら',
firstName: 'ひであき',
}
<C {... {name1, name2}}/>
// 上と同じなので省略
キーと値が同じ場合は{ ... { 名前1, 名前2, 名前3, }}
みたいにすることでさらに短く書けます。もうなんかモダンJSの見本市みたいになってるね。このスプレッド構文を使った引数の取り方は汎用性の化け物です。キーと値の名前が違ってもこんな風に書けたり、
const city = ['かわむら', 'たかし']
const pref = ['おおむら', 'ひであき']
<C {... {name1: city, name2: pref}}/>
classNameやstyleとかを混ぜたりもできます。まあこれはやりすぎ注意だけど。
const name1 = ['かわむら', 'たかし']
const name2 = ['おおむら', 'ひであき']
<C {... {name1, name2, className: 'foo', style: {color: 'pink'}}}/>
さいごに
Reactコンポーネントの引数の書き方色々でした。ReactはただのJSなので本当に何でもありですね!無法地帯にならない程度にJSを楽しみましょう!以上。