You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何通过Dagger 2使Fragment与宿主Activity保持存活?

实现带底部导航的MainActivity与Fragment的Dagger注入方案

我来分享一下针对这个需求的完整实现方案,完全参考了谷歌蓝图示例里的自定义作用域用法,分模块给你拆解清楚:


1. 先定义自定义作用域注解

首先我们需要实现@ActivityScoped和@FragmentScoped这两个自定义作用域,用来限定依赖的生命周期与对应组件保持一致:

import javax.inject.Scope

/**
 * 限定依赖生命周期与Activity一致
 */
@Scope
@MustBeDocumented
@Retention(value = AnnotationRetention.RUNTIME)
annotation class ActivityScoped

/**
 * 限定依赖生命周期与Fragment一致
 */
@Scope
@MustBeDocumented
@Retention(value = AnnotationRetention.RUNTIME)
annotation class FragmentScoped

2. MainActivity的Module(@ActivityScoped)

这个Module负责关联MainActivity下的所有Fragment注入器,标注@ActivityScoped确保依赖只在当前Activity生命周期内有效:

import dagger.Module
import dagger.android.ContributesAndroidInjector

@Module
abstract class MainActivityModule {

    // 为GalleryFragment自动生成注入子组件,并关联GalleryModule
    @FragmentScoped
    @ContributesAndroidInjector(modules = [GalleryModule::class])
    abstract fun contributeGalleryFragment(): GalleryFragment

    // 为ProfileFragment自动生成注入子组件,这里假设ProfileFragment有对应Module
    @FragmentScoped
    @ContributesAndroidInjector(modules = [ProfileModule::class])
    abstract fun contributeProfileFragment(): ProfileFragment
}

用@ContributesAndroidInjector可以省去手动编写Fragment子组件的代码,是Dagger Android推荐的简化写法。


3. GalleryFragment的Module(@FragmentScoped)

GalleryModule负责提供GalleryFragment所需的所有依赖,标注@FragmentScoped保证每个GalleryFragment实例都拥有独立的依赖实例:

import dagger.Module
import dagger.Provides

@Module
class GalleryModule {

    // 示例:提供GalleryFragment需要的仓库类依赖
    @FragmentScoped
    @Provides
    fun provideGalleryRepository(): GalleryRepository {
        return GalleryRepositoryImpl()
    }
}

在GalleryFragment内部,只需通过@Inject注解即可完成依赖注入:

class GalleryFragment : Fragment() {

    @Inject
    lateinit var galleryRepository: GalleryRepository

    override fun onCreate(savedInstanceState: Bundle?) {
        AndroidInjection.inject(this)
        super.onCreate(savedInstanceState)
        // 此时galleryRepository已完成注入可直接使用
    }

    // Fragment其他业务逻辑...
}

4. AppComponent 根组件定义

最后定义根组件AppComponent,作为整个依赖注入体系的入口,包含全局模块和MainActivity的Module:

import dagger.Component
import dagger.android.AndroidInjector
import dagger.android.support.AndroidSupportInjectionModule
import javax.inject.Singleton

@Singleton
@Component(
    modules = [
        AndroidSupportInjectionModule::class,
        MainActivityModule::class,
        // 其他全局依赖模块...
    ]
)
interface AppComponent : AndroidInjector<MyApplication> {

    @Component.Factory
    interface Factory : AndroidInjector.Factory<MyApplication>
}

在自定义Application类中初始化Dagger:

class MyApplication : DaggerApplication() {
    override fun applicationInjector(): AndroidInjector<out DaggerApplication> {
        return DaggerAppComponent.factory().create(this)
    }
}

底部导航切换Fragment的逻辑

在MainActivity中,通过底部导航的点击事件切换Fragment即可,Dagger会自动完成Fragment的依赖注入:

class MainActivity : AppCompatActivity() {

    override fun onCreate(savedInstanceState: Bundle?) {
        AndroidInjection.inject(this)
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        val bottomNav = findViewById<BottomNavigationView>(R.id.bottom_nav)
        bottomNav.setOnItemSelectedListener { item ->
            when (item.itemId) {
                R.id.nav_gallery -> {
                    supportFragmentManager.beginTransaction()
                        .replace(R.id.fragment_container, GalleryFragment::class.java, null)
                        .commit()
                    true
                }
                R.id.nav_profile -> {
                    supportFragmentManager.beginTransaction()
                        .replace(R.id.fragment_container, ProfileFragment::class.java, null)
                        .commit()
                    true
                }
                else -> false
            }
        }

        // 默认加载GalleryFragment
        if (savedInstanceState == null) {
            bottomNav.selectedItemId = R.id.nav_gallery
        }
    }
}

内容的提问来源于stack exchange,提问作者Boris Rozhkovsky

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.20 08:50:35