Migrate AvatarActionBottomSheet to Material3 BottomSheet

Also correctly handle the back press when this bottom sheet is opened, previously it was leaving the room edition screen.
ModalBottomSheetLayout can now be deleted.
This commit is contained in:
Benoit Marty 2024-05-15 16:20:47 +02:00
parent fb7eb924d8
commit bb48bb7531
5 changed files with 58 additions and 207 deletions

View file

@ -14,25 +14,26 @@
* limitations under the License.
*/
@file:OptIn(ExperimentalMaterialApi::class)
@file:Suppress("UsingMaterialAndMaterial3Libraries")
@file:OptIn(ExperimentalMaterial3Api::class)
package io.element.android.libraries.matrix.ui.components
import androidx.activity.compose.BackHandler
import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.imePadding
import androidx.compose.foundation.layout.navigationBarsPadding
import androidx.compose.foundation.lazy.LazyColumn
import androidx.compose.foundation.lazy.items
import androidx.compose.material.ExperimentalMaterialApi
import androidx.compose.material.ModalBottomSheetState
import androidx.compose.material.ModalBottomSheetValue
import androidx.compose.material3.ExperimentalMaterial3Api
import androidx.compose.material3.MaterialTheme
import androidx.compose.material3.rememberModalBottomSheetState
import androidx.compose.runtime.Composable
import androidx.compose.runtime.MutableState
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.rememberCoroutineScope
import androidx.compose.ui.Modifier
import androidx.compose.ui.platform.LocalDensity
import androidx.compose.ui.res.stringResource
import io.element.android.compound.theme.ElementTheme
import io.element.android.libraries.designsystem.components.list.ListItemContent
@ -41,42 +42,53 @@ import io.element.android.libraries.designsystem.preview.PreviewsDayNight
import io.element.android.libraries.designsystem.theme.components.IconSource
import io.element.android.libraries.designsystem.theme.components.ListItem
import io.element.android.libraries.designsystem.theme.components.ListItemStyle
import io.element.android.libraries.designsystem.theme.components.ModalBottomSheetLayout
import io.element.android.libraries.designsystem.theme.components.ModalBottomSheet
import io.element.android.libraries.designsystem.theme.components.Text
import io.element.android.libraries.designsystem.theme.components.hide
import io.element.android.libraries.matrix.ui.media.AvatarAction
import kotlinx.collections.immutable.ImmutableList
import kotlinx.collections.immutable.persistentListOf
import kotlinx.coroutines.launch
@OptIn(ExperimentalMaterial3Api::class)
@Composable
fun AvatarActionBottomSheet(
actions: ImmutableList<AvatarAction>,
modalBottomSheetState: ModalBottomSheetState,
isVisible: MutableState<Boolean>,
onActionSelected: (action: AvatarAction) -> Unit,
modifier: Modifier = Modifier,
) {
val coroutineScope = rememberCoroutineScope()
fun onItemActionClicked(itemAction: AvatarAction) {
onActionSelected(itemAction)
coroutineScope.launch {
modalBottomSheetState.hide()
}
val sheetState = rememberModalBottomSheetState(
skipPartiallyExpanded = true
)
BackHandler(enabled = isVisible.value) {
sheetState.hide(coroutineScope, then = { isVisible.value = false })
}
ModalBottomSheetLayout(
modifier = modifier,
sheetState = modalBottomSheetState,
displayHandle = true,
sheetContent = {
AvatarActionBottomSheetContent(
actions = actions,
onActionClicked = ::onItemActionClicked,
modifier = Modifier
.navigationBarsPadding()
.imePadding()
)
}
)
fun onItemActionClicked(itemAction: AvatarAction) {
onActionSelected(itemAction)
sheetState.hide(coroutineScope, then = { isVisible.value = false })
}
if (isVisible.value) {
ModalBottomSheet(
onDismissRequest = {
sheetState.hide(coroutineScope, then = { isVisible.value = false })
},
modifier = modifier,
sheetState = sheetState,
content = {
AvatarActionBottomSheetContent(
actions = actions,
onActionClicked = ::onItemActionClicked,
modifier = Modifier
.navigationBarsPadding()
.imePadding()
)
}
)
}
}
@Composable
@ -115,10 +127,7 @@ private fun AvatarActionBottomSheetContent(
internal fun AvatarActionBottomSheetPreview() = ElementPreview {
AvatarActionBottomSheet(
actions = persistentListOf(AvatarAction.TakePhoto, AvatarAction.ChoosePhoto, AvatarAction.Remove),
modalBottomSheetState = ModalBottomSheetState(
initialValue = ModalBottomSheetValue.Expanded,
density = LocalDensity.current,
),
isVisible = remember { mutableStateOf(true) },
onActionSelected = { },
)
}