Добавление нескольких OnClickListeners в RecyclerView с использованием Kotlin - PullRequest
2 голосов
/ 29 мая 2020

Я пытаюсь найти работающее приложение, используя Kotlin, и я столкнулся с препятствием при попытке реализовать OnClickListeners для моих трех кнопок. У меня мой RecyclerView заполняется правильно, но, несмотря на соблюдение рекомендаций этого сообщения SO (кроме Kotlin) и документации , у меня все еще возникают проблемы с реализацией



Приведенный ниже код - это мой класс адаптера для реализации.

class BrowseHabitsAdapter(private val habits: ArrayList<Habit>) :
    RecyclerView.Adapter<BrowseHabitsAdapter.ViewHolder>() {

    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
        val itemView = LayoutInflater.from(parent.context).inflate(R.layout.habit_card, parent, false)

        return ViewHolder(itemView, object: HabitClickListener {
            override fun onDecrease(position: Int) {
                val streak = itemView.dayCounter.text.toString().toInt()
                itemView.dayCounter.text = streak.dec().toString()
            }

            override fun onIncrease(position: Int) {
                val streak = itemView.dayCounter.text.toString().toInt()
                itemView.dayCounter.text = streak.inc().toString()
            }

            override fun onEdit(position: Int) {
                TODO("Change Activity to Edit")
            }
        })


    }

    override fun onBindViewHolder(holder: ViewHolder, position: Int) {
        val currentItem = habits[position]

        holder.habitTitle.text = currentItem.title
        holder.streak.text = currentItem.streak.toString()
    }

    override fun getItemCount() = habits.size


    class ViewHolder(itemView : View, listener : HabitClickListener) : RecyclerView.ViewHolder(itemView), View.OnClickListener {
        val habitTitle: TextView = itemView.habitTitle
        val streak: TextView = itemView.dayCounter
        val decreaseCounterButton : Button = itemView.decreaseCounterButton
        val increaseCounterButton : Button = itemView.increaseCounterButton
        val listener = listener

        init {
            decreaseCounterButton.setOnClickListener(this)
            increaseCounterButton.setOnClickListener(this)
        }

        override fun onClick(v: View?) {
            when (itemView.id) {
                itemView.decreaseCounterButton.id -> listener.onDecrease(this.layoutPosition)
                itemView.increaseCounterButton.id -> listener.onIncrease(this.layoutPosition)
            }
        }
    }

    interface HabitClickListener {
        fun onDecrease(position : Int)
        fun onIncrease(position : Int)
        fun onEdit(position : Int)
    }
}

, а ниже - мой XML код, определяющий одну из моих карт:

<?xml version="1.0" encoding="utf-8"?>
<androidx.cardview.widget.CardView xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:id="@+id/cardView"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_marginStart="10dp"
    android:layout_marginTop="10dp"
    android:layout_marginEnd="10dp"
    app:cardBackgroundColor="#eeeeee"
    app:cardCornerRadius="10dp"
    app:layout_constraintEnd_toEndOf="parent"
    app:layout_constraintStart_toStartOf="parent"
    app:layout_constraintTop_toTopOf="parent"
    tools:context=".MainActivity">


    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical">

        <LinearLayout
            android:id="@+id/cardHeader"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:orientation="horizontal">

            <TextView
                android:id="@+id/habitTitle"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_marginLeft="10dp"
                android:layout_marginTop="10dp"
                android:layout_marginRight="10dp"
                android:text="@string/default_card_title"
                android:textSize="18sp" />

            <Space
                android:layout_width="0dp"
                android:layout_height="wrap_content"
                android:layout_gravity="center"
                android:layout_weight="1" />

            <ImageView
                android:id="@+id/settingsIcon"
                android:layout_width="25dp"
                android:layout_height="25dp"
                android:layout_gravity="bottom"
                android:layout_marginRight="10dp"
                app:srcCompat="@android:drawable/ic_menu_manage" />
        </LinearLayout>

        <LinearLayout
            android:id="@+id/cardControls"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:gravity="center"
            android:orientation="horizontal">

            <Button
                android:id="@+id/decreaseCounterButton"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_margin="10dp"
                android:text="-"
                android:textAllCaps="false"
                android:textSize="30sp" />

            <Space
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_weight="1" />

            <TextView
                android:id="@+id/dayCounter"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_margin="10dp"
                android:fontFamily="sans-serif-medium"
                android:text="0"
                android:textAlignment="center"
                android:textSize="30sp"
                android:textStyle="bold" />

            <Space
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_weight="1" />

            <Button
                android:id="@+id/increaseCounterButton"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_margin="10dp"
                android:text="+"
                android:textSize="30sp" />
        </LinearLayout>

    </LinearLayout>

</androidx.cardview.widget.CardView>

Мы будем очень признательны за любые дополнительные объяснения, которые могут быть предоставлены относительно того, что я сделал неправильно и что происходит в деталях!

Ответы [ 2 ]

2 голосов
/ 29 мая 2020

Вы находитесь в kotlin, поэтому вам нужно реализовать View.OnClickListener, вы можете напрямую использовать setOnClickListener в любом представлении.

Внутри вашего класса ViewHolder:

itemView.increaseCounterButton.setOnClickListener{

       listener.onIncrease(this.layoutPosition)
 }       

itemView.decreaseCounterButton.setOnClickListener{

      listener.onDecrease(this.layoutPosition)
 } 
0 голосов
/ 29 мая 2020

Это должно быть view?.id вместо itemView.id

        override fun onClick(v: View?) {
            when (v?.id) {
                itemView.decreaseCounterButton.id -> listener.onDecrease(this.layoutPosition)
                itemView.increaseCounterButton.id -> listener.onIncrease(this.layoutPosition)
            }
        }

Кроме того, ваш код содержит ошибки. Вы обрабатываете HabitClickListener только обновление пользовательского интерфейса, при прокрутке ваши данные будут обновляться на базе habits. Это означает, что он будет возвращаться при прокрутке. Убедитесь, что streak модели Habit равно var

        return ViewHolder(itemView, object: HabitClickListener {
            override fun onDecrease(position: Int) {
                habits[position].streak = habits[position].streak.dec()
                itemView.dayCounter.text = shabits[position].streak.toString()
            }

            override fun onIncrease(position: Int) {
                habits[position].streak = habits[position].streak.inc()
                itemView.dayCounter.text = shabits[position].streak.toString()
            }

            override fun onEdit(position: Int) {
                TODO("Change Activity to Edit")
            }
        })
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...