[英]lateinit property binding has not been initialized
我知道有类似的问题,但我只是找不到类似的东西,我一直在研究新的东西来学习,在将 kotlin 合成转换为viewvbinding
模式时,我遇到了这个错误
kotlin.UninitializedPropertyAccessException: lateinit property binding has not been initialized at com.codepalace.chatbot.ui.MessagingAdapter.onBindViewHolder(MessagingAdapter.kt:60) at com.codepalace.chatbot.ui.MessagingAdapter.onBindViewHolder(MessagingAdapter.kt:17)
它说我必须初始化绑定,但我不知道把它放在哪里。
这是代码。
class MessagingAdapter: RecyclerView.Adapter<MessagingAdapter.MessageViewHolder>() {
var messagesList = mutableListOf<Message>()
private lateinit var binding: MessageItemBinding
inner class MessageViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {
init {
itemView.setOnClickListener {
//Remove message on the item clicked
messagesList.removeAt(adapterPosition)
notifyItemRemoved(adapterPosition)
}
}
}
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): MessageViewHolder {
return MessageViewHolder(
LayoutInflater.from(parent.context).inflate(R.layout.message_item, parent, false)
)
}
override fun getItemCount(): Int {
return messagesList.size
}
@SuppressLint("SetTextI18n")
override fun onBindViewHolder(holder: MessageViewHolder, position: Int) {
val currentMessage = messagesList[position]
when (currentMessage.id) {
SEND_ID -> {
holder.itemView.findViewById<View>(R.id.tv_message).apply {
binding.tvMessage.text = currentMessage.message
visibility = View.VISIBLE
}
holder.itemView.findViewById<View>(R.id.tv_bot_message).visibility = View.GONE
}
RECEIVE_ID -> {
holder.itemView.findViewById<View>(R.id.tv_bot_message).apply {
binding.tvBotMessage.text = currentMessage.message
visibility = View.VISIBLE
}
holder.itemView.findViewById<View>(R.id.tv_message).visibility = View.GONE
}
}
}
fun insertMessage(message: Message) {
this.messagesList.add(message)
notifyItemInserted(messagesList.size)
}
private lateinit var binding: MessageItemBinding
您没有初始化binding
object,因为您将其定义为lateinit,那么您应该定义它。
这通常在onCreateViewHolder
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): TrackedActivityHolder {
val inflater = LayoutInflater.from(parent.context)
binding = DataBindingUtil.inflate<MessageItemBinding>(inflater, R.layout.message_item, parent, false)
return MessageViewHolder(
binding
)
}
更新
您需要在MessageViewHolder
构造函数中接受MessageItemBinding
类型而不是View
,并使用itemView.root
获取列表项的根视图。
inner class MessageViewHolder(itemView: MessageItemBinding) : RecyclerView.ViewHolder(itemView.root) {
init {
itemView.root.setOnClickListener {
//Remove message on the item clicked
messagesList.removeAt(adapterPosition)
notifyItemRemoved(adapterPosition)
}
}
}
您收到此错误的原因是MessageItemBinding
不应该在 Adapter 中,而是在 ViewHolder class 中。 您可以像这样制作 RecyclerView:
object MessageDiffCallback : DiffUtil.ItemCallback<Message>()
{
override fun areItemsTheSame(
oldItem: Message,
newItem: Message
): Boolean =
oldItem.id == newItem.id
override fun areContentsTheSame(
oldItem: Message,
newItem: Message
): Boolean =
oldItem == newItem
}
我假设Message
是数据 class。 您必须创建此MessageDiffCallback
并以与我类似的方式覆盖这两个方法。
现在创建ViewHolder
class:
class MessageViewHolder private constructor(
private val binding: MessageItemBinding
) : RecyclerView.ViewHolder(binding.root)
{
companion object
{
fun create(parent: ViewGroup): MessageViewHolder
{
val layoutInflater = LayoutInflater.from(parent.context)
val binding = MessageItemBinding.inflate(layoutInflater, parent, false)
return MessageViewHolder(
binding
)
}
}
fun bind(
message: Messaage
)
{
// Here You can do everything.
// You pass the message and based on this You can set up a view and use binding
}
}
现在适配器 class
class MessageAdapter : ListAdapter<Message, MessageViewHolder>(MessageDiffCallback)
{
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): MessageViewHolder =
MessageViewHolder.create(parent)
override fun onBindViewHolder(holder: MessageViewHolder, position: Int) =
holder.bind(
message = getItem(position),
)
}
现在你应该有一个工作适配器。 要将数据放入其中,请在您的片段/活动中使用messageAdapter.submitList(messages)
也许不是最好的答案,因为它会更改您的代码并使用一些不同的逻辑,但它应该会更好。 您可以在此处查看google 示例代码或在此处获取codelab 。 注册后免费
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.