Reputation: 3339
I'm trying to convert the following Java Code to Kotlin. It compiles and works fine.
public abstract class MvpViewHolder<P extends BasePresenter> extends RecyclerView.ViewHolder {
protected P presenter;
public MvpViewHolder(View itemView) {
super(itemView);
}
public void bindPresenter(P presenter) {
this.presenter = presenter;
presenter.bindView(this);
}
public void unbindPresenter() {
presenter = null;
}
}
In the code I currently have, I get an error on the presenter.bindView(this)
that states Required: Nothing, Found: MvpViewHolder
.
abstract class MvpViewHolder<P>(itemView: View) : RecyclerView.ViewHolder(itemView) where P : BasePresenter<*,*> {
protected var presenter: P? = null
fun bindPresenter(presenter: P): Unit {
this.presenter = presenter
//I get the error here
presenter.bindView(this)
}
fun unbindPresenter(): Unit {
presenter = null
}
}
bindView
is defined like so
public abstract class BasePresenter<M,V> {
fun bindView(view: V) {
this.view = WeakReference(view)
}
}
The only thing I can attribute it to right now is not defining the class generics correctly. As far as I can tell, this
is still a correct instance of the View generic that is expected as the parameter, I also definitely don't see how it could be Nothing
. How can I fix the bug?
EDIT: Java code for BasePresenter
public abstract class BasePresenter<M, V> {
protected M model;
private WeakReference<V> view;
public void bindView(@NonNull V view) {
this.view = new WeakReference<>(view);
if (setupDone()) {
updateView();
}
}
protected V view() {
if (view == null) {
return null;
} else {
return view.get();
}
}
}
Upvotes: 1
Views: 5039
Reputation: 2825
Your bindView
method requires a View
as an argument.
The error you're seeing appears when you define a variable (view
defined on BasePresenter) that can hold a null result or, in your case, a View object.
On the code below you're binding this
as the argument and MapViewHolder isn't a subclass of View.
abstract class MvpViewHolder<P>(itemView: View) : RecyclerView.ViewHolder(itemView) where P : BasePresenter<*,*> {
protected var presenter: P? = null
fun bindPresenter(presenter: P): Unit {
this.presenter = presenter
//I get the error here
presenter.bindView(this) // -> this references MvpViewHolder which isn't a subclass of View
}
fun unbindPresenter(): Unit {
presenter = null
}
}
I think that what you want is to attach the itemView to the presenter because it is in fact a View
object.
EDIT
The problem has to do with defining BasePresenter<*,*>
which means in this case BasePresenter<Nothing, Nothing>
(Nothing is an object in kotlin) - read more about star projections in kotlin on this link.
I would advice defining explicitly the types base presenter is expecting or defining explicitly as BasePresenter<Any?, Any?>
.
Upvotes: 4
Reputation: 2545
You cannot directly use this to point to current class.
You need to use
this@class_name
.
For example if "Example
" is the class
name, you can use
this@Example
It means this
in Java
For more info visit https://kotlinlang.org/docs/reference/this-expressions.html
Upvotes: 0