I am trying to animate DropdownMenu with a modifie...
# compose-android
a
I am trying to animate DropdownMenu with a modifier
animateContentSize(tween())
when
DropdownMenuItem
count changes as suggested in
5 Quick Animations to Make Your Compose App Stand Out
(

link

) But the animation is stuttering or not that smooth(the video is attached for the release build). Code is mentioned in the 🧵 is there a way to make it more smoother?
Copy code
package com.example.composelistrecomposition

import android.os.Bundle
import androidx.activity.ComponentActivity
import androidx.activity.compose.setContent
import androidx.compose.animation.animateContentSize
import androidx.compose.animation.core.tween
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Row
import androidx.compose.material3.Button
import androidx.compose.material3.DropdownMenu
import androidx.compose.material3.DropdownMenuItem
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableIntStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.setValue
import androidx.compose.runtime.snapshots.SnapshotStateList
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.unit.dp

/**
 * For animation in drop down
 */
class MainActivity3 : ComponentActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            AnimateDropDown()
        }
    }
}

@Composable
private fun AnimateDropDown() {
    DropdownMenu(
        modifier = Modifier.animateContentSize(tween()),
        expanded = true,
        onDismissRequest = { /*TODO*/ }
    ) {
        val list = remember {
            SnapshotStateList<String>()
        }
        var count by remember {
            mutableIntStateOf(0)
        }
        Row(
            verticalAlignment = Alignment.CenterVertically,
            horizontalArrangement = Arrangement.spacedBy(8.dp)
        ) {
            Text("Add/Remove")
            Button(onClick = { count++; list.add("Item $count") }) {
                Text(text = "+")
            }
            Button(enabled = count > 0, onClick = { count--; list.removeLast() }) {
                Text(text = "-")
            }
        }
        list.forEach {
            DropdownMenuItem(text = { Text(it) }, onClick = { /*TODO*/ })
        }
    }
}
When I tried the same in KMM on a desktop this animation was way smoother(attaching the clip of some other code)
j
Out of curiosity have you tried using a LazyColumn?
a
Not related to the the original question, but we can't use
LazyColumn
in
DropdownMenu
see https://issuetracker.google.com/issues/242398344 But anyway even with normal column animation should be smooth and should not require LazyColoumn
j
You can build your own dropdown menu using a Popup. I had to do this in my own project because the Material version UI constraints that classed with my Apps UX.
a
I think you are basing your assumption incorrectly or you couldn't understand the original problem statement. I don't want LazyList as I don't have many items so it's not about lazyList in the dropdown menu. Rather I am pointing out that animation in
DropdownMenu
is not working smoothly I have attached the video for the same kind of UI using Popup as below. It suffers from the same problem
Copy code
@Composable
private fun AnimateDropDownUsingCustomBlue() {
    Popup {
        Column(
            modifier = Modifier
                .background(color = Color.Blue)
                .animateContentSize(tween())
        ) {
            val list = remember {
                SnapshotStateList<String>()
            }
            var count by remember {
                mutableIntStateOf(0)
            }
            Row(
                verticalAlignment = Alignment.CenterVertically,
                horizontalArrangement = Arrangement.spacedBy(8.dp)
            ) {
                Text("Add/Remove")
                Button(onClick = { count++; list.add("Item $count") }) {
                    Text(text = "+")
                }
                Button(enabled = count > 0, onClick = { count--; list.removeLast() }) {
                    Text(text = "-")
                }
            }
            LazyColumn {
                items(list) {
                    Text(
                        modifier = Modifier
                            .height(64.dp)
                            .padding(8.dp),
                        text = it,
                        fontSize = 18.sp
                    )
                }
            }
        }
    }
}
j
I understand your original point. My theory is maybe LazyList could provide a smoother animation.
I’ve tested your code and the animation looks smooth to me
Here it is using the parent column
This is using the DropDownMenu composable
I think the issue may be with your emulator. Have you tested using a live device?
a
I am testing this in Samsung Note9, which is OLD but not that much. Let me test this in few other device and update this thread
j
If testing on a test profile, remember that performance is effected by debug builds.
Try generating a baseline profile as well
a
As mentioned earlier, these videos are in a release build and these projects are sample projects so the baseline profile will not matter much. I am more inclined to the fact that either that device has some issue or Popup implementation doesn't work well in older devices