
Embedded games in mobile apps: Make your app more attractive

20. Sep 2021
AndroidSnackbar is UI component that provides brief message at the bottom of the screen. It is used to inform users that app has performed action or will perform action. Only one snackbar can be used at a time and has to contain only single action which is optional.
This simple component consist of message (1), container (2) and optional action button (3). Message can be maximally 2 lines long.
In Jetpack Compose there is composable function named Snackbar. It's just visual representation of snackbar as defined in Material design guidelines, without show or hide options and without animations. Usually you will need to use SnackbarHost.
This component is responsible for showing(or hiding snackbar after defined time) and it's fade animations. Simply said, SnackbarHost is wrapper of Snackbar mentioned above. It takes 3 parameters
@Composable
fun SnackbarHost(
hostState: SnackbarHostState,
modifier: Modifier = Modifier,
snackbar: @Composable (SnackbarData) -> Unit = { Snackbar(it) }
)
As descriptive name of class suggest, it is used to control state of SnackbarHost. As Material design guideline mentions, only one snackbar should be showed at a time, others are queued and will show later by SnackbarHostState.
Only mandatory parameter of SnackbarHostState is hostState that can be obtained simply by it's constructor. Then you can just place SnackbarHost wherever you want. But snackbar still doesn't show, so how to do that?
val snackbarHostState = remember { SnackbarHostState() }
.
.
.
SnackbarHost(hostState = snackbarHostState)
Snackbar is showed as reaction on something. In our case "something" is click on button. ShowSnackbar is suspend function thus coroutine scope is needed. You need to remember coroutine scope outside of onClick function because when the scope is cancelled the snackbar is removed from the queue.
@Composable
fun SnackbarScreen() {
val scope = rememberCoroutineScope()
val snackbarHostState = remember { SnackbarHostState() }
.
.
.
FloatingActionButton(
onClick = {
//Important part here
scope.launch {
snackbarHostState.showSnackbar("Hello there")
}
//
},
content = { Icon(imageVector = Icons.Default.Add, contentDescription = "") }
)
SnackbarHost(hostState = snackbarHostState)
}
Key here is to modify snackbar parameter of SnackbarHost. Without our modification default Snackbar composable is used. With code below, our design of snackbar is used but default behavior of snackbar is retained.
SnackbarHost(
modifier = Modifier.align(Alignment.BottomCenter),
hostState = snackbarHostState,
snackbar = { snackbarData: SnackbarData ->
Card(
shape = RoundedCornerShape(8.dp),
border = BorderStroke(2.dp, Color.White),
modifier = Modifier
.padding(16.dp)
.wrapContentSize()
) {
Column(
modifier = Modifier.padding(8.dp),
verticalArrangement = Arrangement.spacedBy(4.dp),
horizontalAlignment = Alignment.CenterHorizontally
) {
Icon(imageVector = Icons.Default.Notifications, contentDescription = "")
Text(text = snackbarData.message)
}
}
}
)