当前位置: 首页 > 知识库问答 >
问题:

即使使用removeObserver也永远调用Livedata observer

万铭
2023-03-14

我正面临一个让我发疯的问题。

我尝试在onDestroyView()中删除观察者,它可以工作,观察者被删除,但是一旦片段再次进入onActivityCreated()中,并且我观察到livedata,观察者就会立即被触发...我总是使用“ViewLifecyCleOwner”作为所有者。

如果我返回实例化片段,是否有任何方法可以取消liveData的执行?

我所有的frag都扩展了ScopeFragment:

abstract class ScopedFragment : Fragment(), CoroutineScope {
    private lateinit var job: Job

    override val coroutineContext: CoroutineContext
        get() = job + Dispatchers.Main

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        job = Job()
    }

    override fun onDestroy() {
        super.onDestroy()
        job.cancel()
    }
}
class MyLiveDatas {
    private val _myLiveData = MutableLiveData<CustomType>()
    val myLiveData: LiveData<CustomType>
        get() = _myLiveData


    fun customTrigger(webSocketMessage: WebSocketMessage) {
        val createdCustomType = CreatedCustomType(webSocketMessage)
        _myLiveData.post(createdCustomType)
    }
}

class MyFragment: ScopedFragment(), KodeinAware {

    override val kodein by closestKodein()
    private val myLiveData: MyLiveDatas by instance()

    private val myLiveDataObserver = Observer<CustomType> { customType ->
        ... my actions
    }

    override fun onActivityCreated(savedInstanceState: Bundle?) {
        super.onActivityCreated(savedInstanceState)

        myLiveDatas.myLiveData.observe(viewLifecycleOwner, myLiveDataObserver)
    }


    override fun onDestroyView() {
        super.onDestroyView()

        myLiveDatas.myLiveData.removeObserver(myLiveDataObserver)

        // I've also try removeObservers with viewLifecycleOwner
    }
}

多谢!

共有1个答案

那博瀚
2023-03-14

如果需要单个事件,则需要使用自定义实时数据

这是我的一个项目中的自定义可变实时数据,它正在工作

class SingleLiveEvent<T> : MediatorLiveData<T>() {

    private val observers = ArraySet<ObserverWrapper<in T>>()

    @MainThread
    override fun observe(owner: LifecycleOwner, observer: Observer<in T>) {
        val wrapper = ObserverWrapper(observer)
        observers.add(wrapper)
        super.observe(owner, wrapper)
    }

    @MainThread
    override fun removeObserver(observer: Observer<in T>) {
        if (observers.remove(observer)) {
            super.removeObserver(observer)
            return
        }
        val iterator = observers.iterator()
        while (iterator.hasNext()) {
            val wrapper = iterator.next()
            if (wrapper.observer == observer) {
                iterator.remove()
                super.removeObserver(wrapper)
                break
            }
        }
    }

    @MainThread
    override fun setValue(t: T?) {
        observers.forEach { it.newValue() }
        super.setValue(t)
    }

    private class ObserverWrapper<T>(val observer: Observer<T>) : Observer<T> {

        private var pending = false

        override fun onChanged(t: T?) {
            if (pending) {
                pending = false
                observer.onChanged(t)
            }
        }

        fun newValue() {
            pending = true
        }
    }
}
 类似资料:
  • 问题内容: 我有一些关于永久使用Node.js的问题,可能很琐碎。根据我的阅读,永远可以通过编程使用,并且它维护了一个列表,其中包含所有永远使用的脚本。该进程终止后,它会自动产生一个新的进程,直到停止为止。 但是,我的问题是,如何永远做到这一点?是否还会添加这些脚本以在启动时启动? 问题答案: 您可以像这样永久性地使用程序: 在node.js脚本中使用Forever实例: 您应该花一点时间阅读一下

  • 有什么让我怀念的吗?如果我必须手动关闭连接,是不是至少可以从Javers那里收到一个不再需要连接的通知?

  • 问题内容: 看过很多论坛,但没有找到答案…简单的东西,用@PostLoad注释的方法永远不会被调用…通过@EntityListeners添加了侦听器,但问题仍然存在。我正在使用基于SessionFactory的配置。 问题答案: 当使用基于基础的配置时,EJB3 注释不起作用,后期加载方法将永远不会被调用。 使用Hibernate的Interceptor或事件或基于基本的配置。

  • 欧拉项目的问题#3是: 13195的质因数是5、7、13、29。 600851475143的最大质因数是什么? 我的解决方案需要很长时间。我认为我得到了正确的实施;然而,当使用大数字进行测试时,我无法看到结果。它永远运行。我想知道我的算法是否有问题:

  • 所以我在做一些应该很简单的事情,但显然不是在Spark SQL中。 null 表有外键字段,但数据库中没有定义显式fk关系。我在用Innodb。 Spark中的执行计划: 计划: ==物理计划==TungstenProject[Address_ID#0L]