根据 Apple 的文档(并在 WWDC 2012 上吹捧),可以UICollectionView
动态设置布局,甚至可以为更改设置动画:
您通常在创建集合视图时指定布局对象,但您也可以动态更改集合视图的布局。布局对象存储在 collectionViewLayout 属性中。设置此属性会立即直接更新布局,而不会对更改进行动画处理。如果您想为更改设置动画,则必须调用 setCollectionViewLayout:animated: 方法。
然而,在实践中,我发现这UICollectionView
会对contentOffset
. 为了说明这个问题,我将以下示例代码放在一起,这些代码可以附加到放入故事板中的默认集合视图控制器:
#import <UIKit/UIKit.h>
@interface MyCollectionViewController : UICollectionViewController
@end
@implementation MyCollectionViewController
- (void)viewDidLoad
{
[super viewDidLoad];
[self.collectionView registerClass:[UICollectionViewCell class] forCellWithReuseIdentifier:@"CELL"];
self.collectionView.collectionViewLayout = [[UICollectionViewFlowLayout alloc] init];
}
- (NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection:(NSInteger)section
{
return 1;
}
- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath
{
UICollectionViewCell *cell = [self.collectionView dequeueReusableCellWithReuseIdentifier:@"CELL" forIndexPath:indexPath];
cell.backgroundColor = [UIColor whiteColor];
return cell;
}
- (void)collectionView:(UICollectionView *)collectionView didSelectItemAtIndexPath:(NSIndexPath *)indexPath
{
NSLog(@"contentOffset=(%f, %f)", self.collectionView.contentOffset.x, self.collectionView.contentOffset.y);
[self.collectionView setCollectionViewLayout:[[UICollectionViewFlowLayout alloc] init] animated:YES];
NSLog(@"contentOffset=(%f, %f)", self.collectionView.contentOffset.x, self.collectionView.contentOffset.y);
}
@end
控制器设置默认值并UICollectionViewFlowLayout
在viewDidLoad
屏幕上显示单个单元格。当单元格被选中时,控制器会创建另一个默认值UICollectionViewFlowLayout
并将其设置在带有animated:YES
标志的集合视图上。预期的行为是单元格不移动。然而,实际行为是单元格滚动到屏幕外,此时甚至不可能将单元格滚动回屏幕上。
查看控制台日志显示 contentOffset 发生了莫名其妙的变化(在我的项目中,从 (0, 0) 到 (0, 205))。我发布了针对非动画案例(i.e. animated:NO
作为旁注,我已经测试了自定义布局并获得了相同的行为。