簡體   English   中英

Compose 應用程序在啟動后不加載 api 數據

[英]Compose app doesn't load api data after launch

我正在使用 Jetpack Compose 創建 Pokémon 應用程序。 我正在使用兩款智能手機對其進行測試:Xioami Mi 11T Pro (Android 12) 和 Xiaomi Mi 8 Lite (Android 10)。

好吧,當我在 Mi 8 Lite 中啟動該應用程序時,它正確啟動,神奇寶貝列表完美加載。 但是當我使用 Mi 11 T Pro 啟動應用程序時,它沒有加載,沒有任何顯示。 我發現了兩件事:

  1. 如果我打開 Layout Inspector,它會立即加載,無需執行任何其他操作...
  2. 當屏幕為空時(剛啟動后,加載前),如果我在屏幕上單擊 1-2 次,它就會開始發送請求並正確加載。

為什么會這樣?

我附上我的 ViewModel 和我的 MainActivity。

PokemonListViewModel.kt

@HiltViewModel
class PokemonListViewModel @Inject constructor(
    private val repository: PokemonRepositoryImpl
) : ViewModel() {

    private var currentPage = 0

    var pokemonList = mutableStateOf<List<PokedexListEntry>>(listOf())
    var loadError = mutableStateOf("")
    var isLoading = mutableStateOf(false)
    var endReached = mutableStateOf(false)

    private var cachedPokemonList = listOf<PokedexListEntry>()
    private var isSearchStarting = true
    var isSearching = mutableStateOf(false)

    init {
        loadPokemonList()
    }

    // TODO: Search online, not only already loaded pokémon
    fun searchPokemonList(query: String) {
        val listToSearch = if (isSearchStarting) {
            pokemonList.value
        } else {
            // If we typed at least one character
            cachedPokemonList
        }
        viewModelScope.launch(Dispatchers.Default) {
            if (query.isEmpty()) {
                pokemonList.value = cachedPokemonList
                isSearching.value = false
                isSearchStarting = true
                return@launch
            }

            val results = listToSearch.filter {
                // Search by name or pokédex number
                it.pokemonName.contains(query.trim(), true) ||
                        it.number.toString() == query.trim()
            }

            if (isSearchStarting) {
                cachedPokemonList = pokemonList.value
                isSearchStarting = false
            }

            // Update entries with the results
            pokemonList.value = results
            isSearching.value = true
        }
    }

    fun loadPokemonList() {
        viewModelScope.launch {
            isLoading.value = true

            val result = repository.getPokemonList(PAGE_SIZE, currentPage * PAGE_SIZE)
            when (result) {
                is Resource.Success -> {
                    endReached.value = currentPage * PAGE_SIZE >= result.data!!.count

                    val pokedexEntries = result.data.results.mapIndexed { index, entry ->
                        val number = getPokedexNumber(entry)
                        val url = getImageUrl(number)
                        PokedexListEntry(
                            entry.name.replaceFirstChar(Char::titlecase),
                            url,
                            number.toInt()
                        )
                    }

                    currentPage++

                    loadError.value = ""
                    isLoading.value = false
                    pokemonList.value += pokedexEntries
                }
                is Resource.Error -> {
                    loadError.value = result.message!!
                    isLoading.value = false
                }
                is Resource.Loading -> {
                    isLoading.value = true
                }
            }

        }
    }

    private fun getImageUrl(number: String): String {
        return "https://raw.githubusercontent.com/PokeAPI/sprites/master/sprites/pokemon/${number}.png"
    }

    private fun getPokedexNumber(entry: Result): String {
        return if (entry.url.endsWith("/")) {
            entry.url.dropLast(1).takeLastWhile { it.isDigit() }
        } else {
            entry.url.takeLastWhile { it.isDigit() }
        }
    }

}

主活動.kt

@AndroidEntryPoint
class MainActivity : ComponentActivity() {

    private val argPokemonName = "pokemonName"

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            JetpackComposePokedexTheme {
                val navController = rememberNavController()
                NavHost(navController = navController, startDestination = "pokemon_list_screen") {
                    composable("pokemon_list_screen") {
                        PokemonListScreen(navController = navController)
                    }
                    composable(
                        "pokemon_detail_screen/{$argPokemonName}",
                        arguments = listOf(
                            navArgument(argPokemonName) {
                                type = NavType.StringType
                            }
                        )
                    ) {
                        val pokemonName = remember {
                            it.arguments?.getString(argPokemonName)
                        }
                        PokemonDetailScreen(
                            pokemonName = pokemonName?.lowercase(Locale.ROOT) ?: "",
                            navController = navController
                        )
                    }
                }
            }
        }
    }


}

如果有人知道為什么它不加載...我懷疑可能是 init { } 或 Hilt 注入正在做一些使 init 無法啟動的事情。

感謝您的時間和幫助!

好吧,看來是小米報的bug,谷歌不會修復,你可以在這里看到: https://issuetracker.google.com/issues/227926002

它對我有用,在設置內容之前添加了一點延遲,它似乎正在工作:

lifecycleScope.launch { delay(300) setContent { JetpackComposePokedexTheme {... } } }

還可以看到: compose NavHost 啟動白屏

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM