milancodes
milancodes

Reputation: 173

Type Mismatch with Kotlin Generic Adapter

I'm trying to create a Base Adapter class, which can be extended by all other RecyclerView adapters, since they don't differ much from each other.

Here's my BaseAdapter class:

private const val IS_EMPTY = 0
private const val IS_NOT_EMPTY = 1

abstract class BaseAdapter<T>(
    @LayoutRes open val layoutId: Int,
    private val dataList: ArrayList<T>?
) : RecyclerView.Adapter<BaseViewHolder<Any>>() {

    abstract fun setViewHolder(parent: ViewGroup): BaseViewHolder<Any>
    abstract fun bind(containerView: View, item: T)

    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): BaseViewHolder<Any> {
        return setViewHolder(parent)
    }

    override fun onBindViewHolder(holder: BaseViewHolder<Any>, position: Int) {
        bind(holder.containerView, dataList!![position])
    }

    override fun getItemCount(): Int = dataList!!.size

    override fun getItemViewType(position: Int): Int = if (dataList!!.size == 0) IS_EMPTY else IS_NOT_EMPTY
}

Here's my BaseViewHolder class:

abstract class BaseViewHolder<in T: Any>(override val containerView: View) : RecyclerView.ViewHolder(containerView),
    LayoutContainer

A snippet from the class (LessonsRecyclerViewAdapter) where I'm trying to implement it:

override fun setViewHolder(parent: ViewGroup): BaseViewHolder<Any> {
        val view = LayoutInflater.from(parent.context).inflate(layoutId, parent, false)
        return LessonsViewHolder(view)
        //Type mismatch: Required: BaseViewHolder<Any> Found: LessonsRecyclerViewAdapter.LessonsViewHolder
    }

LessonsViewHolder is just an empty class, extending BaseViewHolder:

class LessonsViewHolder(override val containerView: View): BaseViewHolder<Lesson>(containerView)

Why am I getting Type Mismatch Error, when LessonsViewHolder extends BaseViewHolder?

Upvotes: 0

Views: 199

Answers (1)

Stachu
Stachu

Reputation: 1724

that's because you're mixing type T and Any, try this:
BaseViewHolder

abstract class BaseViewHolder<T>(override val containerView: View) :
    RecyclerView.ViewHolder(containerView),
    LayoutContainer

BaseViewAdapter

abstract class BaseAdapter<T>(
    @LayoutRes open val layoutId: Int,
    private val dataList: ArrayList<T>?
) : RecyclerView.Adapter<BaseViewHolder<T>>() {

    abstract fun setViewHolder(parent: ViewGroup): BaseViewHolder<T>
    abstract fun bind(containerView: View, item: T)

    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): BaseViewHolder<T> {
        return setViewHolder(parent)
    }

    override fun onBindViewHolder(holder: BaseViewHolder<T>, position: Int) {
        bind(holder.containerView, dataList!![position])
    }

    override fun getItemCount(): Int = dataList!!.size

    override fun getItemViewType(position: Int): Int =
        if (dataList!!.size == 0) IS_EMPTY else IS_NOT_EMPTY
}

Upvotes: 1

Related Questions