You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Fragment中RecyclerView无法填充数据 同逻辑Activity正常运行问题求助

问题根因及修复方案

核心错误1:Fragment视图挂载逻辑错误

你在onCreate中初始化的Binding视图从未被挂载到Fragment上,所有RecyclerView的配置都作用在了无效视图上:

  • onCreate里inflate的FragmentTabHomeActivityBinding实例是局部变量,没有被持有
  • onCreateView中重新inflate了完全无关的R.layout.cards_home布局返回,和你配置过RecyclerView的视图没有任何关联
  • 未给RecyclerView设置必填的LayoutManager,RecyclerView没有布局规则不会渲染内容

核心错误2:Adapter逻辑错误

  • ViewHolder的bind方法中重复创建ViewHolder实例,没有使用当前绑定的itemView
  • 重复给同一个R.id.cardHomeTitle赋值,name的值会被后续的superheroName覆盖
  • 网络请求回包时直接用!!取body,接口异常时会直接崩溃

修正后的代码

1. Fragment代码修正

class TabHomeActivity : Fragment() {
    // 全局持有binding实例
    private var _binding: FragmentTabHomeActivityBinding? = null
    private val binding get() = _binding!!
    val itemList = ArrayList<HomeCards>()
    lateinit var adapter: HomeCardsAdapter

    override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?,savedInstanceState: Bundle?): View? {
        // 这里返回binding的根视图
        _binding = FragmentTabHomeActivityBinding.inflate(inflater, container, false)
        return binding.root
    }

    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        super.onViewCreated(view, savedInstanceState)
        adapter = HomeCardsAdapter()
        // 给RecyclerView设置LayoutManager,必填项
        binding.rvHomeCards.layoutManager = LinearLayoutManager(requireContext())
        binding.rvHomeCards.adapter = adapter
        loadData()
    }

    private fun loadData() {
        ApiManager.getInstance().service.listHeroes()
            .enqueue(object : Callback<ResponseData<List<HomeCards>>> {

                override fun onResponse(
                    call: Call<ResponseData<List<HomeCards>>>,
                    response: Response<ResponseData<List<HomeCards>>>
                ) {
                    // 加判空避免崩溃
                    response.body()?.data?.let { listData ->
                        itemList.clear()
                        itemList.addAll(listData)
                        adapter.updateData(itemList)
                    }
                }

                override fun onFailure(call: Call<ResponseData<List<HomeCards>>>, t: Throwable) {
                    // 建议加异常打印,方便排查问题
                    t.printStackTrace()
                }

            })
    }

    // Fragment销毁时清空binding引用避免内存泄漏
    override fun onDestroyView() {
        super.onDestroyView()
        _binding = null
    }
}

2. Adapter代码修正

class HomeCardsAdapter() : RecyclerView.Adapter<HomeCardsAdapter.ViewHolder>() {
    // 初始化时给个默认空列表,避免lateinit的额外判空逻辑
    private var itemList: List<HomeCards> = emptyList()
    lateinit var context: Context

    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
        context = parent.context
        val view = LayoutInflater.from(context).inflate(R.layout.cards_home, parent, false)
        return ViewHolder(view)
    }

    override fun getItemCount(): Int = itemList.size

    override fun onBindViewHolder(holder: ViewHolder, position: Int) {
        holder.bind(itemList[position])
    }

    fun updateData(list: List<HomeCards>) {
        itemList = list
        notifyDataSetChanged()
    }

    inner class ViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {
        // 提前初始化控件,避免每次bind都重复findViewById
        private val titleTv = itemView.findViewById<TextView>(R.id.cardHomeTitle)
        private val iconIv = itemView.findViewById<ImageView>(R.id.cardHomeIcon)

        fun bind(item: HomeCards) {
            // 不要重复创建ViewHolder,直接用当前实例的控件
            titleTv.text = "${item.name}(${item.superheroName})"
            Glide.with(context)
                .load(item.photo)
                .diskCacheStrategy(DiskCacheStrategy.ALL)
                .circleCrop()
                .into(iconIv)
        }
    }
}

内容的提问来源于stack exchange,提问作者Steve Rauco

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.05 05:06:02