当前位置: 首页 > 知识库问答 >
问题:

(Android静态编程语言)RecyclerView Adapter方法未调用:显示空RecyclerView

苗阳文
2023-03-14

我试图使用Reform2显示来自虚拟服务器(JSON服务器)的JSON数据,并将其显示在片段中的RecyclerView中。到目前为止,正在发生以下事件(使用日志信息发现):

  1. 主片段<代码>字符片段(CharactersListFragment)。kt创建已启动
  2. 只调用了getItemCount()。它正在返回0
  3. 未调用OnCreateViewHolder()和onBindViewHolder()
  4. 成功地从服务器获取数据并将其传递到适配器(来自CharactersListFragment.kt)

没有编译时错误,我的应用程序也没有崩溃,只是RecyclerView为空。

这是我的代码文件:

  1. 使用RecycleView布局片段:fragment_characters_list.xml
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    tools:context=".CharactersListFragment">


    <androidx.recyclerview.widget.RecyclerView
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:id="@+id/recycler_view"
        app:layout_constraintTop_toTopOf="parent"
        app:layout_constraintBottom_toBottomOf="parent"
        app:layout_constraintRight_toRightOf="parent"
        app:layout_constraintLeft_toLeftOf="parent"

        />
</androidx.constraintlayout.widget.ConstraintLayout>

<?xml version="1.0" encoding="utf-8"?>
<androidx.cardview.widget.CardView xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:id="@+id/character_card_view"
    android:layout_width="match_parent"
    android:layout_height="300dp"
    android:elevation="15dp"
    app:cardBackgroundColor="@color/violet_forcard"
    app:cardCornerRadius="3dp">

    <androidx.constraintlayout.widget.ConstraintLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent">


        <ImageView
            android:id="@+id/char_thumnail_img"
            android:layout_width="143dp"
            android:layout_height="150dp"
            android:layout_marginStart="24dp"
            app:layout_constraintBottom_toBottomOf="parent"
            app:layout_constraintStart_toStartOf="parent"
            app:layout_constraintTop_toTopOf="parent"
            app:layout_constraintVertical_bias="0.106"
            tools:srcCompat="@tools:sample/avatars" />

        <TextView
            android:id="@+id/char_id_txt"
            android:layout_width="190dp"
            android:layout_height="53dp"
            android:layout_marginTop="16dp"
            android:fontFamily="@font/roboto"
            android:text="Character ID: "
            android:textAlignment="viewStart"
            android:textColor="@color/white"
            android:textSize="18sp"
            android:textStyle="bold"
            app:layout_constraintEnd_toEndOf="parent"
            app:layout_constraintStart_toEndOf="@+id/char_thumnail_img"
            app:layout_constraintTop_toTopOf="parent" />

        <TextView
            android:id="@+id/char_name_txt"
            android:layout_width="190dp"
            android:layout_height="53dp"
            android:layout_marginTop="24dp"
            android:fontFamily="@font/roboto"
            android:text="Name: "
            android:textAlignment="viewStart"
            android:textColor="@color/white"
            android:textSize="18sp"
            android:textStyle="bold"
            app:layout_constraintEnd_toEndOf="parent"
            app:layout_constraintStart_toEndOf="@+id/char_thumnail_img"
            app:layout_constraintTop_toBottomOf="@+id/char_id_txt" />

        <TextView
            android:id="@+id/char_descp_txt"
            android:layout_width="359dp"
            android:layout_height="wrap_content"
            android:fontFamily="@font/roboto"
            android:textAlignment="viewStart"
            android:textColor="@color/white"
            android:textSize="14sp"
            android:textStyle="bold"
            app:layout_constraintBottom_toBottomOf="parent"
            app:layout_constraintEnd_toEndOf="parent"
            app:layout_constraintHorizontal_bias="0.461"
            app:layout_constraintStart_toStartOf="parent"
            app:layout_constraintTop_toTopOf="parent"
            app:layout_constraintVertical_bias="0.918" />

    </androidx.constraintlayout.widget.ConstraintLayout>
