【问题标题】:Implement On Click Listener in ViewHolder With Access To Associated Item在 ViewHolder 中实现单击侦听器并访问关联项
【发布时间】:2019-01-28 23:23:05
【问题描述】:

我听说在ViewHolder 内部实现onClickListener 是一种很好的做法。但是,我不确定如何访问与onClickListener 内部的ViewHolder 关联的项目。

例如:

import android.content.Context
import androidx.recyclerview.widget.RecyclerView
import android.util.Log
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.TextView
import kotlinx.android.synthetic.main.post.view.*

import rstudio.vedantroy.swarm.MainActivity.Companion.TAG

class PostAdapter(private val items : List<Post>, private val contex: Context) : RecyclerView.Adapter<MyViewHolder>() {

    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): MyViewHolder {
        return MyViewHolder(LayoutInflater.from(contex).inflate(R.layout.post, parent, false))
    }

    override fun getItemCount(): Int {
        return items.size
    }

    override fun onBindViewHolder(holder: MyViewHolder, position: Int) {
        holder.bodyContent.text = items[position].content
    }
}


class MyViewHolder(view: View): RecyclerView.ViewHolder(view), View.OnClickListener {

    override fun onClick(v: View?) {
        TODO("not implemented") //To change body of created functions use File | Settings | File Templates.
    }

    val bodyContent : TextView = view.bodyContent

}

如何访问items,如何找到ViewHolder的当前索引?

我查看了这个示例:Recyclerview(Getting item on Recyclerview),但没有解释 mDataSource 的来源。

【问题讨论】:

    标签: android android-recyclerview android-viewholder


    【解决方案1】:

    我个人认为一个很好的解决方案是在onBindViewHolder 中设置OnClickListener

    例如,

    // ... adapter class ...
    
    override fun onBindViewHolder(holder: ViewHolder, position: Int) {
    
        holder.view.apply {
    
            bodyContent.text = items[position].content
    
            setOnClickListener {
                // TODO Handle onClick
            }
        }
    }
    
    class ViewHolder(val view: View) : RecyclerView.ViewHolder(view)
    

    我还发现将view 存储在ViewHolder 中可以很容易地访问布局中的任何元素。

    【讨论】:

    • 我可以只使用holder.itemView 而不是将view 存储在ViewHolder 中吗?
    • 您可能需要将val 添加到您的View 中,您将传递给您的ViewHolder
    • 另外,我特别想知道如何在ViewHolder 本身而不是onBindViewHolder 中实现onClickListener(同时还可以访问相关项目)
    • 是的,我只是建议我个人所做的并认为是一个很好的解决方案。这将所有视图设置逻辑保持在一起。我还没有听说在ViewHolder 中绑定它。举个例子吧。
    【解决方案2】:

    我设法通过移动PostViewHolder 的位置来实现此行为。但是,我不确定inner class 是否会破坏某些东西。

    package rstudio.vedantroy.swarm
    
    import android.content.Context
    import androidx.recyclerview.widget.RecyclerView
    import android.util.Log
    import android.view.LayoutInflater
    import android.view.View
    import android.view.ViewGroup
    import android.widget.TextView
    import androidx.cardview.widget.CardView
    import kotlinx.android.synthetic.main.post.view.*
    
    import rstudio.vedantroy.swarm.MainActivity.Companion.TAG
    
    class PostAdapter(private val items : List<Post>, private val contex: Context) : RecyclerView.Adapter<PostAdapter.PostViewHolder>() {
    
        override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): PostViewHolder {
            return PostViewHolder(LayoutInflater.from(contex).inflate(R.layout.post, parent, false))
        }
    
        override fun getItemCount() = items.size
    
        override fun onBindViewHolder(holder: PostViewHolder, position: Int) {
            holder.bodyContent.text = items[position].content
        }
    
        inner class PostViewHolder(view: View): RecyclerView.ViewHolder(view) {
            val bodyContent : TextView = view.bodyContent
    
            init {
                view.apply {
                    setOnClickListener {
                        isClickable = false
                        Log.d(TAG, "Clicked!")
                    }
                }
    
            }
    
        }
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-03-03
      • 1970-01-01
      • 2017-01-22
      • 1970-01-01
      相关资源
      最近更新 更多