修改上一个demo, 使用Hilt实现单例对象注入到activity。
新建Application,加上HiltAndroidApp注解:
Kotlin
package com.example.testnavigation
import android.app.Application
import dagger.hilt.android.HiltAndroidApp
@HiltAndroidApp // HiltAndroidApp 注解会自动生成 Hilt 组件,并自动注入依赖
class MyApp : Application() {
override fun onCreate() {
super.onCreate()
}
}
修改EventBus, 使用注解生成单例对象:
Kotlin
package com.example.testnavigation
import dagger.Module
import dagger.Provides
import dagger.hilt.InstallIn
import dagger.hilt.components.SingletonComponent
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.flow.MutableSharedFlow
import kotlinx.coroutines.flow.SharedFlow
import kotlinx.coroutines.launch
import javax.inject.Inject
import javax.inject.Singleton
/**
* SharedFlow 事件总线(单例,全局唯一)
*/
class EventBus @Inject constructor() { // @Inject 让 Hilt 构造
private val _events = MutableSharedFlow<Any>(replay = 0, extraBufferCapacity = 10)
val events: SharedFlow<Any> = _events
private val scope = CoroutineScope(Dispatchers.IO)
/**
* 发送事件
*/
fun post(event: Any) {
scope.launch {
_events.emit(event) // 发射事件
}
}
}
// 提供单例
@Module // 标记为 Hilt 模块, 专门用来提供第三方类、接口、无构造函数类的实例
@InstallIn(SingletonComponent::class) // 把这个模块安装到app整个生命周期。SingletonComponent:整个App全局单例
object AppModule {
@Provides // 提供一个对象实例
@Singleton
fun provideEventBus(): EventBus { // 提供eventBus单例
return EventBus()
}
}
修改MainActivity:
Kotlin
package com.example.testnavigation
import android.content.Intent
import android.os.Bundle
import android.widget.Button
import android.widget.TextView
import androidx.fragment.app.FragmentActivity
import dagger.hilt.android.AndroidEntryPoint
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.flow.filter
import kotlinx.coroutines.flow.launchIn
import kotlinx.coroutines.flow.onEach
import javax.inject.Inject
@AndroidEntryPoint // 注入点,可以被注入对象
class MainActivity : FragmentActivity() {
// 直接注入
@Inject // 直接注入对象
lateinit var eventBus: EventBus
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main1)
findViewById<Button>(R.id.btn_goto_second).setOnClickListener {
startActivity(Intent(this@MainActivity, MainActivity2::class.java))
}
eventBus.events
.filter { it is MessageEvent }
.onEach { event ->
val msg = event as MessageEvent
println("收到消息:${msg.content}")
val tv_msg = findViewById<TextView>(R.id.tv_msg)
tv_msg.text = msg.content
}
.launchIn(CoroutineScope(Dispatchers.Main))
}
}
同样,修改第二个activity:
Kotlin
package com.example.testnavigation
import android.os.Bundle
import android.widget.Button
import androidx.fragment.app.FragmentActivity
import androidx.lifecycle.lifecycleScope
import dagger.hilt.android.AndroidEntryPoint
import kotlinx.coroutines.delay
import kotlinx.coroutines.launch
import javax.inject.Inject
@AndroidEntryPoint
class MainActivity2: FragmentActivity() {
@Inject
lateinit var eventBus: EventBus
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_2)
findViewById<Button>(R.id.btn_send_event).setOnClickListener {
eventBus.post(MessageEvent("肃清万里,总齐八荒。"))
lifecycleScope.launch {
delay(1000)
finish()
}
}
}
}
运行:

点击跳转到第二个activity:

点击发送数据:

ok. 除此以外,viewModel也能注入,略。