I am using this tutorial to implement a pull-to-refresh behavior with the RefreshControl
. I am using a Navigation Bar
. When using normal titles eve
The only working solution for me is combining Bruno's suggestion with this line of code:
tableView.contentInsetAdjustmentBehavior = .always
I had this issue too, and i fixed it by embedded my scrollView (or tableView \ collectionView) inside stackView, and it's important that this stackView's top constraint will not be attached to the safeArea view (all the other constraints can). the top constraint should be connect to it's superview or to other view.
It seems there are a lot of different causes that could make this happen, for me I had a TableView embedded within a ViewController. I set the top layout guide of the tableview to the superview with 0. After all of that still nothing until I wrapped my RefreshControl end editing in a delayed block:
DispatchQueue.main.async {
if self.refreshControl.isRefreshing {
DispatchQueue.main.asyncAfter(deadline: .now() + 1.0, execute: {
self.refreshControl.endRefreshing()
})
}
}
If you were using tableView.tableHeaderView = refreshControl
or tableView.addSubView(refreshControl)
you should try using tableView.refreshControl = refreshControl
I was facing the same issue for very long, the only working solution for me was adding refresh control to the background view of tableview.
tableView.backgroundView = refreshControl
I fixed this by delaying calling to API until my collection view ends decelerating
I notice that the issue happens when refresh control ends refreshing while the collection view is still moving up to its original position. Therefore, I delay making API call until my collection view stops moving a.k.a ends decelerating. Here's a step by step:
navigationBar.isTranslucent = false
), then you will have to set extendedLayoutIncludesOpaqueBars = true
on your view controller. Otherwise, skip this.RxSwift
, here's how I do it.collectionView.rx.didEndDecelerating
.map { [unowned self] _ in self.refreshControl.isRefreshing }
.filter { $0 == true }
.subscribe(onNext: { _ in
// make api call
})
.disposed(by: disposeBag)
refreshControl.endRefreshing()
Do note that since we delay API call, it means that this whole pull-to-refresh process is not as quick as it could have been done without the delay.