Android Kotlin 开发中无法从 Github API 获取数据

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

我是Android开发的初学者,当我从Github API获取数据时遇到问题,我有一个详细信息页面可以显示Github用户的详细信息,但当我想显示数据时它总是不起作用

问题是详情页只能显示一次数据,之后就无法再次加载数据了,因为结果的值始终是Result.Loading(false)。这导致每次要打开详细信息页面时都必须重新打开应用程序。

任何人都可以帮助什么使 ResultViewModel.Loading 的值始终等于 false 吗?我需要 ResultViewModel.Loading 为 true 才能从 API 更新新数据

这是我的代码:

// 详细用户活动

@AndroidEntryPoint
class DetailUserActivity : AppCompatActivity() {
    private lateinit var binding: ActivityDetailUserBinding
    private val viewModel by viewModels<DetailUserViewModel>()

    private var isFavorite = false


    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        binding = ActivityDetailUserBinding.inflate(layoutInflater)
        setContentView(binding.root)
        supportActionBar?.setDisplayHomeAsUpEnabled(true)

        val item = intent.getParcelableExtra<GithubUser.Item>("userItems")
        val username = item?.login ?: "User Not Found"

        Log.d("Intent berhasil", "Data berhasil diterima: $item")

        viewModel.getUser(username)

        viewModel.resultDetailUser.observe(this) { result ->
            when (result) {
                is ResultViewModel.Success<*> -> {
                    val data = result.data as GithubDetailUser
                    val user = data
                    binding.imageUser.load(user.avatar_url) {
                        transformations(CircleCropTransformation())
                    }
                    binding.fullNames.text = user.name
                    binding.username.text = user.login
                    binding.followerCount.text = user.followers.toString()
                    binding.followingCount.text = user.following.toString()
                    binding.repositoryCount.text = user.public_repos.toString()

                    Log.d("Detail User", "Detail User bisa di GET: $item")
                }

                is ResultViewModel.Error -> {
                    Toast.makeText(this, result.exception.message.toString(), Toast.LENGTH_SHORT).show()
                    Log.d("Intent Error", "Data gagal di GET")

                }
                is ResultViewModel.Loading -> {
                    binding.progressBar.isVisible = result.isLoading
                    Log.d("Loading Detail", "${result.isLoading}")
                }
            }
        }

        viewModel.getUser(username)
        val fragments = mutableListOf<Fragment>(
            UserFollower.newInstance(UserFollower.FOLLOWERS),
            UserFollower.newInstance(UserFollower.FOLLOWING)
        )
        val titleTabFragments = mutableListOf(
            getString(R.string.follower_tab), getString(R.string.following_tab)
        )
        val adapter = DetailUserAdapter(this, fragments)
        binding.viewPager.adapter = adapter

        TabLayoutMediator(binding.tabLayout, binding.viewPager) { tab, position ->
            tab.text = titleTabFragments[position]
        }.attach()

        binding.tabLayout.addOnTabSelectedListener(object : TabLayout.OnTabSelectedListener {
            override fun onTabSelected(tab: TabLayout.Tab?) {
                if (tab?.position == 0) {
                    viewModel.getFollowerUser(username)
                } else {
                    viewModel.getFollowingUser(username)
                }
            }

            override fun onTabUnselected(tab: TabLayout.Tab?) {
            }

            override fun onTabReselected(tab: TabLayout.Tab?) {
            }

        })

        viewModel.getFollowerUser(username)

        viewModel.resultFavoriteAdd.observe(this) {
            updateFavoriteButtonColor(true)
        }
        viewModel.resultFavoriteDelete.observe(this) {
            updateFavoriteButtonColor(false)
        }

        viewModel.findById(item?.id ?: 0) {
            viewModel.viewModelScope.launch {
                updateFavoriteButtonColor(true )
            }
        }

        binding.favoriteButton.setOnClickListener {
            val titleAdd = getString(R.string.notif_title_add)
            val titleDelete = getString(R.string.notif_title_delete)
            val addMessage = getString(R.string.notif_add_message)
            val deleteMessage = getString(R.string.notif_delete_message)
            val userId = item
            if (userId != null) {
                viewModel.viewModelScope.launch {
                    if (viewModel.isFavorite.value == true) {
                        Log.d("DetailUserActivity", "isFavorite: $isFavorite")
                        viewModel.delete(userId)
//                        viewModel.setFavorite(isFavorite)
                        updateFavoriteButtonColor(isFavorite)
                        sendNotif(titleDelete, deleteMessage)
                        Log.d("DetailUserActivity", "User dengan ID $userId dihapus dari favorit.")
                    } else {
                        viewModel.insert(userId)
//                        viewModel.setFavorite(!isFavorite)
                        updateFavoriteButtonColor(!isFavorite)
                        Log.d("DetailUserActivity", "User dengan ID $userId ditambah ke favorit.")
                        sendNotif(titleAdd, addMessage)
                    }
                }
            }

        }

