基于状态的显示屏幕 - jetpack compose

问题描述 投票:0回答:1

我想根据状态持有者提供的状态显示一个特殊的屏幕。 当应用程序启动时,必须调用 api。 由于这可能需要一段时间,因此应该会显示加载屏幕。 如果请求成功,则显示成功屏幕,否则显示错误消息屏幕。

sealed interface ScreenLoadingState {
    data object Loading : ScreenLoadingState
    data class Success(val data: String) : ScreenLoadingState
    data class Failed(val errorMessage: String) : ScreenLoadingState
}

data class AlbumScreenState(
    val selectedUser: User,
    val albumList: List<Album>,
    val screenLoadingState: ScreenLoadingState = ScreenLoadingState.Loading
)

class AlbumScreenViewModel : ViewModel() {
    private val _uiState: MutableStateFlow<AlbumScreenState> = MutableStateFlow(
        AlbumScreenState(
            selectedUser = User() // from other screen
            albumList = emptyList()
        )
    )
    val uiState: StateFlow<AlbumScreenState> = _uiState.asStateFlow()
}

@Composable
fun AlbumScreen(
    albumScreenViewModel: AlbumScreenViewModel
) {
    val albumScreenState by albumScreenViewModel.uiState.collectAsState()

    when(albumScreenState.screenLoadingState) {
        is ScreenLoadingState.Loading -> {}
        is ScreenLoadingState.Success -> {}
        is ScreenLoadingState.Failed -> {
            val a = albumScreenState.screenLoadingState.errorMessage
        }
    }

}

中的when表达式显示错误, “智能转换为‘ScreenLoadingState.Failed’是不可能的,因为‘albumScreenState.screenLoadingState’是一个复杂的表达式”

为什么这是不可能的? When 表达式检查每个可能的状态。只有这三个选项。如果是Error,那么它就保存着错误信息,那么为什么会出现这个错误以及如何避免这样的问题呢?

顺便问一下,这种结构与密封接口、数据类和视图模型正确还是有更好的解决方案?

感谢您的帮助:-D

kotlin android-jetpack-compose
1个回答
0
投票

您可以使用密封接口和数据类很好地定义状态。有时,由于委托关键字

by
,编译器无法进行智能转换。尝试引入一个when-表达式作用域变量来表示状态。

@Composable
fun AlbumScreen(
    albumScreenViewModel: AlbumScreenViewModel
) {
    val albumScreenState by albumScreenViewModel.uiState.collectAsState()

    when(val state = albumScreenState.screenLoadingState) {
        is ScreenLoadingState.Loading -> {}
        is ScreenLoadingState.Success -> {}
        is ScreenLoadingState.Failed -> {
            val a = state.errorMessage
        }
    }

}

快乐编码

© www.soinside.com 2019 - 2024. All rights reserved.