Skip to content

[iOS] readBytes() for camera photos fails to decode with Skia after upgrading from 0.12.0 to 0.13.0 #555

@mianaliasjad

Description

@mianaliasjad

FileKit version: 0.13.0 (works on 0.12.0)
Platform: iOS (Kotlin Multiplatform / Compose Multiplatform)

Description

After upgrading from FileKit 0.12.0 to 0.13.0, readBytes() on iOS returns bytes that fail to
decode via Skia's Image::makeFromEncoded for camera photos. Screenshots and gallery images
work fine. The same code works on 0.12.0.

Steps to reproduce

  1. Use FileKit.openFilePicker(type = FileKitType.Image) on iOS
  2. Pick a photo taken with the device camera
  3. Call readBytes() on the returned PlatformFile
  4. Pass the bytes to Compose Multiplatform's ByteArray.decodeToImageBitmap()
  5. Crash: IllegalArgumentException: Failed to Image::makeFromEncoded

Code

val platformFile = FileKit.openFilePicker(
    type = FileKitType.Image,
    mode = FileKitMode.Single,
)

val bytes = platformFile?.readBytes()
val imageBitmap = bytes?.decodeToImageBitmap() // 💥 crashes on 0.13.0, works on 0.12.0

Expected behavior

readBytes() should return bytes in a format decodable by Skia (JPEG/PNG), consistent with
0.12.0 behavior.

Actual behavior

On 0.13.0, readBytes() returns bytes for camera photos that Skia's Image::makeFromEncoded
cannot decode, causing the crash. The same code with 0.12.0 works fine for the same photos.

Screenshots work fine on both versions — only camera photos are affected.

Something may have changed in how readBytes() handles camera photos between 0.12.0 and 0.13.0
(possibly related to the "aligned with Apple PhotoKit guidance" change in the 0.13.0 release
notes).

Crash log

LaunchServices: store (null) or url (null) was nil: Error Domain=NSOSStatusErrorDomain Code=-54
"process may not map database"

kotlin.IllegalArgumentException: Failed to Image::makeFromEncoded
    at org.jetbrains.skia.Image.Companion#makeFromEncoded
    at androidx.compose.ui.graphics#createImageBitmap
    at androidx.compose.ui.graphics#decodeToImageBitmap

Workaround

Pass the raw bytes to UIKit's UIImage.imageWithData() instead of Skia's decoder — UIKit handles
these bytes fine:

// Instead of:
val imageBitmap = bytes?.decodeToImageBitmap() // Skia - fails

// Use UIKit directly:
val nsData = bytes.toNSData()
val uiImage = UIImage.imageWithData(nsData) // UIKit - works

Environment

  • FileKit: 0.13.0 (regression from 0.12.0)
  • Kotlin: 2.3.10
  • Compose Multiplatform: 1.10.3
  • iOS: 17+
  • Device: iPhone with HEIF camera format enabled

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions