Google is committed to advancing racial equity for Black communities. See how.

Parcelable implementation generator

The kotlin-parcelize plugin provides a Parcelable implementation generator.

When you annotate a class with @Parcelize, a Parcelable implementation is automatically generated, as shown in the following example:

import kotlinx.parcelize

@Parcelize
class User(val firstName: String, val lastName: String, val age: Int): Parcelable

@Parcelize requires all serialized properties to be declared in the primary constructor. The plugin issues a warning on each property with a backing field declared in the class body. Also, you can't apply @Parcelize if some of the primary constructor parameters are not properties.

If your class requires more advanced serialization logic, write it inside a companion class:

@Parcelize
data class User(val firstName: String, val lastName: String, val age: Int) : Parcelable {
    private companion object : Parceler<User> {
        override fun User.write(parcel: Parcel, flags: Int) {
            // Custom write implementation
        }

        override fun create(parcel: Parcel): User {
            // Custom read implementation
        }
    }
}

Supported types

@Parcelize supports a wide range of types:

  • Primitive types (and their boxed versions)
  • Objects and enums
  • String, CharSequence
  • Exception
  • Size, SizeF, Bundle, IBinder, IInterface, FileDescriptor
  • SparseArray, SparseIntArray, SparseLongArray, SparseBooleanArray
  • All Serializable (including Date) and Parcelable implementations
  • Collections of all supported types: List (mapped to ArrayList), Set (mapped to LinkedHashSet), Map (mapped to LinkedHashMap)
    • Also a number of concrete implementations: ArrayList, LinkedList, SortedSet, NavigableSet, HashSet, LinkedHashSet, TreeSet, SortedMap, NavigableMap, HashMap, LinkedHashMap, TreeMap, ConcurrentHashMap
  • Arrays of all supported types
  • Nullable versions of all supported types

Custom Parcelers

If your type is not supported directly, you can write a Parceler mapping object for it.

class ExternalClass(val value: Int)

object ExternalClassParceler : Parceler<ExternalClass> {
    override fun create(parcel: Parcel) = ExternalClass(parcel.readInt())

    override fun ExternalClass.write(parcel: Parcel, flags: Int) {
        parcel.writeInt(value)
    }
}

You can apply external parcelers using @TypeParceler or @WriteWith annotations:

// Class-local parceler
@Parcelize
@TypeParceler<ExternalClass, ExternalClassParceler>()
class MyClass(val external: ExternalClass)

// Property-local parceler
@Parcelize
class MyClass(@TypeParceler<ExternalClass, ExternalClassParceler>() val external: ExternalClass)

// Type-local parceler
@Parcelize
class MyClass(val external: @WriteWith<ExternalClassParceler>() ExternalClass)

Feedback

If you encounter any issues with the kotlin-parcelize plugin, you can file a bug.