mirror of
https://github.com/element-hq/element-android
synced 2024-11-24 10:25:35 +03:00
Flow migration: use throttleFirst instead of sample on UI
This commit is contained in:
parent
79c5af2585
commit
edf068ee57
11 changed files with 38 additions and 20 deletions
|
@ -67,6 +67,24 @@ fun <T> Flow<T>.chunk(durationInMillis: Long): Flow<List<T>> {
|
|||
}
|
||||
}
|
||||
|
||||
@ExperimentalCoroutinesApi
|
||||
fun <T> Flow<T>.throttleFirst(windowDuration: Long): Flow<T> = flow {
|
||||
var windowStartTime = System.currentTimeMillis()
|
||||
var emitted = false
|
||||
collect { value ->
|
||||
val currentTime = System.currentTimeMillis()
|
||||
val delta = currentTime - windowStartTime
|
||||
if (delta >= windowDuration) {
|
||||
windowStartTime += delta / windowDuration * windowDuration
|
||||
emitted = false
|
||||
}
|
||||
if (!emitted) {
|
||||
emit(value)
|
||||
emitted = true
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun tickerFlow(scope: CoroutineScope, delayMillis: Long, initialDelayMillis: Long = delayMillis): Flow<Unit> {
|
||||
return scope.fixedPeriodTicker(delayMillis, initialDelayMillis).consumeAsFlow()
|
||||
}
|
||||
|
|
|
@ -59,6 +59,7 @@ import im.vector.app.core.extensions.registerStartForActivityResult
|
|||
import im.vector.app.core.extensions.restart
|
||||
import im.vector.app.core.extensions.setTextOrHide
|
||||
import im.vector.app.core.extensions.singletonEntryPoint
|
||||
import im.vector.app.core.flow.throttleFirst
|
||||
import im.vector.app.core.utils.toast
|
||||
import im.vector.app.features.MainActivity
|
||||
import im.vector.app.features.MainActivityArgs
|
||||
|
@ -79,7 +80,6 @@ import im.vector.app.features.themes.ThemeUtils
|
|||
import im.vector.app.receivers.DebugReceiver
|
||||
import kotlinx.coroutines.flow.launchIn
|
||||
import kotlinx.coroutines.flow.onEach
|
||||
import kotlinx.coroutines.flow.sample
|
||||
import org.matrix.android.sdk.api.extensions.tryOrNull
|
||||
import org.matrix.android.sdk.api.failure.GlobalError
|
||||
import reactivecircus.flowbinding.android.view.clicks
|
||||
|
@ -118,7 +118,7 @@ abstract class VectorBaseActivity<VB : ViewBinding> : AppCompatActivity(), Maver
|
|||
|
||||
protected fun View.debouncedClicks(onClicked: () -> Unit) {
|
||||
clicks()
|
||||
.sample(300)
|
||||
.throttleFirst(300)
|
||||
.onEach { onClicked() }
|
||||
.launchIn(lifecycleScope)
|
||||
}
|
||||
|
|
|
@ -35,10 +35,10 @@ import com.google.android.material.bottomsheet.BottomSheetDialog
|
|||
import com.google.android.material.bottomsheet.BottomSheetDialogFragment
|
||||
import dagger.hilt.android.EntryPointAccessors
|
||||
import im.vector.app.core.di.ActivityEntryPoint
|
||||
import im.vector.app.core.flow.throttleFirst
|
||||
import im.vector.app.core.utils.DimensionConverter
|
||||
import kotlinx.coroutines.flow.launchIn
|
||||
import kotlinx.coroutines.flow.onEach
|
||||
import kotlinx.coroutines.flow.sample
|
||||
import reactivecircus.flowbinding.android.view.clicks
|
||||
import timber.log.Timber
|
||||
|
||||
|
@ -168,7 +168,7 @@ abstract class VectorBaseBottomSheetDialogFragment<VB : ViewBinding> : BottomShe
|
|||
|
||||
protected fun View.debouncedClicks(onClicked: () -> Unit) {
|
||||
clicks()
|
||||
.sample(300)
|
||||
.throttleFirst(300)
|
||||
.onEach { onClicked() }
|
||||
.launchIn(viewLifecycleOwner.lifecycleScope)
|
||||
}
|
||||
|
|
|
@ -42,11 +42,11 @@ import im.vector.app.core.dialogs.UnrecognizedCertificateDialog
|
|||
import im.vector.app.core.error.ErrorFormatter
|
||||
import im.vector.app.core.extensions.singletonEntryPoint
|
||||
import im.vector.app.core.extensions.toMvRxBundle
|
||||
import im.vector.app.core.flow.throttleFirst
|
||||
import im.vector.app.features.navigation.Navigator
|
||||
import im.vector.lib.ui.styles.dialogs.MaterialProgressDialog
|
||||
import kotlinx.coroutines.flow.launchIn
|
||||
import kotlinx.coroutines.flow.onEach
|
||||
import kotlinx.coroutines.flow.sample
|
||||
import reactivecircus.flowbinding.android.view.clicks
|
||||
import timber.log.Timber
|
||||
|
||||
|
@ -239,7 +239,7 @@ abstract class VectorBaseFragment<VB : ViewBinding> : Fragment(), MavericksView
|
|||
|
||||
protected fun View.debouncedClicks(onClicked: () -> Unit) {
|
||||
clicks()
|
||||
.sample(300)
|
||||
.throttleFirst(300)
|
||||
.onEach { onClicked() }
|
||||
.launchIn(viewLifecycleOwner.lifecycleScope)
|
||||
}
|
||||
|
|
|
@ -26,12 +26,12 @@ import androidx.lifecycle.lifecycleScope
|
|||
import com.airbnb.mvrx.activityViewModel
|
||||
import im.vector.app.R
|
||||
import im.vector.app.core.extensions.registerStartForActivityResult
|
||||
import im.vector.app.core.flow.throttleFirst
|
||||
import im.vector.app.core.platform.VectorBaseFragment
|
||||
import im.vector.app.core.utils.startImportTextFromFileIntent
|
||||
import im.vector.app.databinding.FragmentSsssAccessFromKeyBinding
|
||||
import kotlinx.coroutines.flow.launchIn
|
||||
import kotlinx.coroutines.flow.onEach
|
||||
import kotlinx.coroutines.flow.sample
|
||||
import org.matrix.android.sdk.api.extensions.tryOrNull
|
||||
import reactivecircus.flowbinding.android.widget.editorActionEvents
|
||||
import reactivecircus.flowbinding.android.widget.textChanges
|
||||
|
@ -50,7 +50,7 @@ class SharedSecuredStorageKeyFragment @Inject constructor() : VectorBaseFragment
|
|||
views.ssssRestoreWithKeyText.text = getString(R.string.enter_secret_storage_input_key)
|
||||
|
||||
views.ssssKeyEnterEdittext.editorActionEvents()
|
||||
.sample(300)
|
||||
.throttleFirst(300)
|
||||
.onEach {
|
||||
if (it.actionId == EditorInfo.IME_ACTION_DONE) {
|
||||
submit()
|
||||
|
|
|
@ -25,12 +25,12 @@ import androidx.core.text.toSpannable
|
|||
import androidx.lifecycle.lifecycleScope
|
||||
import com.airbnb.mvrx.activityViewModel
|
||||
import im.vector.app.R
|
||||
import im.vector.app.core.flow.throttleFirst
|
||||
import im.vector.app.core.platform.VectorBaseFragment
|
||||
import im.vector.app.core.resources.ColorProvider
|
||||
import im.vector.app.databinding.FragmentSsssAccessFromPassphraseBinding
|
||||
import kotlinx.coroutines.flow.launchIn
|
||||
import kotlinx.coroutines.flow.onEach
|
||||
import kotlinx.coroutines.flow.sample
|
||||
import reactivecircus.flowbinding.android.widget.editorActionEvents
|
||||
import reactivecircus.flowbinding.android.widget.textChanges
|
||||
import javax.inject.Inject
|
||||
|
@ -62,7 +62,7 @@ class SharedSecuredStoragePassphraseFragment @Inject constructor(
|
|||
// .colorizeMatchingText(key, colorProvider.getColorFromAttribute(android.R.attr.textColorLink))
|
||||
|
||||
views.ssssPassphraseEnterEdittext.editorActionEvents()
|
||||
.sample(300)
|
||||
.throttleFirst(300)
|
||||
.onEach {
|
||||
if (it.actionId == EditorInfo.IME_ACTION_DONE) {
|
||||
submit()
|
||||
|
|
|
@ -27,11 +27,11 @@ import com.airbnb.mvrx.parentFragmentViewModel
|
|||
import com.airbnb.mvrx.withState
|
||||
import im.vector.app.R
|
||||
import im.vector.app.core.extensions.hideKeyboard
|
||||
import im.vector.app.core.flow.throttleFirst
|
||||
import im.vector.app.core.platform.VectorBaseFragment
|
||||
import im.vector.app.databinding.FragmentBootstrapEnterPassphraseBinding
|
||||
import kotlinx.coroutines.flow.launchIn
|
||||
import kotlinx.coroutines.flow.onEach
|
||||
import kotlinx.coroutines.flow.sample
|
||||
import reactivecircus.flowbinding.android.widget.editorActionEvents
|
||||
import reactivecircus.flowbinding.android.widget.textChanges
|
||||
import javax.inject.Inject
|
||||
|
@ -60,7 +60,7 @@ class BootstrapConfirmPassphraseFragment @Inject constructor() :
|
|||
}
|
||||
|
||||
views.ssssPassphraseEnterEdittext.editorActionEvents()
|
||||
.sample(300)
|
||||
.throttleFirst(300)
|
||||
.onEach {
|
||||
if (it.actionId == EditorInfo.IME_ACTION_DONE) {
|
||||
submit()
|
||||
|
|
|
@ -25,12 +25,12 @@ import androidx.lifecycle.lifecycleScope
|
|||
import com.airbnb.mvrx.parentFragmentViewModel
|
||||
import com.airbnb.mvrx.withState
|
||||
import im.vector.app.R
|
||||
import im.vector.app.core.flow.throttleFirst
|
||||
import im.vector.app.core.platform.VectorBaseFragment
|
||||
import im.vector.app.databinding.FragmentBootstrapEnterPassphraseBinding
|
||||
import im.vector.app.features.settings.VectorLocale
|
||||
import kotlinx.coroutines.flow.launchIn
|
||||
import kotlinx.coroutines.flow.onEach
|
||||
import kotlinx.coroutines.flow.sample
|
||||
import reactivecircus.flowbinding.android.widget.editorActionEvents
|
||||
import reactivecircus.flowbinding.android.widget.textChanges
|
||||
import javax.inject.Inject
|
||||
|
@ -55,7 +55,7 @@ class BootstrapEnterPassphraseFragment @Inject constructor() :
|
|||
views.ssssPassphraseEnterEdittext.setText(it.passphrase ?: "")
|
||||
}
|
||||
views.ssssPassphraseEnterEdittext.editorActionEvents()
|
||||
.sample(300)
|
||||
.throttleFirst(300)
|
||||
.onEach {
|
||||
if (it.actionId == EditorInfo.IME_ACTION_DONE) {
|
||||
submit()
|
||||
|
|
|
@ -33,6 +33,7 @@ import com.airbnb.mvrx.withState
|
|||
import im.vector.app.R
|
||||
import im.vector.app.core.extensions.hideKeyboard
|
||||
import im.vector.app.core.extensions.registerStartForActivityResult
|
||||
import im.vector.app.core.flow.throttleFirst
|
||||
import im.vector.app.core.platform.VectorBaseFragment
|
||||
import im.vector.app.core.resources.ColorProvider
|
||||
import im.vector.app.core.utils.colorizeMatchingText
|
||||
|
@ -40,7 +41,6 @@ import im.vector.app.core.utils.startImportTextFromFileIntent
|
|||
import im.vector.app.databinding.FragmentBootstrapMigrateBackupBinding
|
||||
import kotlinx.coroutines.flow.launchIn
|
||||
import kotlinx.coroutines.flow.onEach
|
||||
import kotlinx.coroutines.flow.sample
|
||||
import org.matrix.android.sdk.api.extensions.tryOrNull
|
||||
import org.matrix.android.sdk.internal.crypto.keysbackup.util.isValidRecoveryKey
|
||||
import reactivecircus.flowbinding.android.widget.editorActionEvents
|
||||
|
@ -65,7 +65,7 @@ class BootstrapMigrateBackupFragment @Inject constructor(
|
|||
views.bootstrapMigrateEditText.setText(it.passphrase ?: "")
|
||||
}
|
||||
views.bootstrapMigrateEditText.editorActionEvents()
|
||||
.sample(300)
|
||||
.throttleFirst(300)
|
||||
.onEach {
|
||||
if (it.actionId == EditorInfo.IME_ACTION_DONE) {
|
||||
submit()
|
||||
|
|
|
@ -182,10 +182,10 @@ import im.vector.app.features.widgets.WidgetActivity
|
|||
import im.vector.app.features.widgets.WidgetArgs
|
||||
import im.vector.app.features.widgets.WidgetKind
|
||||
import im.vector.app.features.widgets.permissions.RoomWidgetPermissionBottomSheet
|
||||
import kotlinx.coroutines.flow.debounce
|
||||
import kotlinx.coroutines.flow.launchIn
|
||||
import kotlinx.coroutines.flow.map
|
||||
import kotlinx.coroutines.flow.onEach
|
||||
import kotlinx.coroutines.flow.sample
|
||||
import kotlinx.coroutines.launch
|
||||
import kotlinx.parcelize.Parcelize
|
||||
import nl.dionsegijn.konfetti.models.Shape
|
||||
|
@ -1350,7 +1350,7 @@ class RoomDetailFragment @Inject constructor(
|
|||
private fun observerUserTyping() {
|
||||
views.composerLayout.views.composerEditText.textChanges()
|
||||
.skipInitialValue()
|
||||
.sample(300)
|
||||
.debounce(300)
|
||||
.map { it.isNotEmpty() }
|
||||
.onEach {
|
||||
Timber.d("Typing: User is typing: $it")
|
||||
|
|
|
@ -32,6 +32,7 @@ import com.airbnb.mvrx.withState
|
|||
import im.vector.app.R
|
||||
import im.vector.app.core.extensions.cleanup
|
||||
import im.vector.app.core.extensions.configureWith
|
||||
import im.vector.app.core.flow.throttleFirst
|
||||
import im.vector.app.core.platform.VectorBaseFragment
|
||||
import im.vector.app.databinding.FragmentSpacePreviewBinding
|
||||
import im.vector.app.features.home.AvatarRenderer
|
||||
|
@ -39,7 +40,6 @@ import im.vector.app.features.spaces.SpacePreviewSharedAction
|
|||
import im.vector.app.features.spaces.SpacePreviewSharedActionViewModel
|
||||
import kotlinx.coroutines.flow.launchIn
|
||||
import kotlinx.coroutines.flow.onEach
|
||||
import kotlinx.coroutines.flow.sample
|
||||
import kotlinx.parcelize.Parcelize
|
||||
import org.matrix.android.sdk.api.util.MatrixItem
|
||||
import reactivecircus.flowbinding.appcompat.navigationClicks
|
||||
|
@ -76,7 +76,7 @@ class SpacePreviewFragment @Inject constructor(
|
|||
|
||||
views.roomPreviewNoPreviewToolbar
|
||||
.navigationClicks()
|
||||
.sample(300)
|
||||
.throttleFirst(300)
|
||||
.onEach { sharedActionViewModel.post(SpacePreviewSharedAction.DismissAction) }
|
||||
.launchIn(viewLifecycleOwner.lifecycleScope)
|
||||
|
||||
|
|
Loading…
Reference in a new issue