Home > Net >  The wrong "items" funciton is being selected by lazy row unless i specifically import &quo
The wrong "items" funciton is being selected by lazy row unless i specifically import &quo

Time:01-22

So im trying to follow an example from jetpack compose for lazyrows

When creating the lazy row object unless i specify this import: import androidx.compose.foundation.lazy.items

the items function inside the lazyrow function throws this error: Type mismatch: inferred type is List<DrawableStringPair> but Int was expected

I believe its going to a different function based on the inputs, but im trying to figure out why the import statement above fixes it. All of the "items" functions are defined within the same file "LazyDsl.kt"

I guess my question is, how does the import above specify that its This function:

inline fun <T> LazyListScope.items(
    items: List<T>,
    noinline key: ((item: T) -> Any)? = null,
    noinline contentType: (item: T) -> Any? = { null },
    crossinline itemContent: @Composable LazyItemScope.(item: T) -> Unit
) = items(

and not this one:

fun items(
    count: Int,
    key: ((index: Int) -> Any)? = null,
    contentType: (index: Int) -> Any? = { null },
    itemContent: @Composable LazyItemScope.(index: Int) -> Unit
) {
    error("The method is not implemented")
}

Data:

private val alignYourBodyData = listOf(
    R.drawable.ab1_inversions to R.string.ab1_inversions,
    R.drawable.ab2_quick_yoga to R.string.ab2_quick_yoga,
    R.drawable.ab3_stretching to R.string.ab3_stretching,
    R.drawable.ab4_tabata to R.string.ab4_tabata,
    R.drawable.ab5_hiit to R.string.ab5_hiit,
    R.drawable.ab6_pre_natal_yoga to R.string.ab6_pre_natal_yoga
).map { DrawableStringPair(it.first, it.second) }

Function causing problems:

@Composable
fun AlignYourBodyRow(
    modifier: Modifier = Modifier
) {
    LazyRow(
        horizontalArrangement = Arrangement.spacedBy(8.dp),
        modifier = modifier
    ) {
        items(alignYourBodyData) { item ->
            AlignYourBodyElement(item.drawable, item.text)
        }
    }
}

Composable function:

@Composable
fun AlignYourBodyElement(
    @DrawableRes drawable: Int,
    @StringRes text: Int,
    modifier: Modifier = Modifier
) {
    Column(
        modifier = modifier,
        horizontalAlignment = Alignment.CenterHorizontally
    ) {
        Image(
            painter = painterResource(drawable),
            contentDescription = null,
            contentScale = ContentScale.Crop,
            modifier = Modifier
                .size(88.dp)
                .clip(CircleShape)
        )
        Text(
            text = stringResource(text),
            style = MaterialTheme.typography.h3,
            modifier = Modifier.paddingFromBaseline(
                top = 24.dp, bottom = 8.dp
            )
        )
    }
}

import that fixes everything: import androidx.compose.foundation.lazy.items

CodePudding user response:

Remove the items(alignYourBodyData) {...} code and its import, and try to type it again yourself!
Then you'll be shown auto-suggestion dialog like this and you can select your function:

video

CodePudding user response:

The import statement import androidx.compose.foundation.lazy.items is specifying that you want to use the items function that is defined within the androidx.compose.foundation.lazy package. This function is specific to the LazyRow composable and it is used to create items in the LazyRow.

Without the import statement, the items function that you are trying to use is inferred as the items function with the different signature that is defined in the same file (LazyDsl.kt) but it does not take a List as an argument, it takes an Int as an argument. This is why you are getting a type mismatch error because the function is expecting an Int as input, but it's receiving a List.

The import statement allows you to avoid confusion between the different item's functions and clearly specify which one you want to use.

CodePudding user response:

It's true that "All of the items functions are defined within the same file LazyDsl.kt". The difference is that the function with count argument is member function of LazyListScope, while the other function with items argument is extension function of LazyListScope.

And by design, you don't need import to call member function of a class, but you need one to call extension function.

To the second question, "How does the import above specify that its this function and not the other one?" - it does not. The import only enables you to call the extension function (all the extension functions called items). The one with count argument is available by default. The correct one is then chosen automatically based on the arguments you provide.

  • Related