BasicTextFieldを使って、TextFieldをカスタマイズする
BasicTextFieldを使って、TextFieldをカスタマイズする
前提
- version
- Kotlin 1.5.31
- Jetpack Compose 1.0.5
概要
Jetpack Composeで文字の入力を行う場合、基本的にはTextFieldを使うことになると思います。
多機能で非常に使いやすいComposableですが、現状ではTextField内のPaddingを変更することができません。
そのため、TextFieldの機能を超えてカスタマイズしたい場合は、BasicTextFieldを使うことになるでしょう。実際にBasicTextFieldを使った一例をメモしておきます。
内容
Paddingを可変とする方法
decorationBoxというコールバックの引数が存在します。
そしてdecorationBoxのコールバックの引数にはinnerTextFieldが渡ってくるため、
innerTextFieldをラップすることでPaddingをつけることができます。
BasicTextField(
value = "",
onValueChange = {},
decorationBox = { innerTextField ->
Box(Modifier.padding(10.dp)) {
innerTextField()
}
}
)
PlaceHolderをつけて、LeadingにIconを配置する
こちらもdecorationBox内で、任意のComposableを用いることで実現できます。
今回はLeading側にIconが欲しいため、Rowで配置します。
PlaceHolderはMutableStateの状態を確認し判断した上で、出し分けるようにすることでPlaceHolderが表示できます。
@Composable
fun LeadingIconTextFieldWithPlaceHolder() {
val text = remember {
mutableStateOf("")
}
BasicTextField(
value = text.value,
onValueChange = {
text.value = it
},
decorationBox = { innerTextField ->
Row {
Icon(painterResource(id = R.drawable.ic_home), contentDescription = "home")
if (text.value.isEmpty()) {
Text(text = "PlaceHolder")
} else {
innerTextField()
}
}
}
)
}
まとめ
今回、メモした内容は簡易的な一例ですが、手軽にCustomizeできて非常に良いですね。
ただ、BasicTextFieldはTextFieldよりも低レイヤーなComponentであるため、ある程度自身で振る舞いを決める必要がありそうです。
デザインなどMaterialDesignなどに準拠したもので良い場合はTextfieldを使用し、
挙動やデザインを変更したい場合は、BasicTextfieldを使うのが良いかなと思いました。
また、複雑なレイアウトなどしたい場合は、TextFieldの実装を見にいくと参考になりそうです。
参考
Discussion