-
Notifications
You must be signed in to change notification settings - Fork 326
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #626 from mkeeda/thumb-up
Thumbs-up function 👍
- Loading branch information
Showing
26 changed files
with
819 additions
and
57 deletions.
There are no files selected for viewing
41 changes: 41 additions & 0 deletions
41
...ponent/androidcomponent/src/main/java/io/github/droidkaigi/confsched2020/ext/Animators.kt
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,41 @@ | ||
package io.github.droidkaigi.confsched2020.ext | ||
|
||
import android.animation.Animator | ||
import android.animation.AnimatorListenerAdapter | ||
import kotlinx.coroutines.suspendCancellableCoroutine | ||
import kotlin.coroutines.resume | ||
|
||
// This function is copied from https://medium.com/androiddevelopers/suspending-over-views-19de9ebd7020 | ||
|
||
suspend fun Animator.awaitEnd() = suspendCancellableCoroutine<Unit> { cont -> | ||
// Add an invokeOnCancellation listener. If the coroutine is | ||
// cancelled, cancel the animation too that will notify | ||
// listener's onAnimationCancel() function | ||
cont.invokeOnCancellation { cancel() } | ||
|
||
addListener(object : AnimatorListenerAdapter() { | ||
private var endedSuccessfully = true | ||
|
||
override fun onAnimationCancel(animation: Animator) { | ||
// Animator has been cancelled, so flip the success flag | ||
endedSuccessfully = false | ||
} | ||
|
||
override fun onAnimationEnd(animation: Animator) { | ||
// Make sure we remove the listener so we don't keep | ||
// leak the coroutine continuation | ||
animation.removeListener(this) | ||
|
||
if (cont.isActive) { | ||
// If the coroutine is still active... | ||
if (endedSuccessfully) { | ||
// ...and the Animator ended successfully, resume the coroutine | ||
cont.resume(Unit) | ||
} else { | ||
// ...and the Animator was cancelled, cancel the coroutine too | ||
cont.cancel() | ||
} | ||
} | ||
} | ||
}) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
40 changes: 40 additions & 0 deletions
40
corecomponent/androidcomponent/src/main/java/io/github/droidkaigi/confsched2020/ext/Views.kt
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,40 @@ | ||
package io.github.droidkaigi.confsched2020.ext | ||
|
||
import android.view.View | ||
import kotlinx.coroutines.suspendCancellableCoroutine | ||
import kotlin.coroutines.resume | ||
|
||
// This function is copied from https://medium.com/androiddevelopers/suspending-over-views-19de9ebd7020 | ||
|
||
suspend fun View.awaitNextLayout() = suspendCancellableCoroutine<Unit> { cont -> | ||
// This lambda is invoked immediately, allowing us to create | ||
// a callback/listener | ||
|
||
val listener = object : View.OnLayoutChangeListener { | ||
override fun onLayoutChange( | ||
v: View?, | ||
left: Int, | ||
top: Int, | ||
right: Int, | ||
bottom: Int, | ||
oldLeft: Int, | ||
oldTop: Int, | ||
oldRight: Int, | ||
oldBottom: Int | ||
) { | ||
// The next layout has happened! | ||
// First remove the listener to not leak the coroutine | ||
v?.removeOnLayoutChangeListener(this) | ||
// Finally resume the continuation, and | ||
// wake the coroutine up | ||
cont.resume(Unit) | ||
} | ||
} | ||
// If the coroutine is cancelled, remove the listener | ||
cont.invokeOnCancellation { removeOnLayoutChangeListener(listener) } | ||
// And finally add the listener to view | ||
addOnLayoutChangeListener(listener) | ||
|
||
// The coroutine will now be suspended. It will only be resumed | ||
// when calling cont.resume() in the listener above | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.