我是靠谱客的博主 迷路羽毛,最近开发中收集的这篇文章主要介绍Kotlin StateFlow&SharedFlow(二),觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

StateFlow

hold flow, 没有消费者进行消费的时候,生产者也可以生产数据(生产者在没有消费者订阅之前生产数据可能会丢失数据)。

class MainViewModel : ViewModel() {

    private val _stateFlow = MutableStateFlow(0)

    val stateFlow = _stateFlow.asStateFlow()

    fun incrementCounter() {
        _stateFlow.value += 1
    }

}

In Compose:

class MainActivity : ComponentActivity() {
    
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            FlowDemoTheme {
                //val viewModel = ViewModelProvider(this).get(MainViewModel::class.java)
                val viewModel = viewModel<MainViewModel>()
                val count = viewModel.stateFlow.collectAsState(initial = 10)
                Box(modifier = Modifier.fillMaxSize()) {
                    Button(onClick = { viewModel.incrementCounter() }) {
                        Text(text = "Counter: ${count.value}")
                    }
                }
            }
        }
    }
    
}

In Xml:

class MainActivity : ComponentActivity() {

    private val viewModel: MainViewModel by viewModels()

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        /*lifecycleScope.launch {
            repeatOnLifecycle(Lifecycle.State.STARTED) {
                viewModel.stateFlow.collectLatest { number ->
                    binding.tvCounter.text = number.toString()
                }
            }
        }*/
        collectLatestLifecycleFlow(viewModel.stateFlow) { number ->
            binding.tvCounter.text = number.toString()
        }
    }
    
}

fun <T> ComponentActivity.collectLatestLifecycleFlow(
    flow: Flow<T>, collect: suspend (T) -> Unit) {
    lifecycleScope.launch {
        repeatOnLifecycle(Lifecycle.State.STARTED) {
            flow.collectLatest(collect)
        }
    }
}

SharedFlow

It is used to send one-time events

class MainViewModel : ViewModel() {
    
	private val _sharedFlow = MutableSharedFlow<Int>()

    val sharedFlow = _sharedFlow.asSharedFlow()

    fun squareNumber(number: Int) {
        viewModelScope.launch {
            _sharedFlow.emit(number * number)
        }
    }

    init {
        println("FLOW: STARTED")
        viewModelScope.launch {
            sharedFlow.collect {
                delay(2000L)
                println("FIRST FLOW: The received number is $it")
            }
        }
        viewModelScope.launch {
            sharedFlow.collect {
                delay(3000L)
                println("SECOND FLOW: The received number is $it")
            }
        }
        // 由于SharedFlow是热流,必须是在声明collector之后调用,否则会丢失数据
        squareNumber(3)
    }
}

在这里插入图片描述

Use cache to cache the emitted data:

class MainViewModel : ViewModel() {
    
	private val _sharedFlowCached = MutableSharedFlow<Int>(replay = 5)

    val sharedFlowCached = _sharedFlowCached.asSharedFlow()
    
    fun squareNumberCached(number: Int) {
        viewModelScope.launch {
            _sharedFlowCached.emit(number * number)
            _sharedFlowCached.emit(number + number)
        }
    }

    init {
        squareNumberCached(3)
        println("FLOW: STARTED")
        viewModelScope.launch {
            sharedFlowCached.collect {
                delay(1000L)
                println("FIRST FLOW: The received number is $it")
            }
        }
        viewModelScope.launch {
            sharedFlowCached.collect {
                delay(3000L)
                println("SECOND FLOW: The received number is $it")
            }
        }
    }

}

在这里插入图片描述

How to use shared flow in Activity?

In Compose:

class MainActivity : ComponentActivity() {

    private val viewModel: MainViewModel by viewModels()

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContent {
            FlowDemoTheme {
                LaunchedEffect(key1 = true) {
                    viewModel.sharedFlow.collect { number ->

                    }
                }
                ...
            }
        }
    }
}

In Xml:

fun <T> ComponentActivity.collectLifecycleFlow(
    flow: Flow<T>, collect: suspend (T) -> Unit) {
    lifecycleScope.launch {
        repeatOnLifecycle(Lifecycle.State.STARTED) {
            flow.collect(collect)
        }
    }
}

StateFlow vs SharedFlow

State flow is used to keep state to keep values that you also want to re-emit on screen.

Shared flow is used to for one-time events that you don’t want to hide the keyboard again.

最后

以上就是迷路羽毛为你收集整理的Kotlin StateFlow&SharedFlow(二)的全部内容,希望文章能够帮你解决Kotlin StateFlow&SharedFlow(二)所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(45)

评论列表共有 0 条评论

立即
投稿
返回
顶部