</androidx.cardview.widget.CardView>
package com.example.marvelapp

import android.os.Bundle
import android.util.Log
import androidx.fragment.app.Fragment
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import androidx.recyclerview.widget.LinearLayoutManager
import androidx.recyclerview.widget.RecyclerView
import retrofit2.Call
import retrofit2.Callback
import retrofit2.Response

class CharactersListFragment : Fragment() {
    private lateinit var charsAdapter: CharacterListAdapter
    private lateinit var apiService: APIService
    private var characters: MutableList<Character> = ArrayList()


    override fun onCreateView(
        inflater: LayoutInflater, container: ViewGroup?,
        savedInstanceState: Bundle?
    ): View? {
        // Inflate the layout for this fragment

        Log.i("INSIDE_FRAGMENT_ONCREATEVIEW", "Fragment creation initiated")
        val v = inflater.inflate(R.layout.fragment_characters_list, container, false)

        apiService = RestClient.client.create(APIService::class.java)

        getCharacterList()

        val recycler_view = v.findViewById(R.id.recycler_view) as RecyclerView
        recycler_view.layoutManager = LinearLayoutManager(activity)
        charsAdapter = CharacterListAdapter()
        recycler_view.adapter = charsAdapter

        return v
    }

    private fun getCharacterList(){
        val call = apiService!!.get_characters()
        call.enqueue(object: Callback<List<Character>> {
            override fun onResponse(
                call: Call<List<Character>>,
                response: Response<List<Character>>
            ) {
                val chars = response.body()
                Log.i("get_character_succeeded_FOR_CALL", chars.toString())
                if (chars != null){
                    characters.addAll(chars!!)
                    Log.i("character_ADD_CHECK_INSIDE_FRAGMENT", characters[0].toString())
                    charsAdapter.submitDataforcharList(characters)
                }

            }

            override fun onFailure(call: Call<List<Character>>, t: Throwable) {
                Log.e("get_character_failed", t.localizedMessage)
            }

        })
    }

}

package com.example.marvelapp

import android.text.Layout
import android.util.Log
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.TextView
import androidx.recyclerview.widget.RecyclerView
import kotlinx.android.synthetic.main.fragment_character_recyclerview_list.view.*

class CharacterListAdapter: RecyclerView.Adapter<RecyclerView.ViewHolder>() {

    private var charItems: List<Character> = ArrayList()

    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): RecyclerView.ViewHolder {
        Log.i("INSIDE_ONCREATE_VIEWHOLDER", "reached")
        return CharacterListViewHolder(LayoutInflater.from(parent.context).inflate(R.layout.fragment_character_recyclerview_list,
        parent,
        false))
    }

    override fun onBindViewHolder(holder: RecyclerView.ViewHolder, position: Int) {
        when(holder){
            is CharacterListViewHolder ->{
                Log.i("VIEWHOLDER_FOUND", "proceeding to bind")
                holder.bind(charItems.get(position))
            }
        }
    }

    override fun getItemCount(): Int {
        Log.i("INSIDE_ADAPTER_GET_ITEM_COUNT", charItems.size.toString())
        return charItems.size
    }

    fun submitDataforcharList (characterlist: List<Character>){
        Log.i("INSIDE_ADAPTER_SUBMIT_DATA", characterlist[0].toString())
        charItems = characterlist
    }

    class CharacterListViewHolder
    constructor(view: View): RecyclerView.ViewHolder(view){
        val char_id = view.findViewById<TextView>(R.id.char_id_txt)
        val char_name = view.findViewById<TextView>(R.id.char_name_txt)
        val char_descp = view.findViewById<TextView>(R.id.char_descp_txt)

        fun bind(character: Character){
            Log.i("INSIDE_VIEWHOLDER_BIND", character.toString())
            val id = Integer.toString(character.charId)
            val id_mess = "Character ID: $id"
            char_id.setText(id_mess)
            val char_name_mess = "Name: ${character.charName}"
            char_name.setText(char_name_mess)
            char_descp.setText(character.charDescp)
        }

    }
}

