【NativeBase】Selectタグのアイテムを選択時に文字色を変更する + 解決アプローチ法
React Nativeでの実装にあたり、UIライブラリとしてNativeBaseを使用しています。
その中でタイトルの通り躓いた箇所の解決法と、余談としてその解決に至った"解決までのアプローチ法"を共有します。
やりたいこと
Selectを開いて中身のItemを選択時に、文字色も変えたい。
(以下、公式例のコード)
const Example = () => {
let [service, setService] = React.useState("");
return <Center>
<Box w="3/4" maxW="300">
<Select
selectedValue={service}
minWidth="200"
accessibilityLabel="Choose Service"
placeholder="Choose Service"
_selectedItem={{
bg: "teal.600",
endIcon: <CheckIcon size="5" />
}} mt={1} onValueChange={itemValue => setService(itemValue)}>
<Select.Item label="UX Research" value="ux" />
<Select.Item label="Web Development" value="web" />
<Select.Item label="Cross Platform Development" value="cross" />
<Select.Item label="UI Designing" value="ui" />
<Select.Item label="Backend Development" value="backend" />
</Select>
</Box>
</Center>;
};
Select内のアイテムを選択すると、上記_selectedItem
内の記述が反映されて、以下のように背景色が付与されます。
これと同様に文字色も変更することが目的です。
試したこと
SelectのPropにcolorを指定すると以下画像のように文字色が変更できるので、同様に_selectedItem
内にcolorを指定したらできるか...と思っていましたが上手くいきませんでした。
SelectにcolorのPropを指定した例
<Select
...
_selectedItem={{
bg: "teal.600",
endIcon: <CheckIcon size="5" />,
}}
mt={1}
onValueChange={(itemValue) => setService(itemValue)}
+ color={'red.400'}
>
_selectedItemにcolorのPropを指定した例
<Select
...
_selectedItem={{
bg: "teal.600",
endIcon: <CheckIcon size="5" />,
+ color:'red.400'
}}
mt={1}
onValueChange={(itemValue) => setService(itemValue)}
>
🤔 🤔 🤔
解決法
_selectedItem内で更に_textのPropとして渡す
_text
のPropの中にcolorを指定することで、アイテムを選択時に指定した色に変更できます。
<Select
...
_selectedItem={{
bg: "teal.600",
endIcon: <CheckIcon size="5" />,
+ _text : {
+ color: "red.400",
+ },
}}
mt={1}
onValueChange={(itemValue) => setService(itemValue)}
>
公式ドキュメントのUtility Props
-> Internal Props
に記載してある、Text childに渡す形式であればOKでした。
またNativeBaseのDevComの方からも、テキストと見出し以外のコンポーネントでテキストのスタイルを変更する場合は、_text
を使用して設定する必要があるとのことでした。
無事に解決です。
お疲れ様でした🤗
余談:今回の課題解決までのアプローチの仕方
今回の例はUIライブラリの概念を理解していたり、NativeBase等UIライブラリを普段から使っていたらすぐに解決できるかもしれません。
しかしまだ使い倒せていなかったり、そもそもやりたいことに対して情報がドキュメントにもweb上にも共有されていなかった場合、解決法が迷子になってしまいます。
今回の例では、解決するのにGitHubにある元のライブラリのソースコードを紐解きました。
どのようなコードで成り立っていて、どのような仕組みで動いているか把握することで、一つ一つの流れを掴み最終的な目的の課題を解決することができます。
これは様々な場面で役に立つと思うので、今回はシンプルな例ですが「こんな風に考えたらいけるやん!」と課題解決の流れを掴める例として見てもらえると、いずれ役に立つのかなと思います。
今回の紐解き例
NativeBaseのSelectItemがどのような構造になっているか見る
やりたいことのゴールとしては、SelectItem
に入っているテキストが選択時に色が変わることです。つまりテキストのカラーを指定するために、どこでどのようなPropを渡せば良いのか探りに行きます。
SelectItem
のコードを見てみると、Actionsheet
を返しているようです。
次はこのActionsheet
がどのようになっているか見にいきます。
NativeBaseのActionsheetがどのような構造になっているか見る
Actionsheet
を見てみると、今度はButton
を返しています。
次はButton
のコードを見ましょう。
NativeBaseのButtonがどのような構造になっているか見る
どうやらBox
の中にテキストが入ってそうですね。スタイリング関係はそのBox
のPropにある_text
が何だか怪しそう。
そもそもButton
の文字色を変更する場合はどのようにするのか。ここで公式ドキュメントのButton
を見にいきます。
公式ドキュメントのButtonの項目を見る
これだ🤯
Select.Item
はButton
で構成されており、テキストの色を変更するにはその形に適したPropを渡してあげる必要があったということです。
つまり最初にやろうとしていたのは以下のようにButton
に直接colorのPropを渡していたので、機能していなかったんですね。
return (
<View style={styles.container}>
<Button size="sm" variant={"solid"} px="3" color={'red.400'}>テスト</Button>
</View>
);
まとめ
困ったらまずソースコードとissueを見ることが大事...!
元のソースを見ること自体が中々ハードル高めに感じますが、「どのように動いているのかな」と見てみると案外すっと理解できたり、腑に落ちます。
何かしらお役に立てたら幸いです!
Discussion