Trejkaz
10/11/2025, 7:36 PMloadImageBitmap(InputStream) is deprecated. The replacement is the resource API, which is fine for resources, but what if I want to load a user-provided image?ephemient
10/11/2025, 8:25 PMTrejkaz
10/11/2025, 8:40 PMTrejkaz
10/11/2025, 8:51 PMTrejkaz
10/11/2025, 8:52 PMTrejkaz
10/11/2025, 9:04 PMTrejkaz
10/11/2025, 9:04 PMephemient
10/12/2025, 4:12 AMephemient
10/12/2025, 4:18 AMephemient
10/12/2025, 4:19 AMMichael Paus
10/12/2025, 6:22 AM//-- ImageLoader.kt
import androidx.compose.ui.graphics.ImageBitmap
expect fun imageBitmapFromBytes(encodedImageData: ByteArray): ImageBitmap
//-- ImageLoader.skikoCommon.kt
import androidx.compose.ui.graphics.ImageBitmap
import androidx.compose.ui.graphics.toComposeImageBitmap
import org.jetbrains.skia.Image
import org.jetbrains.skia.impl.use
actual fun imageBitmapFromBytes(encodedImageData: ByteArray): ImageBitmap {
return Image.makeFromEncoded(encodedImageData).use { it.toComposeImageBitmap() } // 'use' closes intermediate image
}
//-- ImageLoader.android.kt
import android.graphics.BitmapFactory
import androidx.compose.ui.graphics.ImageBitmap
import androidx.compose.ui.graphics.asImageBitmap
actual fun imageBitmapFromBytes(encodedImageData: ByteArray): ImageBitmap {
return BitmapFactory.decodeByteArray(encodedImageData, 0, encodedImageData.size).asImageBitmap()
}
You only have to distinguish Android from all other targets. Skiko can do that out of the box and you only need some different code for Android (which is also available out of the box on Android). Now your image bytes can come from anywhere and with a single function in common code you can convert them to a Compose image.Trejkaz
10/12/2025, 7:42 AMTrejkaz
10/12/2025, 7:43 AMTrejkaz
10/12/2025, 7:49 AMMichael Paus
10/12/2025, 8:49 AM@OptIn(ExperimentalKotlinGradlePluginApi::class)
applyDefaultHierarchyTemplate {
common {
group("skikoCommon") {
withJvm()
withIos()
withJs()
withWasmJs()
}
}
}ephemient
10/12/2025, 9:04 AMMichael Paus
10/12/2025, 9:26 AMephemient
10/12/2025, 10:33 AMwhat if I want to load a user-provided image?doesn't sound like an internal data source
ephemient
10/12/2025, 10:51 AMvar image by remember(file) { mutableStateOf<Image?>(null) }
LaunchedEffect(file) {
withContext(<http://Dispatchers.IO|Dispatchers.IO>) {
image = Image.makeFromEncoded(file.readBytes()).use { it.toComposeImageBitmap() }
}
}
val painter = image?.let { BitmapPainter(it) } ?: placeholder…
or whatever you want to do, but this is a solved problem alreadyMichael Paus
10/12/2025, 11:29 AM