Kotlin:调用函数以更新广播的UI



我是Kotlin的新手,看起来很棒!尽管今天,我一直在尝试做一些非常简单的事情,但是我完全卡住了。

我正在使用广播接收器来确定设备何时连接/断开电源。我需要做的一切都相应地更新我的UI。


我的代码

这是我的BroadcastReceiver课程,它似乎可以正常工作。

class PlugInReceiver : BroadcastReceiver() {
    override fun onReceive(context: Context, intent: Intent) {
        val action = intent.action
        if (action == Intent.ACTION_POWER_CONNECTED) {
            // Do stuff when power connected
        } 
        else if (action == Intent.ACTION_POWER_DISCONNECTED) {
            // Do more stuff when power disconnected
        }
    }
}

现在在我的MainActivity中(但是在其他地方,以后),我想在触发意图时更新我的UI,例如在下面的功能中,背景颜色会更改。

private fun updateBackgroundColor( newBgColorId: Int = R.color.colorAccent){
    val mainLayout = findViewById<View>(R.id.mainLayout)
    val colorFade = ObjectAnimator.ofObject(
            mainLayout, "backgroundColor", ArgbEvaluator(), oldBgColor, newBgColor)
    colorFade.start()
}

问题

如何在MainActivity上调用功能,或在BroadcastReceiver启动事件时更新我的UI?


我到目前为止尝试过的

  • 我考虑在某个地方设有一个静态变量,存储了广播公司的结果,然后在我的UI类中可观察到的一个可观察的变量,相应地观看和调用适当的功能。尽管在谷歌搜索如何做到这一点之后,这似乎不是Kotlin的好方法。

  • 考虑试图在UI线程上运行广播员,但这听起来像是一个可怕的主意。

  • 尝试将Java实现与我的Kotlin类混合,但无法正常工作。

令人沮丧的是,我在So上发现了几个非常相似的问题。但是,他们的实现似乎都使用了Java特定功能:

  • Android Broadcastreceiver OnReceive更新文本视图
  • 如何在广播中更新UI
  • 在Android中调用Broadcastreceiver的活动方法
  • 如何在屏幕截图之后从Broadcastreceiver更新UI

我敢肯定,对于大多数Android开发人员来说,这是一个琐碎的问题,但是我迷路了!让我知道您是否需要更多细节。非常感谢!

共享在Kotlin中注册Broadcastreceiver的信息

步骤1.在MainActivity.kt

中创建Broadcastreceiver
private val mPlugInReceiver = object : BroadcastReceiver() {
    override fun onReceive(context: Context?, intent: Intent?) {
        when (intent?.action) {
            Intent.ACTION_POWER_CONNECTED -> {
                //update your main background color
                updateBackgroundColor()
            }
            Intent.ACTION_POWER_DISCONNECTED -> {
                //update your main background color
                updateBackgroundColor()
            }
        }
    }
}

步骤2.创建IntentFilter

private fun getIntentFilter(): IntentFilter {
    val iFilter = IntentFilter()
    iFilter.addAction(Intent.ACTION_POWER_CONNECTED)
    iFilter.addAction(Intent.ACTION_POWER_DISCONNECTED)
    return iFilter
}

步骤3.在onstart()

上注册接收器
override fun onStart() {
    super.onStart()
    registerReceiver(mPlugInReceiver, getIntentFilter())
}

步骤4.在onstop()

上取消注册接收器
override fun onStop() {
    super.onStop()
    unregisterReceiver(mPlugInReceiver)
}

如果您有自定义的广播员,则可以使用LocalBroadcastManager注册并创建本地IntentFilter

private val mLocalBroadcastReceiver = object : BroadcastReceiver() {
    override fun onReceive(context: Context?, intent: Intent?) {
        when (intent?.action) {
            AnyService.UPDATE_ANY -> {
            }
        }
    }
}
private fun getLocalIntentFilter(): IntentFilter {
    val iFilter = IntentFilter()
    iFilter.addAction(AnyService.UPDATE_ANY)
    return iFilter
}

注册本地接收器 LocalBroadcastManager.getInstance(applicationContext).registerReceiver(mLocalBroadcastReceiver, getLocalIntentFilter())

取消注册本地接收器LocalBroadcastManager.getInstance(applicationContext).unregisterReceiver(mLocalBroadcastReceiver)

实现这一目标的最佳方法是在广播中创建一个抽象方法,当调用onReceive()方法时,您可以调用您的活动将实现的方法。/p>

broadcastreceiver示例:

abstract class ConnectionBroadcastReceiver : BroadcastReceiver() {
override fun onReceive(context: Context, intent: Intent) {
     //Do the checks or whatever you want
     var isConnected = true
    broadcastResult(isConnected)
}
protected abstract fun broadcastResult(connected: Boolean)

}

和您的活动中的代码(例如,在ongreate或onstart中)。在这里,您可以使用方法实现注册广播接收器,在这里您可以更新UI:

    var connectionBroadcastReceiver = object : ConnectionBroadcastReceiver() {
        override fun broadcastResult(connected: Boolean) {
            if(isConnected){
                refreshList()
            }
        }
    }
    val intentFilter = IntentFilter()
    intentFilter.addAction(ConnectivityManager.CONNECTIVITY_ACTION)
    this.registerReceiver(connectionBroadcastReceiver, intentFilter)

不要忘记在(Onpause || OnStop || OnDestroy)中取消接收器,但这不是严格必要的。

主线程在主线程上运行。您可以在OnStart()中注册您的活动,并在OnStop()中将其注册,该活动将保证在接收事件时存在UI。

最新更新