简体   繁体   English

在iOS7中使用UICollectionView的UIRefreshControl

[英]UIRefreshControl with UICollectionView in iOS7

In my application I use refresh control with collection view. 在我的应用程序中,我使用刷新控件和集合视图。

UICollectionView *collectionView = [[UICollectionView alloc] initWithFrame:[UIScreen mainScreen].bounds];
collectionView.alwaysBounceVertical = YES;
...
[self.view addSubview:collectionView];

UIRefreshControl *refreshControl = [UIRefreshControl new];
[collectionView addSubview:refreshControl];

iOS7 has some nasty bug that when you pull collection view down and don't release your finger when refreshing begins, vertical contentOffset shifts for 20-30 points down which results in ugly scroll jump. iOS7有一些令人讨厌的错误,当你向下拉集合视图并且在刷新开始时不释放你的手指时,垂直contentOffset向下移动20-30点,这导致丑陋的滚动跳跃。

Tables have this problem too if you use them with refresh control outside of UITableViewController . 如果在UITableViewController之外使用刷新控件,表也有这个问题。 But for them it could be easily solved by assigning your UIRefreshControl instance to UITableView 's private property called _refreshControl : 但是对于它们来说,可以通过将UIRefreshControl实例分配给名为_refreshControl UITableView的私有属性来轻松解决:

@interface UITableView ()
- (void)_setRefreshControl:(UIRefreshControl *)refreshControl;
@end

...

UITableView *tableView = [[UITableView alloc] initWithFrame:[UIScreen mainScreen].bounds];
[self.view addSubview:tableView];

UIRefreshControl *refreshControl = [UIRefreshControl new];
[tableView addSubview:refreshControl];
[tableView _setRefreshControl:refreshControl];

But UICollectionView does not have such property so there must be some way to deal with it manually. 但是UICollectionView没有这样的属性,因此必须有一些方法来手动处理它。

Having the same problem and found a workaround that seems to fix it. 遇到同样的问题,发现似乎可以修复它的解决方法。

This seems to be happening because the UIScrollView is slowing down the tracking of the pan gesture when you pull past the edge of the scrollview. 这似乎正在发生,因为当您拉过滚动视图的边缘时, UIScrollView正在减慢对平移手势的跟踪。 However, UIScrollView is not accounting for changes to contentInset during tracking. 但是, UIScrollView不会在跟踪期间考虑对contentInset的更改。 UIRefreshControl changes contentInset when it activates, and this change is causing the jump. UIRefreshControl在激活时更改contentInset,此更改导致跳转。

Overriding setContentInset on your UICollectionView and accounting for this case seems to help: 覆盖UICollectionView上的setContentInset并解释此案例似乎有助于:

- (void)setContentInset:(UIEdgeInsets)contentInset {
  if (self.tracking) {
    CGFloat diff = contentInset.top - self.contentInset.top;
    CGPoint translation = [self.panGestureRecognizer translationInView:self];
    translation.y -= diff * 3.0 / 2.0;
    [self.panGestureRecognizer setTranslation:translation inView:self];
  }
  [super setContentInset:contentInset];
}

Interestingly, UITableView accounts for this by NOT slowing down tracking until you pull PAST the refresh control. 有趣的是, UITableView通过不降低跟踪速度来解决这个问题,直到您将PAST拉入刷新控件。 However, I don't see a way that this behavior is exposed. 但是,我没有看到这种行为暴露的方式。

- (void)viewDidLoad
{
     [super viewDidLoad];

     self.refreshControl = [[UIRefreshControl alloc] init];
     [self.refreshControl addTarget:self action:@selector(scrollRefresh:) forControlEvents:UIControlEventValueChanged];
     [self.collection insertSubview:self.refreshControl atIndex:0];
     self.refreshControl.layer.zPosition = -1;
     self.collection.alwaysBounceVertical = YES;
 }

 - (void)scrollRefresh:(UIRefreshControl *)refreshControl
 {
     self.refreshControl.attributedTitle = [[NSAttributedString alloc] initWithString:@"Refresh now"];
     // ... update datasource
     dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(3 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
        self.refreshControl.attributedTitle = [[NSAttributedString alloc] initWithString:[NSString stringWithFormat:@"Updated %@", [NSDate date]]];
        [self.refreshControl endRefreshing];
        [self.collection reloadData];
     }); 

 }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM