How do you create a LazyColumn composible with Button that Toggles

48 Views Asked by At

I have a LazyColumn that has a Button that I would like to Toggle when pressed, how do you implement this in Android?

This is what I have at the moment:

    LazyColumn (
        verticalArrangement = Arrangement.spacedBy(10.dp),
        modifier = Modifier
            .padding(horizontal = 10.dp, vertical = 10.dp)
    )
    {
        items(filtered) { sound ->
            Row {
                // Share Button
                IconToggleButton(
                    checked = false,
                    onCheckedChange = {
                        if (SoundService.isPlaying()) {
                            Toast.makeText(baseContext, "Stop playing", Toast.LENGTH_SHORT).show()
                            val intent = Intent(baseContext, SoundService::class.java).also {
                                it.action = SoundService.Actions.STOP.toString()
                                baseContext?.startForegroundService(it)
                            }
                        }
                        else {
                            Toast.makeText(baseContext, "play: " + sound, Toast.LENGTH_SHORT).show()

                            val projectDirAbsolutePath = baseContext?.filesDir?.toPath()

                            val file = projectDirAbsolutePath?.toString() + "/" + sound

                            val intent = Intent(baseContext, SoundService::class.java).also {
                                it.action = SoundService.Actions.START.toString()
                                it.putExtra("sound", file);
                                baseContext?.startForegroundService(it)
                            }
                        }
                    },
                    modifier = Modifier
                        .align(Alignment.CenterVertically)
                )
                {
                    Icon(Icons.Filled.PlayArrow, contentDescription = null)
                }
                Text(text = sound, fontWeight = FontWeight.Bold, fontSize = 24.sp, modifier = Modifier.align(Alignment.CenterVertically))
            }
        }
    }

I have tried IconButton and am now looking at IconToggleButton, so far I have not been able to find an answer...

2

There are 2 best solutions below

0
Chirag Thummar On

Here is a solution for the Toggle button state in LazyColumn. You need to have a data class which will save the current state of IconToggleButton which we will use for the showing Data based on that.

When a user clicks on the toggle button we will match it with the current index and make it selected and other items deselected.

Preview

preview

Complete Code

data class ToggleItem(
    val text: String, val isSelected: Boolean = false
)

@Preview
@OptIn(ExperimentalMaterial3Api::class)
@Composable
fun Stack033(modifier: Modifier = Modifier) {

    val list = listOf(
        CheckedItem("Item A", false),
        CheckedItem("Item B", false),
        CheckedItem("Item C", false),
        CheckedItem("Item D", false),
        CheckedItem("Item E", false),
        CheckedItem("Item F", false),
        CheckedItem("Item G", false)
    )

    var useList by remember {
        mutableStateOf(list)
    }

    Scaffold(topBar = {
        TopAppBar(title = {
            Text(text = "Toggle Select Demo")
        })
    }) { padding ->
        LazyColumn(
            modifier = Modifier
                .padding(padding)
                .fillMaxSize()
        ) {
            items(useList.size) { i ->

                Row(
                    modifier = Modifier.padding(0.dp),
                    verticalAlignment = Alignment.CenterVertically
                ) {
                    Text(text = "${useList[i].text}${if (useList[i].isSelected) " Playing" else ""}")
                    Spacer(modifier = Modifier.weight(1f))
                    IconToggleButton(checked = useList[i].isSelected, onCheckedChange = {
                        useList = useList.mapIndexed { j, item ->
                            if (i == j) {
                                item.copy(isSelected = it)
                            } else {
                                item.copy(isSelected = false)
                            }
                        }
                    }) {
                        Icon(
                            if (useList[i].isSelected) Icons.Filled.Stop else Icons.Filled.PlayArrow,
                            contentDescription = null
                        )
                    }
                }

            }
        }
    }
}
0
龚诗豪 On

It is easy to implement for you to create a boolean state in your item composition.

            val toggleState = remember {
            mutableStateOf(false)
        }

        fun toggle(){
            toggleState.value= !toggleState.value
        }

        if (toggleState.value)
            Text(text = "pressed", modifier = Modifier.clickable { toggle() })
        else
            Text(text = "click me ", modifier = Modifier.clickable { toggle() })