Skip to content

Instantly share code, notes, and snippets.

@MiSikora
Created December 6, 2019 06:34
Show Gist options
  • Star 21 You must be signed in to star a gist
  • Fork 5 You must be signed in to fork a gist
  • Save MiSikora/bbb9fc475569913f78e88a81932e06a9 to your computer and use it in GitHub Desktop.
Save MiSikora/bbb9fc475569913f78e88a81932e06a9 to your computer and use it in GitHub Desktop.
Coroutine scope for View
val View.viewScope: CoroutineScope
get() {
val storedScope = getTag(R.string.view_coroutine_scope) as? CoroutineScope
if (storedScope != null) return storedScope
val newScope = ViewCoroutineScope()
if (isAttachedToWindow) {
addOnAttachStateChangeListener(newScope)
setTag(R.string.view_coroutine_scope, newScope)
} else newScope.cancel()
return newScope
}
private class ViewCoroutineScope : CoroutineScope, View.OnAttachStateChangeListener {
override val coroutineContext = SupervisorJob() + Dispatchers.Main
override fun onViewAttachedToWindow(view: View) = Unit
override fun onViewDetachedFromWindow(view: View) {
coroutineContext.cancel()
view.setTag(R.string.view_coroutine_scope, null)
}
}
@RunningShadow-007
Copy link

why no removeOnAttachStateChangeListener

@MiSikora
Copy link
Author

MiSikora commented Nov 9, 2021

Why would I?

@Semeruk
Copy link

Semeruk commented Mar 28, 2024

why no removeOnAttachStateChangeListener

Hey @MiSikora I think it would be effective to invoke removeOnAttachStateChangeListener like in the following code:

val View.viewScope: CoroutineScope
    get() {
        val storedScope = getTag(R.string.view_coroutine_scope) as? ViewCoroutineScope
        if (storedScope != null) {
            if (storedScope.isActive && isAttachedToWindow) {
                return storedScope
            } else {
                this.removeOnAttachStateChangeListener(storedScope)
            }
        }
        val newScope = ViewCoroutineScope()
        if (isAttachedToWindow) {
            setTag(R.string.view_coroutine_scope, newScope)
            this.addOnAttachStateChangeListener(newScope)
        } else {
            newScope.cancel()
        }

        return newScope
    }

What do you think?

@MiSikora
Copy link
Author

What's the point?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment