使用Lottie自定义UIRefreshControl

时间:2018-11-02 17:19:21

标签: ios swift uicollectionview uirefreshcontrol lottie

我的目标是用Lottie动画替换UIRefreshControl的默认微调器。

我的问题是,当我下拉子视图为UICollectionView的{​​{1}}时,动画无法立即播放。仅当我稍微向下滚动并暂停手指时,动画才会播放。当我再次开始移动滚动位置时,它立即返回到其初始播放状态,不再播放。

任何指导将不胜感激,以下是相关代码。

UIRefreshControl

1 个答案:

答案 0 :(得分:1)

滚动时看不到动画的播放,因为每次调用scrollViewDidScroll时,您都会通过调用play重新启动动画。并且由于在滚动时几乎连续调用该函数,因此动画没有机会播放比其第一帧更多的内容。所以它看起来暂停了。

实施自定义刷新控件时,您必须实现3个阶段:

1。用户滚动,但尚未触发刷新

在此阶段,您可能希望根据用户滚动的距离来显示动画的进度。为此,您需要在scrollViewDidScroll中计算进度,并将其传递给LOTAnimationView的{​​{1}}属性。

要计算此进度,您必须知道用户必须向下滚动多远才能触发刷新。以我的经验,这种情况发生在animationProgress大约contentOffset.y处。

2。刷新已触发

当用户向下滚动足够多时,将触发150 ControlEvent。发生这种情况时,您可以通过在.valueChanged

上调用play()来启动循环动画

3。刷新完成

刷新完成后,您可以在自定义刷新控件上调用LOTAnimationView。发生这种情况时,您可以通过在endRefreshing()

上调用stop()来停止动画

查看我在一个项目中使用的LottieRefreshControl的小示例:

LOTAnimationView

现在,您只需要在import UIKit import Lottie class LottieRefreshControl: UIRefreshControl { fileprivate let animationView = LOTAnimationView(name: "refresh") fileprivate var isAnimating = false fileprivate let maxPullDistance: CGFloat = 150 override init() { super.init(frame: .zero) setupView() setupLayout() } required init?(coder aDecoder: NSCoder) { fatalError("init(coder:) has not been implemented") } func updateProgress(with offsetY: CGFloat) { guard !isAnimating else { return } let progress = min(abs(offsetY / maxPullDistance), 1) animationView.animationProgress = progress } override func beginRefreshing() { super.beginRefreshing() isAnimating = true animationView.animationProgress = 0 animationView.play() } override func endRefreshing() { super.endRefreshing() animationView.stop() isAnimating = false } } private extension LottieRefreshControl { func setupView() { // hide default indicator view tintColor = .clear animationView.loopAnimation = true addSubview(animationView) addTarget(self, action: #selector(beginRefreshing), for: .valueChanged) } func setupLayout() { animationView.translatesAutoresizingMaskIntoConstraints = false NSLayoutConstraint.activate([ animationView.centerXAnchor.constraint(equalTo: centerXAnchor), animationView.centerYAnchor.constraint(equalTo: centerYAnchor), animationView.widthAnchor.constraint(equalToConstant: 50), animationView.heightAnchor.constraint(equalToConstant: 32) ]) } } 的刷新控件上调用updateProgress

scrollViewDidScroll