1

I'm trying to implement an empty state recycler view based on this post. I have migrated the solution to Kotlin, but the problem is I'm not able to extend CustomRecyclerView.Adapter (Adapter is an abstract class defined in RecyclerView) from the newly defined custom recycler view in Kotlin. And I have observed the same CustomRecyclerView.Adapter can be extended in Java.

Custome RecyclerView implementation

open class CustomRecyclerView: RecyclerView {


private var emptyStateView : View? = null

constructor(context: Context) : super(context)
constructor(context: Context , attrs: AttributeSet) : super(context,attrs)
constructor(context: Context , attrs: AttributeSet, defstyle: Int) : super(context,attrs,defstyle)


var observer: AdapterDataObserver = object : AdapterDataObserver() {

    override fun onChanged() {
        super.onChanged()
        initEmptyView()
    }

    override fun onItemRangeRemoved(positionStart: Int, itemCount: Int) {
        super.onItemRangeRemoved(positionStart, itemCount)
        initEmptyView()
    }

    override fun onItemRangeInserted(positionStart: Int, itemCount: Int) {
        super.onItemRangeInserted(positionStart, itemCount)
        initEmptyView()
    }
}

private fun initEmptyView() {
    emptyStateView?.let {
        it.visibility = if (adapter == null || adapter!!.itemCount == 0) View.VISIBLE else View.GONE
        this@CustomRecyclerView.visibility = if (adapter == null || adapter!!.itemCount == 0) View.GONE else View.VISIBLE
    }
}

override fun setAdapter(adapter: Adapter<*>?) {
    val oldAdapter = getAdapter()
    super.setAdapter(adapter)
    oldAdapter?.unregisterAdapterDataObserver(observer)
    adapter?.registerAdapterDataObserver(observer)
}

/**
 * @param emptyView is the view which is going to display when the recycler view is empty
 * **/
fun setEmptyView(emptyView: View) {
    this.emptyStateView = emptyView
    initEmptyView()
}}

Adding images for the extension implementation in java and kotin

Kotlin java

Arun P M
  • 352
  • 1
  • 15
  • 1
    what is your problem exactly? In Kotlin you would extend the Adapter the same way you do it in Java: `class YourAdapter: RecyclerView.Adapter()`. The tutorial you linked does exactly that. Are you getting any IDE errors? – Droidman Nov 14 '19 at 08:29
  • I'm getting the error: Unresolved reference Adapter – Arun P M Nov 14 '19 at 08:46
  • 2
    what you are probably doing is `class YourAdapter: YourCustomRecyclerView.Adapter()`, what you *should* do instead is `class YourAdapter: RecyclerView.Adapter()`. Because `Adapter` is part of the `RecyclerView` itself and not its subclasses, see RV source code line 6700: `public abstract static class Adapter ` – Droidman Nov 14 '19 at 08:49
  • Thanks, @Droidman, that does make sense. Let me try with normal RecyclerView.Adapter. – Arun P M Nov 14 '19 at 09:07

2 Answers2

3

To summarise the comments: inherit from RecyclerView.Adapter, see below

YourAdapter: RecyclerView.Adapter<YourViewHolder>()

And just a hint, here's the Kotlin way to extend a class with multiple constructors:

class CustomRecyclerView @JvmOverloads constructor(
        context: Context,
        attrs: AttributeSet? = null,
        defStyleAttr: Int = 0
) : RecyclerView(context, attrs, defStyleAttr)

For more info, check @JvmOverloads

Droidman
  • 11,485
  • 17
  • 93
  • 141
  • 1
    adding more insight: https://stackoverflow.com/questions/51266313/is-it-possible-to-override-static-method-in-kotlin?rq=1 – Arun P M Nov 14 '19 at 09:42
0

It should be RecyclerView.Adapter.. and set adapter to customRecyclerView.

Ramesh Yankati
  • 1,197
  • 9
  • 13