    private fun updateFavoriteButtonColor(isFavorite: Boolean) {
        val colorRes = if (isFavorite) R.color.colorFav else android.R.color.white
        val color = ContextCompat.getColor(this, colorRes)
        binding.favoriteButton.setColorFilter(color)
    }


    override fun onOptionsItemSelected(item: MenuItem): Boolean {
        when(item.itemId) {
            android.R.id.home -> {
                finish()
            }
        }

        return super.onOptionsItemSelected(item)
    }
}

// 详细用户视图模型

    @HiltViewModel
    class DetailUserViewModel @Inject constructor(
        private val repository: GithubUserRepositoryImpl,
    ) : ViewModel() {

        val resultDetailUser = MutableLiveData<ResultViewModel>()
        val resultFavoriteAdd = MutableLiveData<ResultViewModel>()
        val resultFavoriteDelete = MutableLiveData<ResultViewModel>()

        val resultFollowersUser = MutableLiveData<ResultViewModel>()
        val resultFollowingUser = MutableLiveData<ResultViewModel>()


        fun getUser(username: String) {
            viewModelScope.launch {
                flow {
                    val response = repository.getDetailUserFromGithub(username)
                    resultDetailUser.value = ResultViewModel.Loading(true)
                    emit(response)
                }.onCompletion {
                    resultDetailUser.value = ResultViewModel.Loading(false)
                } .catch {
                    Log.e("Error ", it.message.toString())
                    it.printStackTrace()
                    resultDetailUser.value = ResultViewModel.Error(it)
                } .collect {
                    // Ubah tipe data yang dikirimkan ke resultSuccess.value
                    resultDetailUser.value = ResultViewModel.Success(it)

                }
            }
        }

        fun getFollowerUser(username: String) {
            viewModelScope.launch {
                flow {
                    resultFollowersUser.value = ResultViewModel.Loading(true)
                    val response = repository.getFollowerUserFromGithub(username)
                    emit(response)
                } .onStart {
                    resultFollowersUser.value = ResultViewModel.Loading(true)
                } .onCompletion {
                    resultFollowersUser.value = ResultViewModel.Loading(false)
                } .catch {
                    Log.e("Error ", it.message.toString())
                    it.printStackTrace()
                    resultFollowersUser.value = ResultViewModel.Error(it)
                } .collect {
                    // Ubah tipe data yang dikirimkan ke resultSuccess.value
                    resultFollowersUser.value = ResultViewModel.Success(it)
                }
            }
        }

        fun getFollowingUser(username: String) {
            viewModelScope.launch {
                flow {
                    resultFollowingUser.value = ResultViewModel.Loading(true)
                    val response = getFollowingUser(username)
                    emit(response)
                } .onStart {
                    resultFollowingUser.value = ResultViewModel.Loading(true)
                } .onCompletion {
                    resultFollowingUser.value = ResultViewModel.Loading(false)
                } .catch {
                    Log.e("Error ", it.message.toString())
                    it.printStackTrace()
                    resultFollowingUser.value = ResultViewModel.Error(it)
                } .collect {
                    // Ubah tipe data yang dikirimkan ke resultSuccess.value
                    resultFollowingUser.value = ResultViewModel.Success(it)
                }
            }
        }

    }

// 结果视图模型

sealed class ResultViewModel {
    data class Success<out T>(val data: T) : ResultViewModel()
    data class Error(val exception: Throwable) : ResultViewModel()
    data class Loading(val isLoading: Boolean) : ResultViewModel()
}
android api kotlin get github-api
1个回答
0
投票

您面临的问题似乎与 DetailUserViewModel 中的 LiveData 未正确更新有关,请改为执行此操作

fun getUser(username: String) {
                viewModelScope.launch {
                resultDetailUser.value = ResultViewModel.Loading(true)
                    flow {
                        val response = repository.getDetailUserFromGithub(username)
                       emit(response)
                    }.onCompletion {
                        resultDetailUser.value = ResultViewModel.Loading(false)
                    } .catch {
                        Log.e("Error ", it.message.toString())
                        it.printStackTrace()
                        resultDetailUser.value = ResultViewModel.Error(it)
                    } .collect {
                        // Ubah tipe data yang dikirimkan ke resultSuccess.value
                        resultDetailUser.value = ResultViewModel.Success(it)
    
                    }
                }
            }
© www.soinside.com 2019 - 2024. All rights reserved.