How to preview LazyPagingItems/Paging 3 Library in Jetpack Compose
Asked Answered
G

3

24

I think the title says it all.

LazyPagingItems constructor is internal. I can't pass LazyPagingItems as parameter in Preview Composable, let alone passing sample data. But I want to show preview of my composable, how should I do this?

@Composable
fun MainUi(users: LazyPagingItems<User>) {
    Scaffold {
        LazyColumn() {
            items(users) {
                // Rest of the code..
            }
        }
    }
}

@Preview
@Composable
fun Preview() {
    DefaultTheme {
        MainUi(users = ) // How to pass sample data here?
    }
}
Goddaughter answered 29/7, 2021 at 6:48 Comment(1)
I believe there's not way to do that now, since LazyPagingItems is based on LaunchedEffect and that seems not to cooperate with PreviewAlliance
P
27

You can use PagingData.empty() or PagingData.from(List<T>), like this:

@Preview
@Composable
fun Preview() {
    DefaultTheme {
        MainUi(users = flowOf(PagingData.from(listOf(User(..)))).collectAsLazyPagingItems()
    }
}

I'm not sure if the items are shown in the preview, but at least you get to render it...

Pantsuit answered 20/9, 2021 at 10:17 Comment(4)
Unfortunately they are not shown in a previewAlliance
Actually I have filled an issue in Google Issue Tracker here. I can get it to build now but the list isn't shown.Goddaughter
Is it at least planned to be fixed in the future? I see the issue tracker doesn't answer at allBraden
They said it's planning for Q2/Q3 2023. Let's hope it won't get magically marked as fixed, again.Carycaryatid
I
5

this is how you can also handle and show page states the page states. refresh, append, prepend.

@Preview
@Composable
fun ScreenContentPreview() {
    ScreenContent(
        Modifier,
        "One Free ticket",
        pageState =
        flowOf(
            PagingData.from(
                listOf(*YOUR_LIST_OF_OBJECT*
                ),
                sourceLoadStates =
                LoadStates(
                    refresh = LoadState.NotLoading(false),
                    append = LoadState.NotLoading(false),
                    prepend = LoadState.NotLoading(false),
                ),
            ),
        ).collectAsLazyPagingItems(),
    )
}

hope this help to someone.

Intercut answered 7/2 at 5:59 Comment(1)
Thank you Google, I've found this answer. LoadStates help with Compose UI testing as well. Otherwise, LoadState.Loading is the initial one.Guinea
D
3

I have not tried this, but there is an example of previewing LazyPagingItems in the paging repository

https://github.com/androidx/androidx/blob/androidx-main/paging/paging-compose/src/androidTest/java/androidx/paging/compose/LazyPagingItemsPreviewTest.kt

@OptIn(ExperimentalCoroutinesApi::class)
@Preview
@Composable
fun PagingPreview() {
    val data = List(50) { it }
    val flow = MutableStateFlow(PagingData.from(data))
    CompositionLocalProvider(
        LocalInspectionMode provides true,
    ) {
        // Use StandardTestDispatcher so we don't start collecting on PagingData
        val lazyPagingItems = flow.collectAsLazyPagingItems(StandardTestDispatcher())
        LazyColumn(Modifier.height(500.dp)) {
            items(count = lazyPagingItems.itemCount) { index ->
                val item = lazyPagingItems[index]
                Spacer(Modifier.height(50.dp).fillParentMaxWidth().testTag("$item"))
            }
        }
    }
}

@OptIn(ExperimentalCoroutinesApi::class)
@Preview
@Composable
fun EmptyPreview() {
    val data = emptyList<Int>()
    val flow = MutableStateFlow(PagingData.from(data))
    CompositionLocalProvider(
        LocalInspectionMode provides true,
    ) {
        // Use StandardTestDispatcher so we don't start collecting on PagingData
        val lazyPagingItems = flow.collectAsLazyPagingItems(StandardTestDispatcher())
        LazyColumn(Modifier.height(500.dp)) {
            items(count = lazyPagingItems.itemCount) { index ->
                val item = lazyPagingItems[index]
                Spacer(Modifier.height(50.dp).fillParentMaxWidth().testTag("$item"))
            }
        }
    }
}
Dialectal answered 25/5, 2023 at 13:28 Comment(2)
This worked fine for me. Also it looks like that the StandardTestDispatcher is not needed, as well as the CompositionLocalProvider.Hoover
I think the sample moved here: github.com/androidx/androidx/blob/androidx-main/paging/…Dialectal

© 2022 - 2024 — McMap. All rights reserved.