kotlin 如何从Retrofit响应中正确地将列表传递给Adapter?[Android Studio 2023]

nhjlsmyf  于 2023-08-06  发布在  Kotlin
关注(0)|答案(2)|浏览(164)

所以,我已经遵循了许多YouTube教程,以正确了解Android中的Retrofit以及如何将响应中的数据传递到我的适配器并显示列表,但现在没有一个对我有效,我不知道为什么。
在我的MainActivity中,我正在调用RetrofitInstance,因此向我的API发起GET请求并从中获取响应。当我调试我的代码并记录响应时,主体是正确可见的,因为它应该是,但是当我试图将该响应以列表的形式传递给适配器时,问题就发生了。
这是两个文件的代码
主活动代码-

  1. class QuizMainActivity : AppCompatActivity() {
  2. private lateinit var quizCategoryAdapter: QuizCategoryAdapter
  3. private lateinit var binding: ActivityQuizMainBinding
  4. override fun onCreate(savedInstanceState: Bundle?) {
  5. super.onCreate(savedInstanceState)
  6. binding = ActivityQuizMainBinding.inflate(layoutInflater)
  7. setContentView(binding.root)
  8. hideactionbar()
  9. setupRecyclerView()
  10. lifecycleScope.launchWhenCreated {
  11. val response = try{
  12. RetrofitInstance.api.getQuizCategories()
  13. }catch (e:IOException){
  14. Log.d("QuizCatTag", "IOException"+e)
  15. return@launchWhenCreated
  16. }catch (e: HttpException){
  17. Log.d("QuizCatTag", "HTTPException"+e)
  18. return@launchWhenCreated
  19. }
  20. if(response.isSuccessful && response.body()!=null){
  21. setupRecyclerView()
  22. quizCategoryAdapter.quizCategoryList = response.body()!!.category_detail //place where I am sending my response list to my adapter.
  23. Log.d("quizCategoryList", quizCategoryAdapter.quizCategoryList.toString() )
  24. }else{
  25. Log.d("TASG", "Response not successful")
  26. }
  27. }
  28. }
  29. private fun hideactionbar() {
  30. supportActionBar?.hide()
  31. }
  32. private fun setupRecyclerView() = binding.quizCategoryRv.apply {
  33. quizCategoryAdapter = QuizCategoryAdapter(this@QuizMainActivity)
  34. adapter = quizCategoryAdapter
  35. layoutManager = LinearLayoutManager(this@QuizMainActivity)
  36. }
  37. }

字符串
适配器代码-(我也在适配器中使用DiffUtils来处理数据的变化)

  1. class QuizCategoryAdapter(
  2. private val context: Context
  3. ) : RecyclerView.Adapter<QuizCategoryAdapter.QuizCategoryHolder>() {
  4. private val diffCallBack = object: DiffUtil.ItemCallback<CategoryDetail>(){
  5. override fun areItemsTheSame(oldItem: CategoryDetail, newItem: CategoryDetail): Boolean {
  6. return oldItem.category_name == newItem.category_name
  7. }
  8. override fun areContentsTheSame(oldItem: CategoryDetail, newItem: CategoryDetail): Boolean {
  9. return oldItem == newItem
  10. }
  11. }
  12. private val differ = AsyncListDiffer(this, diffCallBack)
  13. var quizCategoryList : List<CategoryDetail>
  14. get() = differ.currentList
  15. set(value) {differ.submitList(value)}
  16. val textList = quizCategoryList.chunked(3)
  17. class QuizCategoryHolder(binding: QuizCategoryItemBinding) : RecyclerView.ViewHolder(binding.root){
  18. val listTextV = listOf(binding.qciTv1, binding.qciTv2, binding.qciTv3)
  19. }
  20. override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): QuizCategoryAdapter.QuizCategoryHolder {
  21. return QuizCategoryHolder(QuizCategoryItemBinding.inflate(LayoutInflater.from(context), parent,false))
  22. }
  23. override fun getItemCount(): Int {
  24. return textList.size
  25. }
  26. override fun onBindViewHolder(holder: QuizCategoryHolder, position: Int) {
  27. for (i in 0 until textList[position].size){
  28. if(textList[position][i].category_name==""){
  29. holder.listTextV[i].isVisible = false
  30. }else{
  31. holder.listTextV[i].text = textList[position][i].category_name
  32. }
  33. }
  34. holder.itemView.setOnClickListener{
  35. val intent = Intent(context, QuizQuestionActivity::class.java)
  36. context.startActivity(intent)
  37. }
  38. }
  39. }


