DEV Community

Cover image for Easily manage image type with sealed classes
5AbhishekSaxena
5AbhishekSaxena

Posted on

Easily manage image type with sealed classes

This post was originally posted on medium.

With the introduction of sealed classes in Kotlin, it opened up a way to easily handle restricted hierarchies.
The most common use case of a sealed class is with the handling Result<T> of an API response.

…..but there are way more applications of the sealed classes than you can imagine. I'll discuss one of them here, which would be to handle image type in android.
The source of the image can either be remote, i.e, a URL or local storage. Since the resource can come from only these two types, it makes a perfect use case for the sealed classes.

sealed class UiImage {
    data class LocalImage(val imageRes: Int) : UiImage()
    data class RemoteImage(val imageUrl: String) : UiImage()
}
Enter fullscreen mode Exit fullscreen mode

You can use the Image everywhere in the project and easily refer to either of the two.

Example:

data class Student(
    val name: String,
    val profileImage: UiImage
)

fun main() {
    val abhishekSaxena = Student("Abhishek Saxena", UiImage.RemoteImage("https://remoteurl.com/images/sample.png"))
    val johnDoe = Student("John Doe", UiImage.LocalImage(R.drawable.default_profile_pic))
}
Enter fullscreen mode Exit fullscreen mode

Additionally, you can easily load images with the image loading library like Glide

 fun ImageView.loadImage(
    image: UiImage
) {
    Glide.with(this.context)
        .load(
            when (image) {
                is UiImage.LocalImage -> image.imageRes
                is UiImage.RemoteImage -> image.imageUrl
            }
        )
        .into(this)
}
Enter fullscreen mode Exit fullscreen mode

You can use it with Jetpack Compose.

You can create a composable that consumes a UiImage, that in-app code ends up being remote, but for previews, you can supply a drawable res, so I can see the full behavior

// Component
@Composable
fun UserProfile(
  profileImage: UiImage,
)

// In production
UserProfile(
  profileImage = UiImage.RemoteImage(avatarURL)
)

// In preview
@Preview
@Composable
fun UserProfilePreview() {
  UserProfile(
    profileImage = UiImage.LocalImage(R.drawable.preview_profile_image)
  )
}
Enter fullscreen mode Exit fullscreen mode

Conclusion

Kotlin sealed classes are really powerful when you have a strict hierarchy of classes. Herewith the images, you can even extend the usage to text as it can be directly passed as a string or as a reference of the string resource.

A special thanks to Adam McNeilly for the feedback and suggestions.

Thank you very much for reading the article. I hope you liked it. Do you have any feedback? Comment below or reach out to me on Twitter.

Cover photo credits:

Photo by Pablo Arroyo on Unsplash

Top comments (0)