Skip to content

Commit f05f18e

Browse files
committed
#
1 parent c9902da commit f05f18e

File tree

6 files changed

+113
-87
lines changed

6 files changed

+113
-87
lines changed

README.md

Lines changed: 35 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -5,30 +5,30 @@
55
- 支持生命周期感知
66
- 支持自动清除空闲事件
77

8-
事件(SimpleEventFlow)和状态(MutableStateFlow)
98

10-
- 订阅事件(`Flow<T>.observeEvent`)
11-
- 通过 `Lifecycle.repeatOnLifecycle` 实现
12-
- 订阅后进入 `minState` 状态开始接收处理事件, 脱离 `minState` 状态停止接收处理事件
13-
- 通常配合 `SimpleEventFlow` 使用
14-
- 订阅状态(`Flow<T>.observeState`)
15-
- 通过 `Lifecycle.whenStateAtLeast` 实现
16-
- 订阅后开始接收事件,但不会立刻处理,进入 `minState` 状态后处理最新的一个事件
17-
- 通常配合 `MutableStateFlow` 使用
9+
## 观察
1810

11+
```kotlin
1912

20-
有时,在A页订阅事件`SimpleEventFlow`,然后进入B页发送了事件,但想回到A页时再处理,可用 `observeState`
21-
22-
## Gradle
23-
24-
``` groovy
25-
repositories {
26-
maven { url "https://gitee.com/ezy/repo/raw/cosmo/"}
27-
}
28-
dependencies {
29-
implementation "me.reezy.cosmo:flowbus:0.8.0"
30-
}
13+
/**
14+
* 观察流,进入 [minState] 时开始,脱离 [minState] 时停止
15+
*
16+
* - 对于 [StateFlow],每次进入 [minState] 都会观察一次当前值
17+
* - 对于 [EventFlow],只能收到进入 [minState] 后发射的值
18+
* */
19+
fun <T> Flow<T>.observe(owner: LifecycleOwner, minState: Lifecycle.State = Lifecycle.State.STARTED, action: suspend (T) -> Unit)
20+
21+
/**
22+
* 观察流,脱离 [minState] 后会保存最近产生的值,再次进入 [minState] 时消费
23+
*
24+
* - 对于 [StateFlow],没啥用,效果与 [observe] 没区别
25+
* - 对于 [EventFlow],每次进入 [minState] 时能收到并消费最近产生的值(如果有)
26+
*
27+
* [EventFlow] 场景:在A页订阅事件,然后进入B页发送了事件,但想回到A页时再处理,可用此方法
28+
* */
29+
fun <T> Flow<T>.observeLatest(owner: LifecycleOwner, minState: Lifecycle.State = Lifecycle.State.STARTED, action: suspend (T) -> Unit)
3130
```
31+
3232

3333
## EventBus 使用
3434

@@ -37,18 +37,18 @@ data class FooEvent(val value: String)
3737
data class BarEvent(val value: String)
3838

3939
object Global {
40-
val eventFoo = SimpleEventFlow<FooEvent>()
40+
val eventFoo = EventFlow<FooEvent>()
4141

4242
val stateCount = MutableStateFlow(0)
4343
}
4444

45-
Global.stateCount.observeState(this) {
45+
Global.stateCount.observe(this) {
4646
binding.state.text = "count = $it"
4747
}
48-
Global.eventFoo.observeState(this) {
48+
Global.eventFoo.observeLatest(this) {
4949
log("Global => $it")
5050
}
51-
EventBus.observeEvent<BarEvent>(this) {
51+
EventBus.observe<BarEvent>(this) {
5252
log("EventBus => $it")
5353
}
5454

@@ -61,6 +61,17 @@ binding.barEvent.setOnClickListener {
6161
```
6262

6363

64+
## Gradle
65+
66+
``` groovy
67+
repositories {
68+
maven { url "https://gitee.com/ezy/repo/raw/cosmo/"}
69+
}
70+
dependencies {
71+
implementation "me.reezy.cosmo:flowbus:0.8.0"
72+
}
73+
```
74+
6475
## LICENSE
6576

6677
The Component is open-sourced software licensed under the [Apache license](LICENSE).
Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,17 +1,15 @@
11
package com.demo.app
22

3-
import kotlinx.coroutines.channels.BufferOverflow
4-
import kotlinx.coroutines.flow.MutableSharedFlow
53
import kotlinx.coroutines.flow.MutableStateFlow
6-
import me.reezy.cosmo.flowbus.SimpleEventFlow
4+
import me.reezy.cosmo.flowbus.EventFlow
75

