RecyclerView setOnLongClickListener kotlin

#android #kotlin #android-recyclerview

#Android #котлин #android-recyclerview

Вопрос:

Прежде всего: я хотел бы передать данные из моего RecyclerAdapter в мой фрагмент, поэтому именно таким образом я реализовал этот адаптер ниже :

 class RecyclerItemCart(private val cart: MutableList<Post>, val context: Context, val listener: (Post) -> Unit) : RecyclerView.Adapter<RecyclerItemCart.ViewHolder>() {

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

    interface OnItemClickListener {
        fun onItemClickListener(post: Post)
    }

    override fun onBindViewHolder(holder: ViewHolder, position: Int) {
        holder.bind(cart[position], listener)
        holder.mView.setOnLongClickListener {
            true }
    }

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

    inner class ViewHolder (val mView: View) : RecyclerView.ViewHolder(mView) {
        fun bind(mItem: Post, listener: (Post) -> Unit) = with(itemView)
        {
            val title: TextView = mView.findViewById(R.id.title)
            val authorName: TextView = mView.findViewById<TextView>(R.id.owner)
            val priceIT: TextView = mView.findViewById(R.id.priceIncT)
            val priceExcT: TextView = mView.findViewById(R.id.priceExcT)
            val pic: ImageView = mView.findViewById(R.id.pic)
            title.text = mItem.title
            authorName.text = mItem.authorName
            priceIT.text = mItem.priceIT
            priceExcT.text = mItem.priceExcT
            //        Glide.with(context).load(mItem.url).into(pic)
            setOnLongClickListener { listener(mItem)
                true }
        }
    }
}
  

затем я установил OnLongClickListener в моем фрагменте (версия 1) :

 override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?,
                              savedInstanceState: Bundle?): View? {
        val v = inflater.inflate(R.layout.cart_fragment, container, false)
        activity = getActivity() as MainActivity
        recyclerView = v.findViewById(R.id.recylerItemCart)

        totalAmountView = v.findViewById(R.id.total_amount)
        activity.toolbarTitle.text = resources.getString(R.string.cart)
        RequestGetCart.MakeRequestTask(this, activity).execute(activity.user.token)
        v.findViewById<Button>(R.id.checkout).setOnClickListener(this)
        recyclerView.setOnLongClickListener {
            recyclerView.adapter = RecyclerItemCart(cart.elements, activity){
                RequestRemoveItemCart.MakeRequestTask(this, activity).execute(activity.user.token, it.id, "1")
            }
           AlertDialog.Builder(activity)
                .setTitle("REMOVE ITEM")
                .setMessage(context!!.resources.getString(R.string.removeItemCart))
                .setPositiveButton(android.R.string.yes, DialogInterface.OnClickListener { dialog, which ->
                    recyclerView.adapter = RecyclerItemCart(cart.elements, activity){
                        RequestRemoveItemCart.MakeRequestTask(this, activity).execute(activity.user.token, it.id, "1")
                    }
                })
                .setNegativeButton(android.R.string.no, null)
                .setIcon(android.R.drawable.ic_dialog_alert)
                .show()
            true}
        return v
    }
  

но когда я пытаюсь нажать LongClick, ничего не происходит. Он никогда не попадает в прослушиватель.

Итак, я попытался немного изменить, как :

 recyclerView.setOnLongClickListener(View.OnLongClickListener {
            true
             }) {
            recyclerView.adapter = RecyclerItemCart(cart.elements, activity){
                RequestRemoveItemCart.MakeRequestTask(this, activity).execute(activity.user.token, it.id, "1")
            }
           AlertDialog.Builder(activity)
                .setTitle("REMOVE ITEM")
                .setMessage(context!!.resources.getString(R.string.removeItemCart))
                .setPositiveButton(android.R.string.yes, DialogInterface.OnClickListener { dialog, which ->
                    recyclerView.adapter = RecyclerItemCart(cart.elements, activity){
                        RequestRemoveItemCart.MakeRequestTask(this, activity).execute(activity.user.token, it.id, "1")
                    }
                })
                .setNegativeButton(android.R.string.no, null)
                .setIcon(android.R.drawable.ic_dialog_alert)
                .show()
            true}
  

Но у меня возникает ошибка при использовании

 recyclerView.setOnLongClickListener(View.OnLongClickListener {
            true
             })
  

это говорит о том, что я не передаю хорошие аргументы, но я передаю View.OnLongClickListener, как и просили.
Если у вас есть какие-либо идеи об этом setOnLongClickListener или другом способе обработки длинного щелчка и передачи данных из Recycler во фрагмент.
Только одно условие: я хочу делать что-то в моем фрагменте, а не в моем утилизаторе.

Так, например, я могу перехватить onLongClick из адаптера и вызвать обратный вызов, чтобы вернуться к фрагменту, но я не знаю, как это сделать.

Комментарии:

1. Вы хотите прослушивать длинные клики на каждом из них itemView или на всех recyclerView целиком?

2. @underoid в каждом представлении ItemView. Например, когда я долго нажимаю на элемент 1, я хочу показать заголовок элемента 1 (из фрагмента, как я уже говорил ранее).

Ответ №1:

Я думаю, что код адаптера в порядке, за исключением избыточности OnItemClickListener . Поскольку вы передаете прослушиватель в конструкторе адаптера, вашим методом обратного вызова будет lambda, где вы инициализируете адаптер.

 override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
    ...
    recyclerView = v.findViewById(R.id.recylerItemCart)
    recyclerView.layoutManager = LinearLayoutManager(context)
    recyclerView.adapter = RecyclerItemCart(cart.elements, activity) {
        //this is the lambda (listener) that you pass to the adapter,
        // and this will be called when long click occurs on itemView as it has already set in ViewHolder
    }
    ...
    return v
}
  

Комментарии:

1. Я также удалил файл setOnLongClickListener в onBindViewHolder в адаптере, и он работает, как вы сказали, когда я передаю лямбда-выражение! Спасибо вам!