Emoji2 emojipicker inside compose ModalBottomSheet doesn't scroll
Asked Answered
A

2

9

I need to use the emoji2-emojipicker from androidx which is made like so with XML views:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">

    <androidx.recyclerview.widget.RecyclerView
        android:id="@+id/emoji_picker_header"
        android:layout_width="wrap_content"
        android:layout_height="@dimen/emoji_picker_header_height"
        android:paddingEnd="@dimen/emoji_picker_header_padding"
        android:paddingStart="@dimen/emoji_picker_header_padding" />

    <androidx.recyclerview.widget.RecyclerView
        android:id="@+id/emoji_picker_body"
        android:layout_width="match_parent"
        android:layout_height="match_parent" />
</LinearLayout>

(Sources https://github.com/androidx/androidx/tree/androidx-main/emoji2/emoji2-emojipicker and https://developer.android.com/jetpack/androidx/releases/emoji2)

And I'm using it like this in compose:

AndroidView(
    factory = { context ->
        EmojiPickerView(context)
    },
    modifier = Modifier
        .fillMaxWidth()
        .height(300.dp)
)

Using the emoji picker on a normal surface like a scaffold or column has no issues, it scrolls perfectly fine and doesn't lag.

If I instead put the emoji picker in another scrollable composable, like a ModalBottomSheet, it doesn't scroll anymore.
To make it scroll I need to add the verticalScroll(rememberScrollState()) modifier to the AndroidView but that makes it laggy and takes a long time to load + the emoji tabs don't work for some reason if I make it scrollable like that.
I guess it's laggy because I'm telling the RecyclerView that it has infinite height and so it renders all the emojis at once instead of doing it lazily.

Reading around SO it seems like the scroll events don't propagate properly trough child-parent composables when the RecyclerView is inside another scrollable composable. Any suggestion on how to work around this?

Here is a demo, showing one screen where it works fine (tasks screen) and one where it doesn't in a ModalBottomSheet: https://drive.google.com/file/d/1vU94uPwBTtpDg8hb0JauqZmw-LHyP9Mz/view?usp=sharing (in this video I added the verticalScroll modifier in the ModalBottomSheet emojipicker to make it scrollable otherwise it wouldn't scroll, while the one in Tasks doesn't have that modifier)

Archdiocese answered 22/6, 2023 at 10:11 Comment(0)
V
0

To ensure scroll inside bottom sheet, set the recycler or view you want to scroll with

recycler.isNestedScrollingEnabled = true
Vally answered 6/11, 2023 at 19:18 Comment(2)
this answer had a bit truth in it, but doesn't really solves OP's problemAmphibiotic
Yeah didn't solve it :/Archdiocese
C
0

What worked for me, it's a bit laggy... but better than the laggy option the author mentions:

// assume that sheetState is hoisted ...

val scrollModifier = if (sheetState.currentValue == SheetValue.Expanded) {
    Modifier.verticalScroll(rememberScrollState())
  } else {
    Modifier
  }

  AndroidView(
    modifier = Modifier
      .fillMaxWidth()
      .then(scrollModifier),
   factory = {...},
)

This way, the lag is only produced when the bottom sheet is full expaned, and just for a few seconds.

Compurgation answered 6/9, 2024 at 19:7 Comment(0)

© 2022 - 2025 — McMap. All rights reserved.