UICollectionView 消耗垂直平移手势
UICollectionView consuming vertical pan gesture
我有一个 UICollectionView,它位于 UITableView 和 UIScrollView 内。 collection 视图是一个水平滚动的项目轮播,如果 collection 视图中有足够多的项目,它就可以正常工作,因此它比屏幕的宽度还宽。但是我遇到的问题是,如果只有一两个项目(不足以填满屏幕的宽度),那么 collection 视图似乎会消耗垂直平移手势并且不会让滚动视图滚动。
这是我的应用程序当前的布局方式。有滚动视图(下图中的绿色),它包含页面上的所有内容。在里面,有一个 table 视图,它有多个部分。每个部分都有一个可点击的部分 header。点击 header 部分后,该部分会通过添加包含 collection 视图的一行来扩展。 collection 视图是水平滚动流布局 collection 视图。
只要 collection 视图中有足够的 collection 视图单元格,它就会从屏幕上消失(如上图所示。但是如果只有一个项目,例如(如下图所示),那么如果在 collection 视图内的任意位置(下图中蓝色区域或棕褐色区域的任意位置)开始平移手势,则滚动视图将无法垂直滚动.
代码
下面是初始化 collection 视图的代码:
- (UICollectionView *)collectionView {
if (!self->_collectionView) {
UICollectionViewFlowLayout *layout = [[UICollectionViewFlowLayout alloc] init];
layout.minimumInteritemSpacing = 10;
layout.minimumLineSpacing = 10;
layout.sectionInset = UIEdgeInsetsMake(0, 16, 0, 16);
layout.sectionInsetReference = UICollectionViewFlowLayoutSectionInsetFromContentInset;
layout.scrollDirection = UICollectionViewScrollDirectionHorizontal;
self->_collectionView = [[UICollectionView alloc] initWithFrame:CGRectZero collectionViewLayout:layout];
self->_collectionView.translatesAutoresizingMaskIntoConstraints = NO;
self->_collectionView.backgroundColor = nil;
self->_collectionView.delegate = self;
self->_collectionView.dataSource = self;
[self.collectionView registerClass:[MyCollectionViewCell class] forCellWithReuseIdentifier:@"MyCollectionViewCell"];
}
return self->_collectionView;
}
问题
有谁知道为什么 collection 视图在只有一两个项目时会消耗垂直平移手势,或者如何解决这个问题?
三个视图实际上都是滚动视图。 UITableView
和 UICollectionView
类 继承自 UIScrollView
。
UIScrollView
通过其 panGestureRecognizer
.
识别滚动
由于您没有在滚动视图中定义这些识别器之间的依赖关系,触摸事件将按以下方式使用:
- 所有识别器都接收触摸(这就是它们由
UIScrollView
预先配置的方式)
- 如果命中测试视图的识别器没有失败,它会处理平移手势
- 如果失败,父视图的识别器会尝试处理手势。
并且这个级联的平移处理像那样沿着视图层次上升,直到手势被处理或者没有更多的滚动视图。
在您的情况下,当集合视图的内容大小小于或等于其边界大小时,水平滚动的集合视图的平移识别器对于垂直滚动不会失败。
你可以尝试两件事。要么要求滚动视图平移识别器失败以用于集合视图平移识别器
[self->_collectionView.panGestureRecognizer requireGestureRecognizerToFail:scrollView.panGestureRecognizer]
或在内容大小小于边界时禁用集合视图的滚动。为此,您可以创建 UICollectionView
的子类,覆盖 setContentSize:
和 setBounds:
方法并相应地分配 scrollEnabled
。然后使用你的子类而不是香草 UICollectionView
.
我有一个 UICollectionView,它位于 UITableView 和 UIScrollView 内。 collection 视图是一个水平滚动的项目轮播,如果 collection 视图中有足够多的项目,它就可以正常工作,因此它比屏幕的宽度还宽。但是我遇到的问题是,如果只有一两个项目(不足以填满屏幕的宽度),那么 collection 视图似乎会消耗垂直平移手势并且不会让滚动视图滚动。
这是我的应用程序当前的布局方式。有滚动视图(下图中的绿色),它包含页面上的所有内容。在里面,有一个 table 视图,它有多个部分。每个部分都有一个可点击的部分 header。点击 header 部分后,该部分会通过添加包含 collection 视图的一行来扩展。 collection 视图是水平滚动流布局 collection 视图。
只要 collection 视图中有足够的 collection 视图单元格,它就会从屏幕上消失(如上图所示。但是如果只有一个项目,例如(如下图所示),那么如果在 collection 视图内的任意位置(下图中蓝色区域或棕褐色区域的任意位置)开始平移手势,则滚动视图将无法垂直滚动.
代码
下面是初始化 collection 视图的代码:
- (UICollectionView *)collectionView {
if (!self->_collectionView) {
UICollectionViewFlowLayout *layout = [[UICollectionViewFlowLayout alloc] init];
layout.minimumInteritemSpacing = 10;
layout.minimumLineSpacing = 10;
layout.sectionInset = UIEdgeInsetsMake(0, 16, 0, 16);
layout.sectionInsetReference = UICollectionViewFlowLayoutSectionInsetFromContentInset;
layout.scrollDirection = UICollectionViewScrollDirectionHorizontal;
self->_collectionView = [[UICollectionView alloc] initWithFrame:CGRectZero collectionViewLayout:layout];
self->_collectionView.translatesAutoresizingMaskIntoConstraints = NO;
self->_collectionView.backgroundColor = nil;
self->_collectionView.delegate = self;
self->_collectionView.dataSource = self;
[self.collectionView registerClass:[MyCollectionViewCell class] forCellWithReuseIdentifier:@"MyCollectionViewCell"];
}
return self->_collectionView;
}
问题
有谁知道为什么 collection 视图在只有一两个项目时会消耗垂直平移手势,或者如何解决这个问题?
三个视图实际上都是滚动视图。 UITableView
和 UICollectionView
类 继承自 UIScrollView
。
UIScrollView
通过其 panGestureRecognizer
.
由于您没有在滚动视图中定义这些识别器之间的依赖关系,触摸事件将按以下方式使用:
- 所有识别器都接收触摸(这就是它们由
UIScrollView
预先配置的方式) - 如果命中测试视图的识别器没有失败,它会处理平移手势
- 如果失败,父视图的识别器会尝试处理手势。
并且这个级联的平移处理像那样沿着视图层次上升,直到手势被处理或者没有更多的滚动视图。
在您的情况下,当集合视图的内容大小小于或等于其边界大小时,水平滚动的集合视图的平移识别器对于垂直滚动不会失败。
你可以尝试两件事。要么要求滚动视图平移识别器失败以用于集合视图平移识别器
[self->_collectionView.panGestureRecognizer requireGestureRecognizerToFail:scrollView.panGestureRecognizer]
或在内容大小小于边界时禁用集合视图的滚动。为此,您可以创建 UICollectionView
的子类,覆盖 setContentSize:
和 setBounds:
方法并相应地分配 scrollEnabled
。然后使用你的子类而不是香草 UICollectionView
.