Skip to content

Multiplatform

Orbit publishes for Android, Desktop (JVM), iosArm64 and iosSimulatorArm64. All logic lives in commonMain.

Targets

Target Artifact suffix Status
Android -android Verified on device
Desktop (JVM) -desktop Builds, unit tests pass
iOS arm64 -iosarm64 Builds
iOS simulator arm64 -iossimulatorarm64 Builds, unit tests pass

iosX64 is not published. Compose Multiplatform stopped shipping the Intel simulator target as of 1.11, so there is nothing to compile against.

What has actually been run

The full test suite executes on both the JVM and iosSimulatorArm64. Device verification — navigation, rotation, process death, overlays — has been done on Android only. Desktop and iOS compile and pass unit tests but have not been exercised as running apps.

Toolchain

Component Version
Kotlin 2.3.21
Compose Multiplatform 1.11.1
Android Gradle Plugin 9.2.1
Gradle 9.4.1
JVM toolchain 17

Kotlin 2.3.x is a hard floor. Compose Multiplatform 1.11.1 publishes klibs built with Kotlin 2.3.20, and older compilers cannot read them — Kotlin 2.2.x fails at link time on iOS with a KLIB resolver error, not with a clear version message.

No Parcelable

Screen is a plain commonMain interface with no platform supertype:

@Immutable
public interface Screen

Nothing needs @Parcelize, and no expect/actual annotation shim is required to keep commonMain compiling. Back stack persistence uses kotlinx-serialization on every platform, so the same code path runs everywhere rather than diverging per target.

The cost is that screens must be registered for polymorphic serialization, and an unregistered screen fails at runtime rather than at compile time. See Navigation.

Where expect/actual is used

Almost nowhere. Retained state is the only lifecycle-sensitive piece, and it is handled with the multiplatform androidx.lifecycle ViewModel rather than expect/actual: on Android that ViewModel outlives configuration changes, and on other targets it is scoped to its owner. The registry code in commonMain is identical on every platform.

Consuming from a shared module

Add the dependency to commonMain:

kotlin {
    sourceSets {
        commonMain.dependencies {
            implementation("io.github.avelon1a:orbit-foundation:0.0.11")
        }
    }
}

Gradle metadata resolves the right variant per target, so no platform-specific coordinates are needed.

Platform-specific work

Two things are not provided and should live in platform source sets:

Back handling. Android needs BackHandler; iOS uses its own gesture; desktop may need a key binding. Expose it as expect/actual in your app:

@Composable
expect fun PlatformBackHandler(enabled: Boolean, onBack: () -> Unit)

A ViewModelStoreOwner. ProvideOrbit installs the retained registry through the lifecycle ViewModel APIs, which need an owner in the composition. Android activities provide one; on iOS and desktop, ensure your Compose entry point does.