他の誰かがこの質問に出くわした場合、答えは「いいえ」でした。スワイプアウトのジェスチャーを処理するためにカスタム UICollectionViewFlowLayout を作成するべきではありません。UIScrollViews を使用すると、カスタム レイアウトを実装するよりもはるかに自然な感覚になります。これは、スクロール ビューが iOS 全体で持つのと同じスクロールと勢いを提供します。
ネストされた UIScrollViews を使用して、非常に簡単な方法で問題を解決することができました。私が受け取っていた警告は、実際にはコレクションビューをタブビューコントローラーの最初のタブスポットに配置し、セルが画面全体を占有するという単なるバグだったようです。このバグは、コレクション ビューの背後に別のビューを追加することで解決されました。
- (void)viewDidLoad
{
[super viewDidLoad];
[self.cardCollectionView registerClass:[SwipeCardCollectionViewCell class] forCellWithReuseIdentifier:kCollectionViewCellIdentifier];
self.cardCollectionView.alwaysBounceVertical = NO;
self.cardCollectionView.alwaysBounceHorizontal = YES;
}
- (void)loadView {
self.view = [[UIView alloc] init];
self.layout = [[UICollectionViewFlowLayout alloc] init];
self.layout.scrollDirection = UICollectionViewScrollDirectionHorizontal
self.cardCollectionView = [[UICollectionView alloc] initWithFrame:CGRectZero collectionViewLayout:self.layout];
self.cardCollectionView.translatesAutoresizingMaskIntoConstraints = NO;
self.cardCollectionView.backgroundColor = [UIColor clearColor];
self.cardCollectionView.delegate = self;
self.cardCollectionView.dataSource = self;
[self.view addSubview:self.cardCollectionView];
NSDictionary *views = @{@"cardCollectionView": self.cardCollectionView}
[self.view addConstraints: [NSLayoutConstraint constraintsWithVisualFormat:@"V:|[cardCollectionView]|"
options:0
metrics:nil
views:views]];
[self.view addConstraints: [NSLayoutConstraint constraintsWithVisualFormat:@"H:|[cardCollectionView]|"
options:0
metrics:nil
views:views]];
views:views]];
}
-(UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath{
SwipeCardCollectionViewCell *cell = [collectionView dequeueReusableCellWithReuseIdentifier:kCollectionViewCellIdentifier forIndexPath:indexPath];
cell.delegate = self;
return cell;
}
コレクションビューsizeForItemAtIndexPath:
を画面のサイズと同じにしました
- (CGSize)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout*)collectionViewLayout sizeForItemAtIndexPath:(NSIndexPath *)indexPath {
return CGSizeMake(self.cardCollectionView.frame.size.width - CARD_WIDTH_INSET, self.cardCollectionView.frame.size.height);
}
-(CGFloat)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout *)collectionViewLayout minimumInteritemSpacingForSectionAtIndex:(NSInteger)section{
return 0.0;
}
-(CGFloat)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout *)collectionViewLayout minimumLineSpacingForSectionAtIndex:(NSInteger)section {
return CARD_SPACING;
}
scrollViewWillEndDragging:withVelocity:targetContentOffset:
コレクション ビューの両側にコンテンツ インセットを実装して追加することで、コレクション ビューの境界の幅ではなく、カードの幅でカードをページングできるようにしました。
- (UIEdgeInsets)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout*)collectionViewLayout insetForSectionAtIndex:(NSInteger)section{
CGFloat inset = CARD_WIDTH_INSET/2.0;
return UIEdgeInsetsMake(0.0, inset, 0.0, inset);
}
- (void)scrollViewWillEndDragging:(UIScrollView *)scrollView withVelocity:(CGPoint)velocity targetContentOffset:(inout CGPoint *)targetContentOffset {
CGFloat cardWidth = self.cardCollectionView.frame.size.width - CARD_WIDTH_INSET;
NSInteger cardNumber = round(targetContentOffset->x/(cardWidth + CARD_SPACING));
CGFloat finalOffset = cardNumber*(cardWidth + CARD_SPACING);
targetContentOffset->x = finalOffset;
}
最後に、作成したカスタム スワイプ セルにスクロール ビューを追加することで、カードを画面からスワイプすることができました。ページングを有効にすると、スプリングボード マルチタスク UI と同じように、カードを画面から右にスワイプできます。そのようです、
- (id)initWithFrame:(CGRect)frame
{
self = [super initWithFrame:frame];
if (self) {
self.cardContainerScrollView = [[UIScrollView alloc] init];
self.cardContainerScrollView.delegate = self;
self.cardContainerScrollView.pagingEnabled = YES;
self.cardContainerScrollView.translatesAutoresizingMaskIntoConstraints = NO;
self.cardContainerScrollView.alwaysBounceHorizontal = NO;
self.cardContainerScrollView.alwaysBounceVertical = YES;
self.cardContainerScrollView.showsHorizontalScrollIndicator = NO;
self.cardContainerScrollView.showsVerticalScrollIndicator = NO;
self.cardView = [[UIView alloc] init];
self.cardView.translatesAutoresizingMaskIntoConstraints = NO;
self.cardView.backgroundColor = [UIColor whiteColor];
[self.cardContainerScrollView addSubview:self.cardView];
[self.contentView addSubview:self.cardContainerScrollView];
NSDictionary *views = @{@"cardView": self.cardView,
@"cardContainerScrollView": self.cardContainerScrollView};
[self.contentView addConstraints: [NSLayoutConstraint constraintsWithVisualFormat:@"V:|[cardContainerScrollView]|"
options:0
metrics:nil
views:views]];
[self.contentView addConstraints: [NSLayoutConstraint constraintsWithVisualFormat:@"H:|[cardContainerScrollView]|"
options:0
metrics:nil
views:views]];
[self.contentView addConstraints: [NSLayoutConstraint constraintsWithVisualFormat:@"V:|-70-[cardView(400)]-650-|"
options:0
metrics:nil
views:views]];
[self.contentView addConstraints: [NSLayoutConstraint constraintsWithVisualFormat:@"H:|[cardView(260)]|"
options:0
metrics:nil
views:views]];
}
return self;
}