I'm new to Kotlin and I started a new Android project using this language. From the beginning I faced some issues when a tried to make a schema of a MVP pattern in Kotlin using generic types. This is what I'm trying to accomplish:
AbstractBasePresenter.kt
abstract class AbstractBasePresenter<T: Any> internal constructor(
private val compositeDisposable: CompositeDisposable = CompositeDisposable()
) {
constructor() : this(CompositeDisposable())
private var view: T? = null
fun bind(view: T) {
if (this.view != null) throw IllegalStateException("view already bound")
this.view = view
afterBind()
}
fun unbind() {
if (this.view == null) throw IllegalStateException("view already unbound")
this.view = null
compositeDisposable.clear()
}
abstract fun afterBind()
protected fun addDisposable(disposable: Disposable): Disposable =
disposable.also {
compositeDisposable.add(it)
}
protected fun view(): T = view ?: throw IllegalStateException("view not bound")
}
BaseView.kt
interface BaseView<T : AbstractBasePresenter<*>> {
fun getPresenter(): T
}
AbstractBaseActivity
abstract class AbstractBaseActivity<T : AbstractBasePresenter<*>> : AppCompatActivity(), BaseView<T> {
override fun onStart() {
super.onStart()
getPresenter().bind(this)
}
override fun onStop() {
getPresenter().unbind()
super.onStop()
}
override fun startActivity(intent: Intent?) {
super.startActivity(intent)
slideInRight(this)
}
override fun onBackPressed() {
super.onBackPressed()
slideOutRight(this)
}
}
When I'm trying to use the base class I want something like bellow:
SplashActivity
class SplashActivity : AbstractBaseActivity<SplashPresenter>(), SplashActivityView {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.splash_activity)
}
override fun getPresenter(): SplashPresenter {
TODO("not implemented") //To change body of created functions use File | Settings | File Templates.
}
}
SplashPresenter
class SplashPresenter : AbstractBasePresenter<SplashActivityView>() {
override fun afterBind() {
TODO("not implemented") //To change body of created functions use File | Settings | File Templates.
}
}
SplashActivityView
interface SplashActivityView {
}
The idea is that this type of implementation is working fine in Java, but after the conversion it seems that with generic types from Kotlin I'm missing something and I got the following error in AbstractBaseActivity at binding the view:
**getPresenter().bind(this)** ------> "this" is underlined and I have the error: **"Type mismatch. Required nothing AbstractBaseActivity<T> found"**
Please tell me where I am doing things wrong or give me another type of solution to accomplish the actual BaseActivity scope (bind and unbing from a single place). Thank you!