用KVO监听实现collectionView滚动一致,完整项目movie

来源:互联网 发布:网络阅卷成绩 编辑:程序博客网 时间:2024/06/05 19:13

效果图如下:  为使的上面的collectionView的滚动和下面的collectionView的滚动保持一致  先采用 kvo方式

详情请看代码注释

        //1.kvo监听模式 option需要新的值还是旧的值        [_postView addObserver:self forKeyPath:@"currentIndex" options:NSKeyValueObservingOptionNew context:nil];        [_headerColletion addObserver:self forKeyPath:@"currentIndex" options:NSKeyValueObservingOptionNew context:nil];

其中_postView 是下面的collectionView  headerCollectionView是上面的collectionView  分别监听他们的currentIndex属性  currentIndex是标记他在第几个item上

//1.kvo监听模式/** keyPath:监听的属性名 object:监听的对象 change:监听的值 context:传递的数据 */- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context{    //取得新的值    NSNumber *value = [change objectForKey:@"new"];    //转换为int值    NSInteger selectIndex = [value intValue];    //转换为滚动到的位置书    NSIndexPath *IndexPath = [NSIndexPath indexPathForItem:selectIndex inSection:0];        //如果监听的对象是headerView 并且postView的currentIndex 不等于headerViewcell选中的currentIndex那么 postView 就滚动到选中的item    if (object == _headerColletion && _postView.currentIndex != selectIndex) {                [_postView scrollToItemAtIndexPath:IndexPath atScrollPosition:UICollectionViewScrollPositionCenteredHorizontally animated:YES];                //操作完成后把postView的currentIndex 变成这个        _postView.currentIndex = selectIndex;            //如果监听的对象是postView 并且headerView的currentIndex 不等于postViewcell选中的currentIndex那么 postView 就滚动到选中的item    } else if(object == _postView && _headerColletion.currentIndex != selectIndex){                [_headerColletion scrollToItemAtIndexPath:IndexPath atScrollPosition:UICollectionViewScrollPositionCenteredHorizontally animated:YES];        //操作完成后把postView的currentIndex 变成这个        _headerColletion.currentIndex = selectIndex;    }}
这里的值得一提的事change这个这个值 可以用key new 和old取值  分别取得 新值和旧值
具体可以看注释  下面是posterView中滚动完成后的调用函数属性currentIndex改变 受到监听

- (void)scrollViewWillEndDragging:(UIScrollView *)scrollView withVelocity:(CGPoint)velocity targetContentOffset:(inout CGPoint *)targetContentOffset{    //因为offset不是对象不能用点访问    CGFloat contentX = targetContentOffset->x;        /*round:如果参数是小数,则求本身的四舍五入。     ceil:如果参数是小数,则求最小的整数但不小于本身.     floor:如果参数是小数,则求最大的整数但不大于本身.          Example:如何值是3.4的话,则     3.4 -- round 3.000000     -- ceil 4.000000     -- floor 3.00000     **/        //用四色五入 计算第几页    float pageFloat = contentX/_pageWidth;        NSInteger page = (int)round(pageFloat);        targetContentOffset->x = page * _pageWidth;        //记录当前页面 此处要提醒一句  这个值必须要用系统生成的setter语句来赋值才能kvo监听 _currentIndex = page是不能够监听到的    self.currentIndex = page;

此处要提醒一句  这个值必须要用系统生成的setter语句来赋值才能kvo监听 _currentIndex = page是不能够监听到的

当点击了 不是当前的item 那么也会滚动  currentIndex 也会改变


//单元格点击事件处理- (void)collectionView:(UICollectionView *)collectionView didSelectItemAtIndexPath:(NSIndexPath *)indexPath{            //滚到点击的cell    [collectionView scrollToItemAtIndexPath:indexPath atScrollPosition:UICollectionViewScrollPositionCenteredHorizontally animated:YES];//    if ([self.scrolldelegate respondsToSelector:@selector(scrollToCurrentIndex:)]) {//        [self.scrolldelegate scrollToCurrentIndex:indexPath.item];//    }                    //记录当前的cell  此处要提醒一句  这个值必须要用系统生成的setter语句来赋值才能kvo监听 _currentIndex = indexPath.item是不能够监听到的    self.currentIndex = indexPath.item;        }


其中注释部分为代理实现方式  不用理会 如果你想看代理实现方式 可以看下一篇文章

也可以看源代码 地址点击打开链接  github上的动画太卡了  真实没那么卡的  你们可以下下来看一下

0 0
原创粉丝点击