AlertDialog上下文依赖注入问题

问题描述

我的应用程序是用Kotlin编写的,并且我正在使用Koin进行注射。

我有一个用于显示对话框的类,该类需要传递上下文。

文件如下:

class SettingsDialogHelper(val resources: Resources,val context: Context) {
    private var settingsAboutDialog: AlertDialog? = null
    private var settingsPrivacyPolicyDialog: AlertDialog? = null

    fun showSettingsAboutDialog() {
        settingsAboutDialog = AlertDialog.Builder(context,R.style.Theme_MaterialComponents_Light_Dialog)
            .setTitle(resources.getString(R.string.about_dialog_title,resources.getString(R.string.app_name)))
            .setMessage(
                resources.getString(
                    R.string.about_dialog_message,resources.getString(R.string.app_name),resources.getString(R.string.company_name))
            )
            .setPositiveButton(R.string.ok,null)
            .show()
    }

    fun isSettingsAboutDialogVisible(): Boolean = settingsAboutDialog?.isShowing == true
}

我的模块文件如下:

val appModule = module {

    single<Resources> { androidContext().resources }

    single { SettingsDialogHelper(get(),androidContext()) }
}

最后,在MainActivity中,我这样注入:

private val settingsDialogHelper: SettingsDialogHelper by inject()

当我的代码调用显示对话框时,发生以下崩溃:

I: |    +-- 'android.content.res.Resources'
I: |    +-- 'android.content.Context'
I: \-- (*) Created
D: Shutting down VM

    android.view.WindowManager$BadTokenException: Unable to add window -- token null is not valid; is your activity running?
        at android.view.ViewRootImpl.setView(ViewRootImpl.java:1041)
        at android.view.WindowManagerGlobal.addView(WindowManagerGlobal.java:397)
        at android.view.WindowManagerImpl.addView(WindowManagerImpl.java:108)
        at android.app.Dialog.show(Dialog.java:340)
        at androidx.appcompat.app.AlertDialog$Builder.show(AlertDialog.java:1008)
        at com.myapp.apps.blog.main.ui.SettingsDialogHelper.showSettingsAboutDialog(SettingsDialogHelper.kt:23)
        at com.myapp.apps.blog.main.ui.MainActivity.onoptionsItemSelected(MainActivity.kt:44)

我认为问题与AlertDialog.Builder通常需要活动而不是上下文有关,并且我不想生活在我的片段中,但还不太清楚如何解决此问题

非常感谢您的帮助

解决方法

您需要使用koin注入参数。

在koin模块中,您的定义应如下所示:

single { activityContext -> SettingsDialogHelper(get(),activityContext }

然后在注入类中,在运行时传递参数。在您的情况下,可以在MainActivity中注入:

private val settingsDialogHelper: SettingsDialogHelper by inject { parametersOf(this) }

您可以在koin documentation

中找到更多详细信息。

相关问答

Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其...
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。...
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbc...