Can I write:
@IdRes
abstract fun getHeaderId(): Int
With a val
instead of a fun
in kotlin? It complains I need a backing field or delegate when i write:
@IdRes <-- errors
abstract val headerId: Int
Which is the most idiomatic in this case? One-liner with a fun
or mess around with a backing field (I'm not used to backing fields, maybe it's change-resistance, i have never really used them so i think they are unpleasant)
Since abstract val
or var
is just a function without a backing field it cannot be annotated by IdRes
annotation but there is a workaround. You can use it like this:
@get:IdRes
abstract val headerId: Int
EDIT:
Why does this works? We need to closer inspect IdRes
annotation and its source code:
@Documented
@Retention(CLASS)
@Target({METHOD, PARAMETER, FIELD, LOCAL_VARIABLE})
public @interface IdRes {
}
As we can see this annotation can be used on methods, parameters, fields and local variables. When we use abstract val
it's neither of those since it is abstract and we cannot have abstract fields in Java. Normally equivalent of abstract val something: Int
in Java is:
private int something
public int getSomething() {
return something;
}
From example, it's easy to see that the private field is what is called backing field of a property and you can't have those as abstract so that was the problem.
As mentioned in @AtulGupta comment, @theKarlo 's answer does not force the subclass to pass in an IdRes
.
Therefore, an alternative to
@IdRes
abstract fun getHeaderId(): Int
and
@get:IdRes
abstract val headerId: Int
Is to pass the value into the constructor of the class itself, so that the backing field issue can be avoided and the subclass is forced to pass in an IdRes
.
For example:
abstract class SomeClass(@IdRes val idRes: Int)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With