我试图通过Retrofit将从API获取的列表显示到RecyclerView适配器中。但不幸的是,当我将列表传递给我的Adapter类时,它仍然显示为null/empty,并且不显示任何内容。
话虽如此,当我试图将列表作为参数传递给class时,它会显示列表。在我看来,我不认为这是正确的方式。
请引导我,让我知道你的想法。实现这一点的最正确的方法是什么?

qltillow

qltillow1#

在适配器中设置列表后,您缺少notifyDataSetChanged()。

  1. quizCategoryAdapter.notifyDataSetChanged()

字符串
在设置从API调用中获得的列表后,应调用。

mfuanj7w

mfuanj7w2#

所以我调试和Log.Cat我的代码中的一切,终于找到了错误在哪里-
基本上,这份名单没有任何问题。该列表将按预期的方式发送到适配器。但在我的适配器类中,我正在分块列表,如您所见

  1. val textList = quizCategoryList.chunked(3)

字符串
现在,这一行和textList变成了null,因为当我最终从API获取列表时,这个列表没有更新。因此导致不显示任何内容的错误。

  1. override fun getItemCount(): Int {
  2. return textList.size // was showing 0 hence not displaying anything }


因此,为了修复这个错误,我只是在显示之前将onBindViewHolder方法中的列表分块,并编辑了我的getItemCount()方法。
Adapter类的更新代码看起来像这样-

  1. class QuizCategoryAdapter(
  2. private val context: Context
  3. ) : RecyclerView.Adapter<QuizCategoryAdapter.QuizCategoryHolder>() {
  4. private val diffCallBack = object: DiffUtil.ItemCallback<CategoryDetail>(){
  5. override fun areItemsTheSame(oldItem: CategoryDetail, newItem: CategoryDetail): Boolean {
  6. return oldItem.category_name == newItem.category_name
  7. }
  8. override fun areContentsTheSame(oldItem: CategoryDetail, newItem: CategoryDetail): Boolean {
  9. return oldItem == newItem
  10. }
  11. }
  12. private val differ = AsyncListDiffer(this, diffCallBack)
  13. var quizCategoryList : List<CategoryDetail>
  14. get() = differ.currentList
  15. set(value) {differ.submitList(value)}
  16. class QuizCategoryHolder(binding: QuizCategoryItemBinding) : RecyclerView.ViewHolder(binding.root){
  17. val listTextV = listOf(binding.qciTv1, binding.qciTv2, binding.qciTv3)
  18. }
  19. override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): QuizCategoryAdapter.QuizCategoryHolder {
  20. return QuizCategoryHolder(QuizCategoryItemBinding.inflate(LayoutInflater.from(context), parent,false))
  21. }
  22. override fun getItemCount(): Int {
  23. return quizCategoryList.chunked(3).size //returning the size of the chunked list so that content is rightfully displayed
  24. }
  25. override fun onBindViewHolder(holder: QuizCategoryHolder, position: Int) {
  26. val textList = quizCategoryList.chunked(3) //chunking my list here rather than at the beginning of the class where it was not getting updated.
  27. for (i in 0 until textList[position].size){
  28. holder.listTextV[i].text = textList[position][i].category_name
  29. }
  30. holder.itemView.setOnClickListener{
  31. val intent = Intent(context, QuizQuestionActivity::class.java)
  32. context.startActivity(intent)
  33. }
  34. }
  35. }

展开查看全部

相关问题