ColumnScope Modifier as a parameter of a composable

Viewed 1700

I'm making a compose scaffold-like composable which contains a text composable. I want the scaffold to have a modifier parameter for the text. I would like to be able to pass a modifier from ColumnScope, for instance to be able to align the text.

Here is a simplified version of the scaffold:

@Composable
fun MyScaffold(
    text: String,
    modifier: Modifier,
) {
    Text(
        modifier = modifier,
        text = text
    )
}

When calling the Scaffold, I want to pass a modifier so that the text will be horizontally aligned:

@Preview
@Composable
fun PreviewScaffold() {
    MyScaffold(
        text = "Hello",
        modifier = Modifier.align(Alignment.CenterHorizontally)
    )
}

However this doesn't compile, because the align() method is an extension function in the ColumnScope so it only works when inside the ColumnsScope.

How can I pass a ColumnScope Modifier as a parameter of MyScaffold?

Please note that an alternative would be to pass a whole Text composable in the scaffold instead of just a string, but I'd rather have just a string so that I can make most of the styling inside the scaffold but just give the outside caller the possibility to override it.

Thanks!

1 Answers

You can scope your composable with the required scope:

@Composable
fun ColumnScope.MyScaffoldX(
    text: String,
    modifier: Modifier,
) {
    Text(
        modifier = modifier.align(Alignment.CenterHorizontally),
        text = text
    )
}

and then use it with:

Column() {
    MyScaffoldX(text = "Hello")
}

Otherwise you can have the Modifier parameter in your composable as in your example:

@Composable
fun MyScaffold(
    text: String,
    modifier: Modifier = Modifier,
) {
    Text(
        modifier = modifier,
        text = text
    )
}

using it with:

Column() {
    MyScaffold(
        text = "Hello",
        modifier = Modifier.align(Alignment.CenterHorizontally)
    )
}
Related