Files
keyboard/keyBoard/Class/Pay/V/KBSvipFlowLayout.m
2026-02-04 12:48:18 +08:00

91 lines
3.8 KiB
Objective-C

//
// KBSvipFlowLayout.m
// keyBoard
//
// SVIP 页面自定义布局,支持 Section 背景装饰视图
//
#import "KBSvipFlowLayout.h"
#import "KBSvipBenefitBgView.h"
static NSString * const kKBSvipDecorationViewKind = @"KBSvipBenefitBgDecoration";
@interface KBSvipFlowLayout ()
@property (nonatomic, strong) NSMutableArray<UICollectionViewLayoutAttributes *> *decorationAttributes;
@end
@implementation KBSvipFlowLayout
- (instancetype)init {
if (self = [super init]) {
_decorationSection = 1; // 默认 Section 1 需要背景
[self registerClass:[KBSvipBenefitBgView class] forDecorationViewOfKind:kKBSvipDecorationViewKind];
}
return self;
}
- (void)prepareLayout {
[super prepareLayout];
self.decorationAttributes = [NSMutableArray array];
NSInteger numberOfSections = [self.collectionView numberOfSections];
if (self.decorationSection >= numberOfSections) { return; }
NSInteger numberOfItems = [self.collectionView numberOfItemsInSection:self.decorationSection];
if (numberOfItems == 0) { return; }
// 获取 Section Header 的布局属性
UICollectionViewLayoutAttributes *headerAttr = [self layoutAttributesForSupplementaryViewOfKind:UICollectionElementKindSectionHeader atIndexPath:[NSIndexPath indexPathForItem:0 inSection:self.decorationSection]];
// 获取第一个和最后一个 item 的布局属性
UICollectionViewLayoutAttributes *firstItemAttr = [self layoutAttributesForItemAtIndexPath:[NSIndexPath indexPathForItem:0 inSection:self.decorationSection]];
UICollectionViewLayoutAttributes *lastItemAttr = [self layoutAttributesForItemAtIndexPath:[NSIndexPath indexPathForItem:numberOfItems - 1 inSection:self.decorationSection]];
if (!firstItemAttr || !lastItemAttr) { return; }
// 计算背景区域
UIEdgeInsets sectionInset = self.sectionInset;
if ([self.collectionView.delegate respondsToSelector:@selector(collectionView:layout:insetForSectionAtIndex:)]) {
sectionInset = [(id<UICollectionViewDelegateFlowLayout>)self.collectionView.delegate collectionView:self.collectionView layout:self insetForSectionAtIndex:self.decorationSection];
}
CGFloat minY = CGRectGetMinY(headerAttr.frame);
CGFloat maxY = CGRectGetMaxY(lastItemAttr.frame) + 16; // 底部留 16 间距
CGFloat x = sectionInset.left;
CGFloat width = self.collectionView.bounds.size.width - sectionInset.left - sectionInset.right;
CGRect decorationFrame = CGRectMake(x, minY, width, maxY - minY);
UICollectionViewLayoutAttributes *decorationAttr = [UICollectionViewLayoutAttributes layoutAttributesForDecorationViewOfKind:kKBSvipDecorationViewKind withIndexPath:[NSIndexPath indexPathForItem:0 inSection:self.decorationSection]];
decorationAttr.frame = decorationFrame;
decorationAttr.zIndex = -1; // 放在最底层
[self.decorationAttributes addObject:decorationAttr];
}
- (NSArray<__kindof UICollectionViewLayoutAttributes *> *)layoutAttributesForElementsInRect:(CGRect)rect {
NSMutableArray *attrs = [[super layoutAttributesForElementsInRect:rect] mutableCopy];
for (UICollectionViewLayoutAttributes *decorationAttr in self.decorationAttributes) {
if (CGRectIntersectsRect(rect, decorationAttr.frame)) {
[attrs addObject:decorationAttr];
}
}
return attrs;
}
- (UICollectionViewLayoutAttributes *)layoutAttributesForDecorationViewOfKind:(NSString *)elementKind atIndexPath:(NSIndexPath *)indexPath {
if ([elementKind isEqualToString:kKBSvipDecorationViewKind]) {
for (UICollectionViewLayoutAttributes *attr in self.decorationAttributes) {
if (attr.indexPath.section == indexPath.section) {
return attr;
}
}
}
return [super layoutAttributesForDecorationViewOfKind:elementKind atIndexPath:indexPath];
}
@end