Preview was unable to find a compositionlocal
1 min readJul 22, 2023
I am using staticCompositionLocalOf, to provide LocalNavController and LocalSnackBarHostState
val LocalNavController = staticCompositionLocalOf<NavHostController> {
error("No LocalNavController provided")
}
val LocalSnackBarHostState = staticCompositionLocalOf<SnackbarHostState> {
error("No LocalScaffold provided")
}
In the @Composable function, I’m trying to access the local values:
@Composable
fun FirstScreen() {
val navController: NavController = LocalNavController.current
val snackBarHostState = LocalSnackBarHostState.current
Column(modifier = Modifier.fillMaxSize(),
horizontalAlignment = Alignment.CenterHorizontally)
{
// other code
}
}
When I try to render the preview, it fails with the message "This preview was unable to find a CompositionLocal. You might need to define it so it can render correctly."
@Preview(showSystemUi = true, showBackground = true)
@Composable
fun FirstScreenPreview() {
FirstScreen()
}
One solution is to put the preview inside CompositionLocalProvider like this:
@Preview(showSystemUi = true, showBackground = true)
@Composable
fun FirstScreenPreview() {
CompositionLocalProvider(
LocalNavController provides rememberNavController(),
LocalSnackBarHostState provides remember { SnackbarHostState() },
){
FirstScreen()
}
For a simplicity, we can create a wrapper component,
@Composable
fun ComposeLocalWrapper(content: @Composable () -> Unit) {
CompositionLocalProvider(
LocalNavController provides rememberNavController(),
LocalSnackBarHostState provides remember { SnackbarHostState() },
content = content
)
}
This wrapper can be used in all of your project’s previews:
@Preview(showSystemUi = true, showBackground = true)
@Composable
fun FirstScreenPreview() {
ComposeLocalWrapper{
FirstScreen()
}