【问题标题】:define recyclerview click NOT as a member of constructor定义recyclerview click NOT 作为构造函数的成员
【发布时间】:2021-05-18 00:48:37
【问题描述】:

通过阅读许多网站,我知道在 recycerview 上处理 onclick 的最佳方法是设置 clicklistener 不在 OnBindViewHolder 中,它可以在 onCreateViewHolder(在 here 中解释)或在“bind”方法中传递 clickListener(在 @987654322 中解释) @)。

但真正困扰我的一件事是 clickListener 在活动/片段中的处理方式

val adapter : MyAdapter(){
//click goes here
}

它可能并不多,但老实说它不是那么可读

我更喜欢不在构造函数中处理点击侦听器,而是使用单独的方法,meyabe 像这样

adapter.onItemClickListner = {
val adapter = MyAdapter()
//click more readable, yay!
}

但我不确定它是否会影响性能,还是我真的需要坚持点击构造函数?

【问题讨论】:

    标签: android kotlin android-recyclerview onitemclicklistener


    【解决方案1】:

    我自己以前使用过这种方法。我没有在构造函数中传递侦听器,而是按照您的描述从方法调用中显式设置它。当我使用这种方法时,我必须确保在适配器中检查了侦听器的初始化及其空安全性。因此,在调用适配器中的侦听器方法之前,您必须确保它绝对存在并已初始化。

    我逐渐转向构造函数,因为我不想在任何点击之前对我的适配器进行有意识的检查。 (当有多个可点击视图时。)

    【讨论】:

      【解决方案2】:

      创建一个interface,其中包含一些function 来处理您的onClick。

      现在你需要在你的activity 类中implement 这个interface 像这样:-

      class MainActivity : InterfaceAdapterOnClick(这里InterfaceAdapterOnClick是一个接口,它有一些函数来处理你的onClick

      假设我们的interface 中有一个名为onClickItemfunction

      所以现在当你像adapter = MyAdapter() 这样创建你的适配器时,你可以用它来传递你的接口。所以它应该看起来像:-

      var adapter = MyAdapter(this)this,因为您已经在 mainActivity 类中实现了interface)并且您的适配器应该如下所示:-

      class MyAdapter(onClickHandler: InterfaceAdapterOnClick) {}
      

      所以最后你将在你的mainActivity 中有一个单独的interface 方法,你的mainAcitvity 应该看起来像:-

      class MainActivity : InterfaceAdapterOnClick {
      
          // This will be your seperate onClick handler for your recyclerView item
      
           override func onClickItem(// You can take some parameter as input here like `posistion` or `adapterItem` here ) {
          }
      }
      

      【讨论】:

        【解决方案3】:

        恕我直言,如果您的适配器需要 itemClickListener 才能正常运行,那么您应该将它传递给它的构造函数,并且使用 setter 函数传递它并不好,因为您可能在某些时候忘记传递它而忘记传递侦听器并浪费您的时间来检查为什么单击项目不起作用! (它发生在我身上:D)。如果您担心可读性,那么您可以使用接口并将实现传递给适配器或使用Kotlin 的某些功能(如命名参数)或传递函数的可调用引用以使其更具可读性。比如这样的

        class MyAdapter(onItemClick: (MyData) -> Unit) {
            // ...
        }
        

        并像这样初始化它

        val adapter = MyAdapter(
            onItemClick = { data -> 
                // ...
            }
        )
        

        或者像这样传递函数

        class MyActivity: AppCompatActivity() {
        
            override fun onCreateView(/**/) { 
                // ...
        
                val adapter = MyAdapter(
                    onItemClick = ::onItemClick
                )
                // or
                // val adapter = MyAdapter(::onItemClick)
            }
        
            private fun onItemClick(data: MyData) {
            }
        }
        

        【讨论】:

          【解决方案4】:

          您可以简单地在活动和适配器类之间传递一个接口,但最好的方法是向您的适配器类传递一个函数,像这样

               adapter = BasketRVA { basketEntity: BasketEntity, minus: Boolean -> changeQuantity(basketEntity, minus) }
          
                 private fun changeQuantity(basketEntity: BasketEntity, minus: Boolean) {
          ///your code
          }
          

          然后在适配器中输入这个

          class BasketRVA(private val clickListener: (BasketEntity, Boolean)->Unit): RecyclerView.Adapter<BasketRVA.BasketViewHolder>()
          

          在你的 viewHolder 类和绑定函数中

           inner class BasketViewHolder(binding: BasketItemBinding): RecyclerView.ViewHolder(binding.root) {
              @SuppressLint("SetTextI18n")
              fun bind(basketEntity: BasketEntity?, clickListener: (BasketEntity, Boolean) -> Unit){
                  binding.tvProductName.text = basketEntity?.productName
          

          在你的绑定函数中为你的视图创建一个点击监听器并传递你想要继续的函数

          binding.imMinus.setOnClickListener {
                      val minus = true
                      clickListener(basketEntity!!, minus)
                  }
          

          在你的绑定 viewHolder 中

          override fun onBindViewHolder(holder: BasketViewHolder, position: Int) {
              BasketViewHolder(binding).bind(basketList[position], clickListener)
              Log.d(TAG, "onBindViewHolder: basket list position is ${basketList[position]}")
          }
          

          如果还有问题可以问我

          【讨论】:

            猜你喜欢
            • 2018-07-30
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2014-10-12
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多