package com.example.marvelapp


data class Character(
    val charId: Int,
    val charName: String,
    val charDescp: String,
){
}

我是一个Android初学者,已经坚持了很长一段时间,任何帮助将不胜感激。提前谢谢!

共有2个答案

曹浩
2023-03-14

在UI线程(主线程)上调用了getCharacterList(),但设备和API服务器之间的通信(请求和响应)正在另一个线程中进行,这意味着不能保证onResponse()会早于recycler\u视图。adapter=charsAdapter,实际上,这种情况通常不会发生。因此,您必须调用charsAdapter。notifyDataSetChanged()在charsAdapter之后。submitDataforcharList(characters)以使recyclerview表示数据。另一种更有效的方法是在submitDataforcharList()中添加notifyDatasetChanged():

fun submitDataforcharList (characterlist: List<Character>){
        charItems = characterlist
        notifyDatasetChanged()
}
何升
2023-03-14

在CharactersListFragment的onCreateView中调用getCharacterList(),然后继续初始化回收器视图。调用完成后,您可能会获得一些数据,只需更新适配器类中的数据列表,但不会通知recyclerview刷新视图以显示新数据。因此,我认为如果在设置新数据后在适配器上调用notifyDataSetChanged(),它应该可以工作。

解决此问题的另一种方法是,在从getCharacterList()调用接收到数据后初始化recyclerview,并在提取数据时在recycler视图的位置显示一些加载图标。

 类似资料:
  • 我是一个初学静态编程语言的学生,正在学习一个示例回收人员视图。我开始编码,但没有得到我应该得到的结果,即使在检查和重新检查代码之后也是如此。然后我注意到,即使使用非常基本的代码,它仍然没有按照应有的方式运行。我将包含基本代码,当使用时,它应该显示一个通用列表。我只得到列表中的一项。我怀疑代码以外的其他东西正在影响结果;但是我还没有达到知道的水平。 请看活动内容。xml: 注意它有行。 下面是列表(

  • 我正在尝试用Java编写下面用Kotlin编写的代码。我无法创建DefaultElementsAdapter,因为我无法获得正确的语法。 我无法获得正确的Java代码 Kotlin班是这样的 我正在尝试使用图书馆https://github.com/m7mdra/HtmlRecycler

  • 我有一个使用Kotlin 1.0版的Android项目。Android Studio中的0-beta-1038。 我可以在不同的部分使用Kotlin运行它,它在模拟器中编译并工作,但当我尝试使用ReadWriteProperty时,它会给出以下错误消息: 未解析的引用:ReadWriteProperty 类称为首选Utils.kt: build.grade(模块:app) build.grade(

  • 我试图用OkHttp和Cucumber在静态编程语言中设置一个Spring启动项目,并且在运行Cucumber任务时遇到以下错误。如何修复? 还有build gradle kts片段 我看到了这个错误https://github.com/square/okio/issues/647看起来可能是它,并修复了这个build.gradle,我如何将其翻译为kotlinbuild.gradle.kts?

  • 我想知道为什么在下面的代码中没有捕捉到异常: 函数的调用方式如下: 但我还是遇到了一个导致应用程序崩溃的异常: 我想说try/catch块会捕获异常,但唉。。。 什么原因导致异常没有被捕获?我想说线程并不重要,因为我使用try/get块来处理线程中的异常。 在Laalto的回答之后,我更新了代码,如下所示(对于那些感兴趣的人):

  • 我有一个Spring Boot应用程序,以Kotlin为语言,Gradle为构建系统。所以基本上,我试图用应用程序源代码和依赖项构建一个胖jar,可以使用Java命令行工具运行。 Gradle构建脚本: 如果我使用gradle命令运行项目,那么它运行正常。但是当我构建jar并尝试ti运行时,它会抱怨以下错误:- 应用.kt:- 不知道我到底哪里做错了什么。