Kotlin android parcelable
In Kotlin classes and members are final by default. In other words the following declarations have the same bytecode:
@JvmField final val CREATOR: Parcelable.Creator<Person> = PersonCreator()
@JvmField val CREATOR: Parcelable.Creator<Person> = PersonCreator()
So while the generated code has final
keyword and it is not an error it is redundant.
Even though classes and members are final by default there are still a need for final
modifier in Kotlin. One example would be to mark open
method as final
in derived class:
open class Base {
open fun test(){}
}
open class DerivedA : Base(){
final override fun test(){}
}
class DerivedB : DerivedA() {
override fun test(){} //error: 'test' in 'DerivedA' is final and cannot be overriden
}
While it's a good practice to make public static
field final
in java there's no strict requirement for the Parccelable.Creator
field to be marked as such:
Classes implementing the Parcelable interface must also have a non-null static field called CREATOR of a type that implements the Parcelable.Creator interface.
In Kotlin you can use the @Parcelize
Kotlin Android Extension:
@Parcelize
data class User(val id: String, val name: String) : Parcelable
This is a compiler plugin that automatically generates the Parcelable implementation for you.
This page on the Kotlin docs gives more details about it, including requirements, supported types and how to create custom parcelers for unsupported types.
If you are curious and you want dive into the technical details of the implementation, see the Kotlin Evolution and Enhancement Process Compiler Extension to Support android.os.Parcelable
.
This feature was experimental until Kotlin 1.3.40. If you are still using a Kotlin version earlier than 1.3.40, you need to enable the experimental features to use this:
android {
// Enable @Parcelize
// You only need this for Kotlin < 1.3.40
androidExtensions {
experimental = true
}
...
}