86
object Global {
97

10-
val eventFloat = SimpleEventFlow<Float>()
8+
val eventFloat = EventFlow<Float>()
119

12-
val eventString = SimpleEventFlow<String>()
10+
val eventString = EventFlow<String>()
1311

14-
val eventFoo = SimpleEventFlow<FooEvent>()
12+
val eventFoo = EventFlow<FooEvent>()
1513

1614
val stateCount = MutableStateFlow(0)
1715
}

app/src/main/java/com/demo/app/MainActivity.kt

Lines changed: 12 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -5,11 +5,11 @@ import android.os.Bundle
55
import android.util.Log
66
import android.view.ViewGroup
77
import androidx.appcompat.app.AppCompatActivity
8+
import androidx.lifecycle.Lifecycle
89
import com.demo.app.databinding.ActivityMainBinding
9-
import kotlinx.coroutines.flow.collect
1010
import me.reezy.cosmo.flowbus.EventBus
11-
import me.reezy.cosmo.flowbus.observeEvent
12-
import me.reezy.cosmo.flowbus.observeState
11+
import me.reezy.cosmo.flowbus.observe
12+
import me.reezy.cosmo.flowbus.observeLatest
1313
import kotlin.random.Random
1414

1515
class MainActivity : AppCompatActivity() {
@@ -20,33 +20,34 @@ class MainActivity : AppCompatActivity() {
2020
super.onCreate(savedInstanceState)
2121
setContentView(R.layout.activity_main)
2222

23+
Global.stateCount.value = 3
2324

24-
Global.stateCount.observeState(this) {
25+
Global.stateCount.observe(this, minState = Lifecycle.State.RESUMED) {
2526
binding.state.text = "count = $it"
2627
log("count = $it")
2728
}
2829

29-
Global.eventFoo.observeEvent(this) {
30+
Global.eventFoo.observe(this) {
3031
log("Global foo1 => $it")
3132
}
32-
Global.eventFoo.observeState(this) {
33+
Global.eventFoo.observeLatest(this) {
3334
log("Global foo2 sticky => $it")
3435
}
35-
Global.eventFloat.observeEvent(this) {
36+
Global.eventFloat.observe(this) {
3637
log("Global float event => $it")
3738
}
38-
Global.eventString.observeEvent(this) {
39+
Global.eventString.observe(this) {
3940
log("Global => $it")
4041
}
4142

4243

43-
EventBus.observeState<BarEvent>(this) {
44+
EventBus.observe<BarEvent>(this) {
4445
log("EventBus => $it")
4546
}
46-
EventBus.observeState<Float>(this) {
47+
EventBus.observe<Float>(this) {
4748
log("EventBus => $it")
4849
}
49-
EventBus.observeState<String>(this) {
50+
EventBus.observe<String>(this) {
5051
log("EventBus => $it")
5152
}
5253

app/src/main/java/com/demo/app/SecondActivity.kt

Lines changed: 9 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -7,8 +7,8 @@ import android.view.ViewGroup
77
import androidx.appcompat.app.AppCompatActivity
88
import com.demo.app.databinding.ActivityMainBinding
99
import me.reezy.cosmo.flowbus.EventBus
10-
import me.reezy.cosmo.flowbus.observeEvent
11-
import me.reezy.cosmo.flowbus.observeState
10+
import me.reezy.cosmo.flowbus.observe
11+
import me.reezy.cosmo.flowbus.observeLatest
1212
import kotlin.random.Random
1313

1414
class SecondActivity : AppCompatActivity() {
@@ -21,29 +21,29 @@ class SecondActivity : AppCompatActivity() {
2121
setContentView(R.layout.activity_main)
2222

2323

24-
Global.stateCount.observeState(this) {
24+
Global.stateCount.observeLatest(this) {
2525
binding.state.text = "count = $it"
2626
log("count = $it")
2727
}
2828

29-
Global.eventFoo.observeEvent(this) {
29+
Global.eventFoo.observe(this) {
3030
log("Global => $it")
3131
}
32-
Global.eventFloat.observeEvent(this) {
32+
Global.eventFloat.observe(this) {
3333
log("Global float event => $it")
3434
}
35-
Global.eventString.observeEvent(this) {
35+
Global.eventString.observe(this) {
3636
log("Global => $it")
3737
}
3838

3939

40-
EventBus.observeEvent<BarEvent>(this) {
40+
EventBus.observe<BarEvent>(this) {
4141
log("EventBus => $it")
4242
}
43-
EventBus.observeEvent<Float>(this) {
43+
EventBus.observe<Float>(this) {
4444
log("EventBus => $it")
4545
}
46-
EventBus.observeEvent<String>(this) {
46+
EventBus.observe<String>(this) {
4747
log("EventBus => $it")
4848
}
4949

flowbus/src/main/java/me/reezy/cosmo/flowbus/EventBus.kt

Lines changed: 13 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -29,12 +29,12 @@ class EventBus : ViewModel() {
2929
global.emit(T::class.java, "", value)
3030
}
3131

32-
inline fun <reified T> observeEvent(owner: LifecycleOwner, eventName: String = "", minState: Lifecycle.State = Lifecycle.State.STARTED, noinline observer: (T) -> Unit) {
33-
global.observeEvent(T::class.java, owner, eventName, minState, observer)
32+
inline fun <reified T> observe(owner: LifecycleOwner, eventName: String = "", minState: Lifecycle.State = Lifecycle.State.STARTED, noinline observer: (T) -> Unit) {
33+
global.observe(T::class.java, owner, eventName, minState, observer)
3434
}
3535

36-
inline fun <reified T> observeState(owner: LifecycleOwner, eventName: String = "", minState: Lifecycle.State = Lifecycle.State.STARTED, noinline observer: (T) -> Unit) {
37-
global.observeState(T::class.java, owner, eventName, minState, observer)
36+
inline fun <reified T> observeLatest(owner: LifecycleOwner, eventName: String = "", minState: Lifecycle.State = Lifecycle.State.STARTED, noinline observer: (T) -> Unit) {
37+
global.observeLatest(T::class.java, owner, eventName, minState, observer)
3838
}
3939

4040
inline fun <reified T> observeForever(eventName: String = "", noinline observer: (T) -> Unit) {
@@ -56,12 +56,12 @@ class EventBus : ViewModel() {
5656
emit(T::class.java, "", value)
5757
}
5858

59-
inline fun <reified T> observeState(owner: LifecycleOwner, eventName: String = "", minState: Lifecycle.State = Lifecycle.State.STARTED, noinline observer: (T) -> Unit) {
60-
observeState(T::class.java, owner, eventName, minState, observer)
59+
inline fun <reified T> observe(owner: LifecycleOwner, eventName: String = "", minState: Lifecycle.State = Lifecycle.State.STARTED, noinline observer: (T) -> Unit) {
60+
observe(T::class.java, owner, eventName, minState, observer)
6161
}
6262

63-
inline fun <reified T> observeEvent(owner: LifecycleOwner, eventName: String = "", minState: Lifecycle.State = Lifecycle.State.STARTED, noinline observer: (T) -> Unit) {
64-
observeEvent(T::class.java, owner, eventName, minState, observer)
63+
inline fun <reified T> observeLatest(owner: LifecycleOwner, eventName: String = "", minState: Lifecycle.State = Lifecycle.State.STARTED, noinline observer: (T) -> Unit) {
64+
observeLatest(T::class.java, owner, eventName, minState, observer)
6565
}
6666

6767
inline fun <reified T> observeForever(eventName: String = "", noinline observer: (T) -> Unit) {
@@ -76,12 +76,13 @@ class EventBus : ViewModel() {
7676
}
7777
}
7878

79-
fun <T> observeState(eventClazz: Class<T>, owner: LifecycleOwner, eventName: String, minState: Lifecycle.State = Lifecycle.State.STARTED, action: (T) -> Unit) {
80-
get<T>("$eventClazz:$eventName", owner).observeState(owner, minState, action)
79+
80+
fun <T> observe(eventClazz: Class<T>, owner: LifecycleOwner, eventName: String, minState: Lifecycle.State = Lifecycle.State.STARTED, action: (T) -> Unit) {
81+
get<T>("$eventClazz:$eventName", owner).observe(owner, minState, action)
8182
}
8283

83-
fun <T> observeEvent(eventClazz: Class<T>, owner: LifecycleOwner, eventName: String, minState: Lifecycle.State = Lifecycle.State.STARTED, action: (T) -> Unit) {
84-
get<T>("$eventClazz:$eventName", owner).observeEvent(owner, minState, action)
84+
fun <T> observeLatest(eventClazz: Class<T>, owner: LifecycleOwner, eventName: String, minState: Lifecycle.State = Lifecycle.State.STARTED, action: (T) -> Unit) {
85+
get<T>("$eventClazz:$eventName", owner).observeLatest(owner, minState, action)
8586
}
8687

8788
fun <T> observeForever(eventClazz: Class<T>, eventName: String, observer: (T) -> Unit) {
Lines changed: 40 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -1,46 +1,61 @@
11
package me.reezy.cosmo.flowbus
22

3-
import androidx.lifecycle.*
3+
import androidx.lifecycle.Lifecycle
4+
import androidx.lifecycle.LifecycleOwner
5+
import androidx.lifecycle.lifecycleScope
6+
import androidx.lifecycle.repeatOnLifecycle
47
import kotlinx.coroutines.channels.BufferOverflow
58
import kotlinx.coroutines.flow.Flow
69
import kotlinx.coroutines.flow.MutableSharedFlow
10+
import kotlinx.coroutines.flow.StateFlow
711
import kotlinx.coroutines.launch
812

913

1014
@Suppress("NOTHING_TO_INLINE", "FunctionName")
11-
inline fun <T> SimpleEventFlow() = MutableSharedFlow<T>(0, 1, BufferOverflow.DROP_OLDEST)
12-
13-
14-
//fun <T> StateFlow<T>.observeState(owner: LifecycleOwner, minState: Lifecycle.State = Lifecycle.State.STARTED, action: suspend (T) -> Unit) {
15-
// owner.lifecycleScope.launch {
16-
// owner.lifecycle.whenStateAtLeast(minState) {
17-
// collect(action)
18-
// }
19-
// }
20-
//}
21-
22-
23-
fun <T> Flow<T>.observeState(owner: LifecycleOwner, minState: Lifecycle.State = Lifecycle.State.STARTED, action: suspend (T) -> Unit) {
15+
inline fun <T> EventFlow() = MutableSharedFlow<T>(0, 1, BufferOverflow.DROP_OLDEST)
16+
17+
/**
18+
* 观察流,进入 [minState] 时开始,脱离 [minState] 时停止
19+
*
20+
* - 对于 [StateFlow],每次进入 [minState] 都会观察一次当前值
21+
* - 对于 [EventFlow],只能收到进入 [minState] 后发射的值
22+
* */
23+
fun <T> Flow<T>.observe(owner: LifecycleOwner, minState: Lifecycle.State = Lifecycle.State.STARTED, action: suspend (T) -> Unit) {
2424
owner.lifecycleScope.launch {
25-
owner.lifecycle.whenStateAtLeast(minState) {
26-
try {
27-
collect(action)
28-
} catch (ex: Throwable) {
29-
ex.printStackTrace()
30-
}
25+
owner.lifecycle.repeatOnLifecycle(minState) {
26+
collect(action)
3127
}
3228
}
3329
}
3430

35-
fun <T> Flow<T>.observeEvent(owner: LifecycleOwner, minState: Lifecycle.State = Lifecycle.State.STARTED, action: suspend (T) -> Unit) {
31+
/**
32+
* 观察流,脱离 [minState] 后会保存最近产生的值,再次进入 [minState] 时消费
33+
*
34+
* - 对于 [StateFlow],没啥用,效果与 [observe] 没区别
35+
* - 对于 [EventFlow],每次进入 [minState] 时能收到并消费最近产生的值(如果有)
36+
*
37+
* [EventFlow] 场景:在A页观察流,然后进入B页发送了事件,但想回到A页时再处理,可用此方法
38+
* */
39+
fun <T> Flow<T>.observeLatest(owner: LifecycleOwner, minState: Lifecycle.State = Lifecycle.State.STARTED, action: suspend (T) -> Unit) {
40+
var data: T? = null
3641
owner.lifecycleScope.launch {
3742
owner.lifecycle.repeatOnLifecycle(minState) {
38-
try {
39-
collect(action)
40-
} catch (ex: Throwable) {
41-
ex.printStackTrace()
43+
if (data != null) {
44+
action(data!!)
45+
data = null
46+
}
47+
}
48+
}
49+
owner.lifecycleScope.launch {
50+
collect {
51+
if (owner.lifecycle.currentState >= minState) {
52+
data = null
53+
action(it)
54+
} else {
55+
data = it
4256
}
4357
}
4458
}
4559
}
4660

61+

0 commit comments

Comments
 (0)