Flow
- replay 设置为 BufferOverflow.DROP_LATEST 时 , replay 必须大于 0,replay 为0 时 ,必须为suspend,BufferOverflow.DROP_LATEST 会crash
- StateFlow 具备自动去重功能 , ShareFlow 不具备去重功能
- replay 必须大于0 时候 , tryEmit 才会有效果
- 任何场景下 onCompletion 均会调用 ,无论是 throw 还是 cancel , 都会调用, catch 只会catch 自定义的异常
LinearSmoothScroller
private fun RecyclerView.smoothScrollToPositionWithOffset(position: Int, offset: Int, millisecondsPerInch: Float = 0f, snapPreference: Int = SNAP_TO_START) {
val itemCount = adapter?.itemCount ?: -1
if (position < 0 || position >= itemCount) {
return
}
val linearSmoothScroller = object : LinearSmoothScroller(context) {
override fun onTargetFound(targetView: View, state: RecyclerView.State, action: Action) {
super.onTargetFound(targetView, state, action)
val dx = calculateDxToMakeVisible(targetView, snapPreference)
val dy = calculateDyToMakeVisible(targetView, snapPreference)
val distance = sqrt((dx * dx + dy * dy).toDouble()).toInt()
val time = calculateTimeForDeceleration(distance)
if (time > 0) {
action.update(-dx - offset, -dy - offset, time, mDecelerateInterpolator)
}
}
override fun calculateSpeedPerPixel(displayMetrics: DisplayMetrics): Float {
return if (millisecondsPerInch > 0) {
millisecondsPerInch / displayMetrics.densityDpi
} else {
super.calculateSpeedPerPixel(displayMetrics)
}
}
}
linearSmoothScroller.targetPosition = position
layoutManager?.startSmoothScroll(linearSmoothScroller)
}
ViewPager预加载位置计算
var currentState = ViewPager.SCROLL_STATE_IDLE
viewPager.addOnPageChangeListener(object : SimpleOnPageChangeListener() {
override fun onPageScrolled(position: Int, positionOffset: Float, positionOffsetPixels: Int) {
if (currentState == ViewPager.SCROLL_STATE_DRAGGING) {
val scrollX = viewPager.scrollX
val pageStartScrollX = viewPager.currentItem * viewPager.width
if (scrollX < pageStartScrollX) {
viewPager.currentItem - 1
} else if (scrollX > pageStartScrollX) {
viewPager.currentItem + 1
}
}
}
override fun onPageScrollStateChanged(state: Int) {
currentState = state
}
})
viewPager.post {
viewPager.setCurrentItem(4, false)
}