2 min read
Kotlin Extensions I Use in Every Project

Over the past couple of years switching to Kotlin full-time, I’ve accumulated a small library of extension functions that I copy into every new project. These aren’t fancy - they’re just helpers that come up constantly and make the code noticeably easier to read.

1. View Visibility Shortcuts

Chaining visibility changes becomes much cleaner.

fun View.show() { visibility = View.VISIBLE }
fun View.hide() { visibility = View.GONE }
fun View.invisible() { visibility = View.INVISIBLE }

// Usage: textView.hide()

2. Safe String Conversions

Eliminate repetitive try-catch blocks when parsing user input.

fun String?.toIntOrDefault(default: Int = 0): Int {
    return this?.toIntOrNull() ?: default
}

// Usage: val age = editText.text.toString().toIntOrDefault(18)

3. Toast Shorthand

fun Context.toast(message: String, length: Int = Toast.LENGTH_SHORT) {
    Toast.makeText(this, message, length).show()
}

// Usage: toast("Saved")

4. Date Formatting

Turn timestamps into readable dates inline.

fun Long.toDateString(pattern: String = "yyyy-MM-dd"): String {
    val formatter = SimpleDateFormat(pattern, Locale.getDefault())
    return formatter.format(Date(this))
}

// Usage: val dateStr = task.updatedAt.toDateString("MMM dd, yyyy")

5. Lifecycle-Aware Coroutine Launch

Now that viewModelScope is available in the stable lifecycle extensions, this helper wraps it with automatic error handling so I don’t have to repeat the try-catch in every ViewModel.

fun ViewModel.launchSafe(block: suspend CoroutineScope.() -> Unit) {
    viewModelScope.launch(Dispatchers.Main) {
        try {
            block()
        } catch (e: Exception) {
            Log.e("ViewModel", "Coroutine error: ${e.message}")
        }
    }
}

When NOT to Use Extensions

  • Core logic: If a function modifies the internal state of a class, it belongs inside that class.
  • Private members: Extensions cannot see private APIs.
  • One-off functions: If you only use it once, a standard function is simpler.

I organise extensions by context in separate files - ViewExt.kt, DateExt.kt - so they’re easy to find and easy to copy across projects.