DZNEmptyDataSet
DZNEmptyDataSet copied to clipboard
Empty data set view breaks "pull to refresh"
I'm trying to use this handy library in a UITableViewController
which applies the "pull to refresh" pattern and which thus owns a UIRefreshControl
. Unfortunately, this combination causes a number of problems:
-
As long as the empty data set view is visible, the "pull to refresh" gesture is no longer possible even when
emptyDataSetShouldAllowTouch:
returnsNO
. -
The empty data set view seems to hide the
UIRefreshControl
(which can be invoked manually by callingbeginRefreshing
, but it won't become visible as long as the empty data set view is visible). This is also the case when I manually set the background color to transparent (but as far as I can judge from looking at the source code this is the default anyway). -
The offset of the empty data set view is wrong (although this could probably also be fixed by returning a custom offset from the according delegate method).
Is there any way to use this library in conjunction with a UIRefreshControl
? If there is anything I can do to help resolve this issue, just let me know.
Addendum: I'm using the latest version available through CocoaPods (1.4.1).
To be totally honest, I've never tested it out with UIRefreshControl
. I'm not a big fan of that control.
The scrollview it self isn't modified by the library, so UIRefreshControl
should respond normally to it and display the control.
Have you tried using this API?
- (BOOL)emptyDataSetShouldAllowScroll:(UIScrollView *)scrollView {
return YES;
}
Does the UIRefreshControl
at least show up?
That fixes the pull-to-refresh gesture. Oddly enough, the manual invocation of beginRefreshing
still seems to be broken, but that would be acceptable given that the gesture is usable.
However, the empty dataset view now scrolls down during the pull gesture, which is not exactly the desired behaviour. But since offsetForEmptyDataSet:
is not called during scrolling, I guess there is no way around that?
Not currently, no. Sorry. Glad to know that the issue was something related to the scrollview.
Thing is, the empty data set view is nested inside of the scrollView, so it's nearly impossible not to scroll it, if the scroll is enabled.
Actually, the desired sticky behaviour can be achieved as follows:
- (void) scrollViewDidScroll:(UIScrollView *)scrollView {
UIView *v = [scrollView emptyDataSetView];
v.frame = CGRectMake(v.frame.origin.x, scrollView.contentOffset.y, v.frame.size.width, v.frame.size.height);
}
Which also fixes the wrong offset. Only problem with this solution is that there is no way to access the empty dataset view (I just made the accessor public for testing purposes). So unless this is something you might consider incorporating, I guess I will have to fork...
This seems to be a decent solution actually.
Please do fork, and submit a PR exposing the emptyDataSetView
as a readOnly
property. And if you can add a UIRefreshControl
to any of the example projects (Countries, perhaps), that would be great for illustrating this workaround.
Unfortunately release 1.5 has broken my nice workaround, now there is a nasty glitch where the empty dataset view moves down a view pixels and immediately in the correct position again afterwards once the refreshing starts, and I don't know yet why this happens. So the pull request is postponed for the time being...
That's weird. If you could investigate, would be great.
On the meantime, I'll expose the emptyDataSetView
as a readOnly
property.
@leoschweizer Did you fix it?
@allaire No, I figured that simply using the background view of a UITableView
is a much more reliable solution for my use case than working around the design of this library.
Tried UIRefreshControl with
- (BOOL)emptyDataSetShouldAllowScroll:(UIScrollView *)scrollView {
return YES;
}
but it just don't work...
@allaire @rene-dohan Working with a CollectionView I had to implement these two delegates in order to restore the pull-to-refresh gesture (even if the emptyDataSetShouldAllowTouch
is marked as true
by default... Weird but it works.):
func emptyDataSetShouldAllowScroll(_ scrollView: UIScrollView!) -> Bool {
return true
}
func emptyDataSetShouldAllowTouch(_ scrollView: UIScrollView!) -> Bool {
return true
}
Hope it helps.
In case anyone made mistake like me, with the override method above, please make sure you have set self.tableview.emptyDataSetDelegate = self Without this line, refresh control will never show up.
Maybe it'll help someone as a temp solution.
func emptyDataSetShouldAllowScroll(_ scrollView: UIScrollView!) -> Bool {
return true
}
func scrollViewDidScroll(_ scrollView: UIScrollView) {
guard let view = scrollView.value(forKey: "emptyDataSetView") as? UIView else {return}
view.frame = CGRect(x: view.frame.origin.x, y: scrollView.contentOffset.y, width: view.bounds.width, height: view.bounds.height)
}