android - 使用 dispose 处理程序 rxjava 创建 Observable
问题描述
我们想观察视图大小的变化,我们创建了一个这样的扩展:
fun View.layoutSizeObservable(): io.reactivex.Observable<Size> {
return io.reactivex.Observable.create<Size> { emitter ->
viewTreeObserver.addOnGlobalLayoutListener {
Log.d("MainFragment", "ViewTreeObserver Listener called back.")
if (measuredWidth > 0 && measuredHeight > 0) {
emitter.onNext(Size(measuredWidth, measuredHeight))
}
}
}
}
然后我们像这样使用它,它在功能上运行良好:
sizeChangedDisposable = titleTextView.layoutSizeObservable().subscribe { size: Size ->
Log.d("MainFragment", "Size changed subscribe on $size")
}
但是,与我们不完全一样的一件事是Listener
通过添加addOnGlobalLayoutListener
,但从未删除。
我们可以调用sizeChangedDisposable.dispose()
which 将正确停止订阅:
D/MainFragment:大小更改订阅 $size
但这将继续被调用:
D/MainFragment:ViewTreeObserver 监听器回调。
我们如何以及在哪里删除布局侦听器回调?
解决方案
您需要在Disposable
处置时删除侦听器。为了能够做到这一点,Cancellable
请为发射器设置一个动作来移除听者。
例子
fun View.layoutSizeObservable(): io.reactivex.Observable<Size> {
return io.reactivex.Observable.create<Size> { emitter ->
val listener = ViewTreeObserver.OnGlobalLayoutListener {
Log.d("MainFragment", "ViewTreeObserver Listener called back.")
if (measuredWidth > 0 && measuredHeight > 0) {
emitter.onNext(Size(measuredWidth, measuredHeight))
}
}
viewTreeObserver.addOnGlobalLayoutListener(listener)
emitter.setCancellable {
Log.d("MainFragment", "ViewTreeObserver Listener removed.")
viewTreeObserver.removeOnGlobalLayoutListener(listener)
}
}
}
推荐阅读
- sql - 需要基于某些条件的sql查询
- amazon-sns - 使用 AWS SNS 发送的 SMS 失败
- .net-core - 如何使用 xunit 和 moq 传递我的 DbContext 对象进行测试
- razorpay - Razorpay 直接从服务器端创建和应用付款,无需前端
- r - 如何用需要满足条件的随机值填充矩阵?
- c - shellcode中的地址在执行过程中发生变化
- hibernate - Hibernate 为 ManyToMany 关系保留重复项
- python - Python在值的3d数组中查找坐标
- spring-boot - 如何解决这个错误语法错误,在spring boot中插入“Type VariableDeclaratorId”来完成FormalParameterList?
- python - django media url 正确但不显示图片