UICollectionViewLayout (布局對象)
1登钥、創(chuàng)建集合視圖布局的方法:
typedef NS_ENUM(NSInteger, UICollectionViewScrollDirection) {
UICollectionViewScrollDirectionVertical,
UICollectionViewScrollDirectionHorizontal
};
#pragma mark --------創(chuàng)建集合視圖布局
//創(chuàng)建集合視圖布局對象。
- (instancetype)init;
//從給定unarchiver中的數(shù)據(jù)創(chuàng)建集合視圖布局對象烘苹。
- (instancetype)initWithCoder:(NSCoder *)coder;
2、獲取集合視圖信息的方法:
#pragma mark -------- 獲取集合視圖信息
// 當前使用此布局對象的集合視圖對象背传。
@property(nullable, nonatomic, readonly) UICollectionView *collectionView;
// 集合視圖內(nèi)容的寬度和高度兵怯。
@property(nonatomic, readonly) CGSize collectionViewContentSize;
3敷存、提供布局屬性的方法:
#pragma mark ------- 提供布局屬性
//創(chuàng)建布局屬性對象時要使用的類.
//用于布局屬性對象的類.
//如果你子類化UICollectionViewLayoutAttributes來管理額外的布局屬性,
//你應該重寫這個方法并返回你的自定義子類柴我。
//創(chuàng)建布局屬性的方法在創(chuàng)建新的布局屬性對象時使用這個類解寝。
//此方法僅用于子類,不需要由代碼調(diào)用艘儒。
@property(class, nonatomic, readonly) Class layoutAttributesClass;
//告訴布局對象更新當前的布局聋伦。
//布局更新發(fā)生在集合視圖第一次顯示其內(nèi)容時,
//以及布局因視圖更改而顯式或隱式失效時,都會進行布局更新界睁。
//在每次布局更新期間觉增,集合視圖首先調(diào)用這個方法,
//使布局對象有機會為即將到來的布局操作做準備翻斟。
//此方法的默認實現(xiàn)不執(zhí)行任何操作逾礁。
//子類可以覆蓋它,并使用它來設置數(shù)據(jù)結(jié)構(gòu)或執(zhí)行以后執(zhí)行布局所需的任何初始計算访惜。
- (void)prepareLayout;
//檢索指定矩形中所有單元格和視圖的布局屬性嘹履。
//UICollectionViewLayoutAttributes對象數(shù)組,表示單元格和視圖的布局信息债热。
//默認實現(xiàn)返回nil砾嫉。
//子類必須重寫此方法,并使用它返回視圖與指定矩形相交的所有項的布局信息窒篱。
//您的實現(xiàn)應該返回所有可視元素的屬性焕刮,包括單元格、補充視圖和裝飾視圖墙杯。
//在創(chuàng)建布局屬性時济锄,總是創(chuàng)建一個表示正確元素類型(單元格、補充或裝飾)的屬性對象霍转。
//集合視圖區(qū)分每種類型的屬性,并使用該信息來決定創(chuàng)建哪些視圖以及如何管理它們一汽。
- (NSArray<__kindof UICollectionViewLayoutAttributes *> *)layoutAttributesForElementsInRect:(CGRect)rect;
//檢索具有相應單元格的指定索引路徑上的項的布局信息避消。
//一個布局屬性對象低滩,包含要應用到該項單元格的信息。
//子類必須重寫此方法岩喷,并使用它返回集合視圖中項目的布局信息恕沫。
//使用此方法僅為具有相應單元格的項提供布局信息。
//不要將它用于補充視圖或裝飾視圖I匆狻I羲荨!
- (UICollectionViewLayoutAttributes *)layoutAttributesForItemAtIndexPath:(NSIndexPath *)indexPath;
//當一個item被用戶交互式移動時偷霉,檢索該item的布局屬性迄委。
//item 位于指定位置時的布局屬性。
//當項由于用戶交互而移動時类少,布局對象使用此方法檢索項在指定位置時要使用的布局屬性叙身。
//該方法的默認實現(xiàn)返回一個項目現(xiàn)有屬性的副本,
//并進行了兩個更改:中心點被設置為position中的值硫狞,
//zIndex值被設置為NSIntegerMax信轿,以便項目在集合視圖中浮動在其他項目之上。
//子類可以覆蓋這個方法残吩,并根據(jù)需要修改額外的布局屬性财忽。
//如果重寫此方法,請首先調(diào)用super檢索該項的現(xiàn)有屬性泣侮,然后對返回的結(jié)構(gòu)進行更改即彪。
//indexPath 被移動的項目的索引路徑。
//position item 在集合視圖坐標系中的當前位置
- (UICollectionViewLayoutAttributes *)layoutAttributesForInteractivelyMovingItemAtIndexPath:(NSIndexPath *)indexPath
withTargetPosition:(CGPoint)position;
//檢索指定補充視圖的布局屬性旁瘫。
//一個布局屬性對象祖凫,包含應用到補充視圖的信息。
//如果布局對象定義了任何補充視圖酬凳,則必須重寫此方法并使用它返回這些視圖的布局信息惠况。
//elementKind 標識補充視圖類型的字符串。
//indexPath 視圖的索引路徑.
- (UICollectionViewLayoutAttributes *)layoutAttributesForSupplementaryViewOfKind:(NSString *)elementKind
atIndexPath:(NSIndexPath *)indexPath;
//檢索指定裝飾視圖(Decoration View)的布局屬性.
// 布局屬性對象宁仔,包含要應用于裝飾視圖的信息稠屠。
//如果布局對象定義了任何裝飾視圖,則必須重寫此方法并使用它來返回這些視圖的布局信息翎苫。
//elementKind 標識 裝飾視圖(Decoration View)類型的字符串权埠。
//indexPath 視圖的索引路徑.
- (UICollectionViewLayoutAttributes *)layoutAttributesForDecorationViewOfKind:(NSString*)elementKind
atIndexPath:(NSIndexPath *)indexPath;
//檢索在動畫布局更新或更改后要使用的內(nèi)容偏移量。
//您要使用的內(nèi)容偏移量煎谍。此方法的默認實現(xiàn)返回proposedContentOffset參數(shù)中的值攘蔽。
//在布局更新期間,或在布局之間轉(zhuǎn)換時呐粘,集合視圖調(diào)用此方法满俗,
//以便您有機會更改要在動畫結(jié)束時使用的建議內(nèi)容偏移转捕。
//如果動畫或過渡可能導致項目的定位方式不是最適合您的設計,則可以重寫此方法唆垃。
//集合視圖在調(diào)用prepareLayout和collectionViewContentSize方法之后調(diào)用該方法五芝。
// proposedContentOffset 提議的內(nèi)容偏移
-(CGPoint)targetContentOffsetForProposedContentOffset:(CGPoint)proposedContentOffset;
// 檢索停止?jié)L動的點。
//您要使用的內(nèi)容偏移量辕万。該值反映了調(diào)整后的可見區(qū)域的左上角枢步。
//此方法的默認實現(xiàn)返回proposedContentOffset參數(shù)中的值。
//如果希望滾動行為捕捉到特定的邊界渐尿,可以重寫此方法并使用它來更改停止的點醉途。
//例如,您可以使用此方法始終在項目之間的邊界上停止?jié)L動涡戳,而不是在項目中間停止?jié)L動结蟋。
//proposedContentOffset 建議停止?jié)L動的點(在集合視圖的內(nèi)容視圖中)。
//如果不做任何調(diào)整渔彰,滾動就會自然停止嵌屎。該點反映可見內(nèi)容的左上角。
//velocity 當前沿水平軸和垂直軸的滾動速度恍涂。該值以每秒點數(shù)為單位宝惰。
-(CGPoint)targetContentOffsetForProposedContentOffset:(CGPoint)proposedContentOffset
withScrollingVelocity:(CGPoint)velocity;
4、響應集合視圖更新的方法:
#pragma mark ------- 響應集合視圖更新
// 通知布局對象集合視圖的內(nèi)容即將更改再沧。
//當插入或刪除項時尼夺,集合視圖通知它的布局對象,以便它可以根據(jù)需要調(diào)整布局炒瘸。
//這個過程的第一步是調(diào)用這個方法淤堵,讓布局對象知道預期會發(fā)生什么變化。
//在此之后顷扩,將進行其他調(diào)用拐邪,以收集插入、刪除和移動項的布局信息隘截,這些項將圍繞集合視圖進行動畫化扎阶。
- (void)prepareForCollectionViewUpdates:(NSArray<UICollectionViewUpdateItem *> *)updateItems;
//執(zhí)行在集合視圖更新期間所需的任何其他動畫或清理。
//集合視圖調(diào)用此方法作為將任何更改動畫化之前的最后一步.
//此方法在用于執(zhí)行所有插入婶芭、刪除和移動動畫的動畫塊中調(diào)用东臀,
//因此您可以根據(jù)需要使用此方法創(chuàng)建其他動畫。
//否則犀农,您可以使用它來執(zhí)行與管理布局對象的狀態(tài)信息相關(guān)的任何最后一分鐘的任務惰赋。
- (void)finalizeCollectionViewUpdates;
//檢索要添加到布局中的補充視圖的索引路徑數(shù)組。
//NSIndexPath對象數(shù)組呵哨,表示新的補充視圖的位置赁濒,
//如果不想添加任何補充視圖贵扰,則為空數(shù)組。
//每當向集合視圖添加cells或sections時流部,集合視圖都會調(diào)用此方法。
//實現(xiàn)此方法使您的布局對象有機會添加新的補充視圖來補充添加的內(nèi)容纹坐。
//集合視圖在調(diào)用prepareForCollectionViewUpdates:和
//finalizeCollectionViewUpdates之間調(diào)用此方法枝冀。
- (NSArray<NSIndexPath *> *)indexPathsToInsertForSupplementaryViewOfKind:(NSString *)elementKind;
//檢索表示要添加的裝飾視圖的索引路徑數(shù)組。
//NSIndexPath對象數(shù)組耘子,表示新裝飾視圖的位置果漾,
//如果不想添加任何裝飾視圖,則為空數(shù)組谷誓。
//每當向集合視圖添加cells或sections時绒障,集合視圖都會調(diào)用此方法。
//實現(xiàn)此方法使布局對象有機會添加新的裝飾視圖來補充添加的內(nèi)容捍歪。
//集合視圖在調(diào)用prepareForCollectionViewUpdates:和
//finalizeCollectionViewUpdates之間調(diào)用此方法户辱。
- (NSArray<NSIndexPath *> *)indexPathsToInsertForDecorationViewOfKind:(NSString *)elementKind;
//檢索插入到集合視圖中的項的起始布局信息。
//一個布局屬性對象糙臼,用于描述要放置相應單元格的位置庐镐。
//該方法在prepareForCollectionViewUpdates方法之后和
//finalizeCollectionViewUpdates方法之前被調(diào)用,用于即將插入的任何項变逃。
//您的實現(xiàn)應該返回描述該項的初始位置和狀態(tài)的布局信息必逆。
//集合視圖使用這些信息作為任何動畫的起點(動畫的結(jié)束點是項目在集合視圖中的新位置)。
//如果你返回nil揽乱,布局對象使用項目的final屬性作為動畫的開始點和結(jié)束點名眉。
//此方法的默認實現(xiàn)將返回nil。
- (UICollectionViewLayoutAttributes *)initialLayoutAttributesForAppearingItemAtIndexPath:(NSIndexPath *)itemIndexPath;
//檢索插入到集合視圖中的補充視圖的起始布局信息凰棉。
//一個布局屬性對象损拢,它描述放置相應補充視圖的位置。
//該方法在prepareForCollectionViewUpdates方法之后和
//finalizeCollectionViewUpdates方法之前被調(diào)用,用于即將插入的任何補充視圖渊啰。
//您的實現(xiàn)應該返回描述視圖初始位置和狀態(tài)的布局信息探橱。
//集合視圖使用這些信息作為任何動畫的起點(動畫的結(jié)束點是視圖在集合視圖中的新位置)。
//如果你返回nil绘证,布局對象使用項目的final屬性作為動畫的開始點和結(jié)束點隧膏。
//此方法的默認實現(xiàn)將返回nil。
- (UICollectionViewLayoutAttributes *)initialLayoutAttributesForAppearingSupplementaryElementOfKind:(NSString *)elementKind
atIndexPath:(NSIndexPath *)elementIndexPath;
//檢索插入到集合視圖中的裝飾視圖的起始布局信息嚷那。
//一個布局屬性對象胞枕,描述放置相應裝飾視圖的位置。
//這個方法在prepareForCollectionViewUpdates方法之后和
//finalizeCollectionViewUpdates方法之前被調(diào)用魏宽,用于任何即將插入的裝飾視圖腐泻。
//您的實現(xiàn)應該返回描述視圖初始位置和狀態(tài)的布局信息决乎。
//集合視圖使用這些信息作為任何動畫的起點(動畫的結(jié)束點是視圖在集合視圖中的新位置)。
//如果你返回nil派桩,布局對象使用項目的final屬性作為動畫的開始點和結(jié)束點构诚。
//此方法的默認實現(xiàn)將返回nil。
- (UICollectionViewLayoutAttributes *)initialLayoutAttributesForAppearingDecorationElementOfKind:(NSString *)elementKind
//檢索表示要刪除的補充視圖的索引路徑數(shù)組铆惑。
//NSIndexPath對象數(shù)組范嘱,表示要刪除的補充視圖;
//如果不想刪除任何給定類型的視圖,則為空數(shù)組员魏。
//每當向集合視圖刪除cells或sections時丑蛤,集合視圖都會調(diào)用此方法。
//實現(xiàn)此方法使布局對象有機會刪除不再需要的任何補充視圖撕阎。
//集合視圖在調(diào)用prepareForCollectionViewUpdates:和
//finalizeCollectionViewUpdates之間調(diào)用此方法受裹。
- (NSArray<NSIndexPath *> *)indexPathsToDeleteForSupplementaryViewOfKind:(NSString *)elementKind;
//檢索表示要刪除的裝飾視圖的索引路徑數(shù)組。
//NSIndexPath對象數(shù)組虏束,表示要刪除的裝飾視圖;
//如果不想刪除任何給定類型的視圖棉饶,則為空數(shù)組。
//每當向集合視圖刪除cells或sections時魄眉,集合視圖都會調(diào)用此方法砰盐。
//實現(xiàn)此方法使布局對象有機會刪除不再需要的任何裝飾視圖。
//集合視圖在調(diào)用prepareForCollectionViewUpdates:和
//finalizeCollectionViewUpdates之間調(diào)用此方法坑律。
- (NSArray<NSIndexPath *> *)indexPathsToDeleteForDecorationViewOfKind:(NSString *)elementKind;
//檢索即將從集合視圖中刪除的項的最終布局信息岩梳。
//一個布局屬性對象,描述要用作動畫刪除單元格的終點的單元格的位置晃择。
//該方法在prepareForCollectionViewUpdates方法之后和
//finalizeCollectionViewUpdates方法之前被調(diào)用冀值,用于將要刪除的任何項。
//您的實現(xiàn)應該返回描述該項的最終位置和狀態(tài)的布局信息宫屠。//集合視圖使用此信息作為任何動畫的結(jié)束點列疗。(動畫的起點是物品的當前位置。)
//如果你返回nil浪蹂,布局對象對動畫的開始點和結(jié)束點使用相同的屬性抵栈。
//此方法的默認實現(xiàn)將返回nil。
- (UICollectionViewLayoutAttributes *)finalLayoutAttributesForDisappearingItemAtIndexPath:(NSIndexPath *)itemIndexPath;
//檢索即將從集合視圖中刪除的補充視圖的最終布局信息坤次。
//一個布局屬性對象古劲,用于描述補充視圖的位置,以作為動畫刪除的結(jié)束點缰猴。
//這個方法在prepareForCollectionViewUpdates方法之后和
//finalizeCollectionViewUpdates方法之前被調(diào)用产艾,用于將要刪除的任何補充視圖。
//您的實現(xiàn)應該返回描述視圖的最終位置和狀態(tài)的布局信息。
//集合視圖使用此信息作為任何動畫的結(jié)束點闷堡。(動畫的起點是視圖的當前位置隘膘。)
//如果你返回nil,布局對象對動畫的開始點和結(jié)束點使用相同的屬性杠览。
//此方法的默認實現(xiàn)將返回nil弯菊。
- (nullable UICollectionViewLayoutAttributes *)finalLayoutAttributesForDisappearingSupplementaryElementOfKind:(NSString *)elementKind atIndexPath:(NSIndexPath *)elementIndexPath;
//檢索即將從集合視圖中移除的裝飾視圖的最終布局信息。
//一個布局屬性對象踱阿,它描述裝飾視圖的位置误续,用于動畫化其移除。
//這個方法在prepareForCollectionViewUpdates方法之后和
//finalizeCollectionViewUpdates方法之前被調(diào)用扫茅,用于任何即將被刪除的裝飾視圖。
//您的實現(xiàn)應該返回描述視圖的最終位置和狀態(tài)的布局信息育瓜。
//集合視圖使用此信息作為任何動畫的結(jié)束點葫隙。(動畫的起點是視圖的當前位置。)
//如果你返回nil躏仇,布局對象對動畫的開始點和結(jié)束點使用相同的屬性恋脚。
//此方法的默認實現(xiàn)將返回nil。
- (nullable UICollectionViewLayoutAttributes *)finalLayoutAttributesForDisappearingDecorationElementOfKind:(NSString *)elementKind atIndexPath:(NSIndexPath *)decorationIndexPath;
//當項位于集合視圖邊界中的指定位置時焰手,檢索項的索引路徑糟描。
//與集合視圖中指定位置對應的索引路徑。
//在項目的交互移動過程中书妻,
//此方法將集合視圖的邊界矩形中的點映射到與這些點的位置對應的索引路徑船响。
//此方法的默認實現(xiàn)在指定位置搜索現(xiàn)有單元格并返回該單元格的索引路徑。
//如果在同一位置有多個單元格躲履,則該方法返回最上面的單元格见间,
//即zIndex布局屬性值最大的單元格。
//您可以根據(jù)需要重寫此方法工猜,以更改確定索引路徑的方式米诉。
//例如,您可以返回zIndex值最低而不是最高的單元格的索引路徑篷帅。
//如果重寫此方法史侣,則不需要調(diào)用super。
- (NSIndexPath *)targetIndexPathForInteractivelyMovingItem:(NSIndexPath *)previousIndexPath
withPosition:(CGPoint)position;
5魏身、使布局無效的方法:
#pragma mark ------- Invalidating the layout
//使當前布局失效并觸發(fā)布局更新惊橱。
//你可以在任何時候調(diào)用這個方法來更新布局信息。
//此方法使集合視圖本身的布局無效叠骑,并立即返回李皇。
//因此,您可以從同一代碼塊多次調(diào)用此方法,而不會觸發(fā)多次布局更新掉房。
//實際的布局更新發(fā)生在下一個視圖布局更新周期茧跋。
//如果重寫此方法,則必須在實現(xiàn)中的某個位置調(diào)用super卓囚。
- (void)invalidateLayout;
//使用 所提供的上下文對象中的信息 使當前布局失效瘾杭。
//這個方法的默認實現(xiàn)使用UICollectionViewLayoutInvalidationContext類的基本屬性來優(yōu)化布局過程。
//如果您為布局定義了一個自定義上下文對象哪亿,
//請重寫此方法并將上下文對象的任何自定義屬性應用到布局計算中粥烁。
//如果重寫此方法,則必須在實現(xiàn)中的某個位置調(diào)用super蝇棉。
- (void)invalidateLayoutWithContext:(UICollectionViewLayoutInvalidationContext *)context;
// 返回在為布局創(chuàng)建無效上下文時要使用的類讨阻。
//如果你子類化UICollectionViewLayout并使用一個自定義的
//無效上下文對象來提高布局更新的性能,重寫這個方法并返回
//你的UICollectionViewLayoutInvalidationContext子類篡殷。
//當集合視圖需要使布局無效時钝吮,它使用您提供的類來創(chuàng)建適當?shù)臒o效上下文對象。
@property(class, nonatomic, readonly) Class invalidationContextClass;
//詢問布局對象新的邊界是否需要更新布局板辽。
//如果集合視圖需要更新布局奇瘦,則為YES;如果布局不需要更改,則為NO劲弦。
//此方法的默認實現(xiàn)返回NO耳标。子類可以覆蓋它,
//并根據(jù)集合視圖邊界的更改是否需要更改單元格和補充視圖的布局來返回適當?shù)闹怠?//如果集合視圖的邊界發(fā)生了變化并且該方法返回YES邑跪,
//集合視圖將通過調(diào)用invalidatelayoutithcontext:方法使布局失效次坡。
- (BOOL)shouldInvalidateLayoutForBoundsChange:(CGRect)newBounds;
//檢索一個上下文對象,該對象定義了在發(fā)生邊界更改時應更改的布局部分画畅。
//一個無效上下文贸毕,用于描述需要進行的更改。不返回nil夜赵。
//此方法的默認實現(xiàn)創(chuàng)建一個由invalidationContextClass類方法提供的類實例并返回它明棍。
//如果你想在你的布局中使用一個自定義的無效上下文對象,
//總是重寫這個方法并返回你的自定義類寇僧。
//如果要創(chuàng)建和配置自定義失效上下文以響應邊界更改摊腋,則可以覆蓋此方法。
//如果重寫此方法嘁傀,則必須首先調(diào)用super以獲取要返回的無效上下文對象兴蒸。
//獲得該對象后,設置任何自定義屬性并返回它细办。
- (UICollectionViewLayoutInvalidationContext *)invalidationContextForBoundsChange:(CGRect)newBounds;
// 詢問布局對象對自定大小單元格的更改是否需要布局更新橙凳。
//如果該布局應該無效蕾殴,則為YES;如果不應該無效,則為NO岛啸。
//當集合視圖包含自調(diào)整大小的單元格時钓觉,
//單元格在應用這些屬性之前有機會修改自己的布局屬性。
//自調(diào)整大小的單元格可以這樣做坚踩,以指定與布局對象提供的單元格不同的單元格大小荡灾。
//當單元格提供不同的屬性集時,
//集合視圖調(diào)用此方法來確定單元格的更改是否需要更大的布局刷新瞬铸。
//如果您正在實現(xiàn)自定義布局批幌,
//則可以覆蓋此方法并使用它來確定是否應該基于指定的屬性使布局失效。
//此方法的默認實現(xiàn)返回NO嗓节。
- (BOOL)shouldInvalidateLayoutForPreferredLayoutAttributes:(UICollectionViewLayoutAttributes *)preferredAttributes
withOriginalAttributes:(UICollectionViewLayoutAttributes *)originalAttributes;
//檢索一個上下文對象荧缘,該對象標識應根據(jù)動態(tài)單元格更改而更改的布局部分。
//一個無效上下文拦宣,其中包含關(guān)于需要對布局進行哪些更改的信息尚猿。
//此方法的默認實現(xiàn)創(chuàng)建一個由invalidationContextClass類方法提供的類實例并返回它冲粤。
//如果你想在你的布局中使用一個自定義的無效上下文對象某弦,
//總是重寫這個方法并返回你的自定義類危纫。
//子類可以重寫此方法财破,并在返回該方法之前使用它執(zhí)行無效上下文的附加配置掰派。
//在自定義實現(xiàn)中,調(diào)用super左痢,以便父類可以執(zhí)行對象的基本配置靡羡。
- (UICollectionViewLayoutInvalidationContext *)invalidationContextForPreferredLayoutAttributes:(UICollectionViewLayoutAttributes *)preferredAttributes
withOriginalAttributes:(UICollectionViewLayoutAttributes *)originalAttributes;
//檢索一個上下文對象,該對象標識在布局中以交互方式移動的項俊性。
//一個無效上下文略步,其中包括有關(guān)需要對布局進行哪些更改的信息。
//當一個或多個項目的交互移動正在進行時定页,布局對象使用此方法檢索無效上下文趟薄。
//默認實現(xiàn)創(chuàng)建invalidationContextClass類方法提供的類的實例,
//用提供的信息填充它典徊,并返回它杭煎。
//如果你想在你的布局中使用一個自定義的無效上下文對象,
//總是重寫這個方法并返回你的自定義類卒落。
//子類可以重寫此方法羡铲,并在返回該方法之前使用它執(zhí)行無效上下文的附加配置。
//在自定義實現(xiàn)中儡毕,調(diào)用super也切,以便父類可以執(zhí)行對象的基本配置。
//targetIndexPaths(目標索引路徑): 正在移動的項的當前位置。
//targetPosition(目標位置) : 集合視圖坐標系中的點雷恃,它是項目的潛在放置點疆股。
//previousIndexPaths(以前的索引路徑): 正在移動的項的先前位置。
//previousPosition( 先前位置 ): 集合視圖坐標系中的前一個點褂萧。
//這是以前用于確定項目的投放點的點押桃。
- (UICollectionViewLayoutInvalidationContext *)invalidationContextForInteractivelyMovingItems:(NSArray<NSIndexPath *> *)targetIndexPaths
withTargetPosition:(CGPoint)targetPosition
previousIndexPaths:(NSArray<NSIndexPath *> *)previousIndexPaths
previousPosition:(CGPoint)previousPosition;
// 檢索一個上下文對象,該對象標識已移動的項
//一個無效上下文导犹,其中包含關(guān)于需要對布局進行哪些更改的信息唱凯。
//當一個或多個項目的交互移動(因為移動成功或因為用戶取消)結(jié)束時,
//布局對象使用此方法檢索無效上下文谎痢。
//默認實現(xiàn)創(chuàng)建invalidationContextClass類方法提供的類的實例磕昼,
//用提供的信息填充它,并返回它节猿。
//如果你想在你的布局中使用一個自定義的無效上下文對象票从,
//總是重寫這個方法并返回你的自定義類。
//子類可以重寫此方法滨嘱,并在返回該方法之前使用它執(zhí)行無效上下文的附加配置峰鄙。
//在自定義實現(xiàn)中,調(diào)用super太雨,以便父類可以執(zhí)行對象的基本配置吟榴。
- (UICollectionViewLayoutInvalidationContext *)invalidationContextForEndingInteractiveMovementOfItemsToFinalIndexPaths:(NSArray<NSIndexPath *> *)indexPaths
previousIndexPaths:(NSArray<NSIndexPath *> *)previousIndexPaths
movementCancelled:(BOOL)movementCancelled;
6、協(xié)調(diào)動畫變化的方法:
#pragma mark ------- Coordinating animated changes
//為視圖邊界的動畫更改或項的插入或刪除準備布局對象囊扳。
//集合視圖在對視圖的邊界執(zhí)行任何動畫更改之前吩翻,
//或者在動畫插入或刪除項之前調(diào)用此方法。
//這個方法是布局對象執(zhí)行任何計算的機會锥咸,為這些動畫變化做準備狭瞎。
//具體來說,可以使用此方法計算插入或刪除項的初始或最終位置搏予,
//以便在請求時返回這些值熊锭。
//您還可以使用此方法來執(zhí)行其他動畫。
//您所創(chuàng)建的任何動畫都將添加到用于處理插入雪侥、刪除和邊界更改的動畫塊中球涛。
- (void)prepareForAnimatedBoundsChange:(CGRect)oldBounds;
//在對視圖的邊界進行任何動畫更改之后或在插入或刪除項之后清理。
//集合視圖在創(chuàng)建用于更改視圖邊界的動畫之后校镐,
//或者在動畫插入或刪除項之后調(diào)用此方法亿扁。
//該方法是布局對象執(zhí)行與這些操作相關(guān)的任何清理的機會。
//您還可以使用此方法來執(zhí)行其他動畫鸟廓。
//您所創(chuàng)建的任何動畫都將添加到用于處理插入从祝、刪除和邊界更改的動畫塊中襟己。
- (void)finalizeAnimatedBoundsChange;
7、在布局之間轉(zhuǎn)換的方法:
#pragma mark ------- Transitioning between layouts
//告訴布局對象準備安裝為集合視圖的布局牍陌。
//在執(zhí)行布局轉(zhuǎn)換之前擎浴,集合視圖調(diào)用此方法,
//以便布局對象可以執(zhí)行生成布局屬性所需的任何初始計算毒涧。
- (void)prepareForTransitionFromLayout:(UICollectionViewLayout *)oldLayout;
//告訴布局對象它將作為集合視圖的布局被刪除贮预。
//在執(zhí)行布局轉(zhuǎn)換之前,集合視圖調(diào)用此方法契讲,
//以便布局對象可以執(zhí)行生成布局屬性所需的任何初始計算仿吞。
- (void)prepareForTransitionToLayout:(UICollectionViewLayout *)newLayout;
//告訴布局對象在轉(zhuǎn)換動畫發(fā)生之前執(zhí)行任何最后步驟。
//集合視圖在收集了執(zhí)行從一個布局轉(zhuǎn)換到另一個布局所需的所有布局屬性后調(diào)用此方法捡偏。
//你可以使用這個方法來清理你的prepareForTransitionFromLayout:
//或prepareForTransitionToLayout:方法的實現(xiàn)所創(chuàng)建的任何數(shù)據(jù)結(jié)構(gòu)或緩存唤冈。
- (void)finalizeLayoutTransition;
8、注冊裝飾視圖的方法:
#pragma mark ------- Registering decoration views
// 注冊一個類银伟,用于為集合視圖創(chuàng)建裝飾視圖你虹。
//該方法使布局對象有機會注冊一個裝飾視圖,以便在集合視圖中使用彤避。
//裝飾視圖為部分或整個集合視圖提供視覺裝飾,但不綁定到集合視圖數(shù)據(jù)源提供的數(shù)據(jù)傅物。
//您不需要顯式地創(chuàng)建裝飾視圖。
//注冊一個后琉预,就由布局對象來決定何時需要裝飾視圖董饰,
//并從其layoutAttributesForElementsInRect:方法中返回相應的布局屬性。
//對于指定裝飾視圖的布局屬性模孩,集合視圖創(chuàng)建(或重用)一個視圖,
//并根據(jù)注冊的信息自動顯示它贮缅。
//如果您之前注冊了具有相同類型字符串的類或nib文件榨咐,
//則在viewClass參數(shù)中指定的類將替換舊的條目。
//如果你想取消裝飾視圖的注冊谴供,你可以為viewClass指定nil块茁。
- (void)registerClass:(Class)viewClass
forDecorationViewOfKind:(NSString *)elementKind;
//注冊一個nib文件,用于為集合視圖創(chuàng)建裝飾視圖桂肌。
//該方法使布局對象有機會注冊一個裝飾視圖数焊,以便在集合視圖中使用。
//裝飾視圖為部分或整個集合視圖提供視覺裝飾,但不綁定到集合視圖數(shù)據(jù)源提供的數(shù)據(jù)崎场。
//您不需要顯式地創(chuàng)建裝飾視圖佩耳。
//注冊一個后,就由布局對象來決定何時需要裝飾視圖谭跨,
//并從其layoutAttributesForElementsInRect:方法中返回相應的布局屬性干厚。
//對于指定裝飾視圖的布局屬性李滴,集合視圖創(chuàng)建(或重用)一個視圖,
//并根據(jù)注冊的信息自動顯示它蛮瞄。
//如果您之前注冊了具有相同類型字符串的類或nib文件所坯,
//則在viewClass參數(shù)中指定的類將替換舊的條目。
//如果你想取消裝飾視圖的注冊挂捅,你可以為viewClass指定nil芹助。
- (void)registerNib:(UINib *)nib
forDecorationViewOfKind:(NSString *)elementKind;
9、支持從右向左布局的方法:
#pragma mark ------- Supporting right-to-left layouts
// 設計自定義布局時使用的語言方向闲先。
//此屬性的默認值是與主包的開發(fā)區(qū)域相關(guān)聯(lián)的語言使用的布局方向状土。
//子類可以重寫此屬性并返回不同的值。
@property(nonatomic, readonly) UIUserInterfaceLayoutDirection developmentLayoutDirection;
//一個布爾值饵蒂,指示是否在適當?shù)臅r間自動翻轉(zhuǎn)水平坐標系統(tǒng)声诸。
//開發(fā)過程中使用的語言自然會影響您在配置布局對象時所做的決策。
//當您使用從左到右的語言進行開發(fā)時退盯,
//您的布局信息將自動匹配集合視圖的自然坐標系統(tǒng)彼乌。
//然而,當用戶的語言具有從右到左的方向時渊迁,
//您提供的布局信息仍然基于集合視圖的自然坐標系統(tǒng)慰照。
//對于使用相反方向的語言,這種差異可能會導致布局問題琉朽。
//當此屬性設置為YES時毒租,集合視圖自動翻轉(zhuǎn)其水平坐標系統(tǒng)的方向,以匹配當前語言的前沿箱叁。
//(developlayoutdirection屬性指定用于設計布局的布局方向墅垮。)
//翻轉(zhuǎn)水平坐標系統(tǒng)可以有效地翻轉(zhuǎn)現(xiàn)有的布局信息,這應該會產(chǎn)生更好看的布局耕漱。
//該屬性的默認值為NO算色。
@property(nonatomic, readonly) BOOL flipsHorizontallyInOppositeLayoutDirection;
Methods to override 要覆蓋的方法
每個布局對象都應該實現(xiàn)以下方法:
//子類必須重寫此屬性,并使用它返回UICollectionView內(nèi)容的寬度和高度螟够。
//這些值表示所有內(nèi)容的寬度和高度灾梦,而不僅僅是當前可見的內(nèi)容。
//UICollectionView使用此信息來配置自己的內(nèi)容大小妓笙,以便于滾動若河。
// 此方法的默認實現(xiàn)返回CGSizeZero。
@property(nonatomic, readonly) CGSize collectionViewContentSize;
//子類必須重寫此方法寞宫,并使用它返回視圖與指定矩形相交的所有項的布局信息萧福。
//您的實現(xiàn)應該返回所有視覺元素的屬性,包括單元格辈赋、補充視圖和裝飾視圖统锤。
//創(chuàng)建布局屬性時毛俏,始終創(chuàng)建表示正確元素類型(單元格、補充或裝飾)的屬性對象饲窿。
//集合視圖區(qū)分每種類型的屬性煌寇,并使用這些信息來決定創(chuàng)建哪些視圖以及如何管理它們。
//返回指定矩形中所有單元格和視圖的布局屬性逾雄。
//rect 包含目標視圖的矩形(在集合視圖的坐標系統(tǒng)中指定)阀溶。
//返回的是UICollectionViewLayoutAttributes對象的數(shù)組,
//表示單元格和視圖的布局信息鸦泳。默認實現(xiàn)返回nil银锻。
-(NSArray<UICollectionViewLayoutAttributes *> *)layoutAttributesForElementsInRect:(CGRect)rect;
//檢索具有相應單元格的指定索引路徑上的item的布局信息。
// 返回一個布局屬性對象做鹰,包含要應用于項目單元格的信息击纬。
//子類必須重寫此方法,并使用它返回集合視圖中項目的布局信息钾麸。
//使用此方法僅為具有相應單元格的項提供布局信息更振。
//請不要將這個方法用于補充視圖或裝飾視圖!饭尝!
-(UICollectionViewLayoutAttributes *)
layoutAttributesForItemAtIndexPath:(NSIndexPath *)indexPath;
//檢索指定補充視圖的布局屬性肯腕。
//一個布局屬性對象,包含應用到補充視圖的信息钥平。
//如果布局對象定義了任何補充視圖实撒,則必須重寫此方法并使用它返回這些視圖的布局信息。
//elementKind 標識補充視圖類型的字符串涉瘾。
//indexPath 視圖的索引路徑.
- (UICollectionViewLayoutAttributes *)layoutAttributesForSupplementaryViewOfKind:(NSString *)elementKind
atIndexPath:(NSIndexPath *)indexPath;
//檢索指定裝飾視圖(Decoration View)的布局屬性.
// 布局屬性對象知态,包含要應用于裝飾視圖的信息。
//如果布局對象定義了任何裝飾視圖立叛,則必須重寫此方法并使用它來返回這些視圖的布局信息负敏。
//elementKind 標識 裝飾視圖(Decoration View)類型的字符串。
//indexPath 視圖的索引路徑.
- (UICollectionViewLayoutAttributes *)layoutAttributesForDecorationViewOfKind:(NSString*)elementKind
atIndexPath:(NSIndexPath *)indexPath;
// 詢問布局對象新的邊界是否需要布局更新囚巴。
//如果集合視圖需要更新布局原在,則為YES;如果布局不需要更改友扰,則為NO彤叉。
//此方法的默認實現(xiàn)返回NO。子類可以覆蓋它村怪,
//并根據(jù)集合視圖邊界的更改是否需要更改單元格和補充視圖的布局來返回適當?shù)闹怠?//如果集合視圖的邊界發(fā)生了變化并且該方法返回YES秽浇,
//集合視圖將通過調(diào)用invalidatelayoutithcontext:方法使布局失效。
- (BOOL)shouldInvalidateLayoutForBoundsChange:(CGRect)newBounds;
這些方法提供了集合視圖在屏幕上放置內(nèi)容所需的基本布局信息甚负。如果你的布局不支持補充視圖或裝飾視圖柬焕,就不要實現(xiàn)相應的方法审残。
當集合視圖中的數(shù)據(jù)發(fā)生變化,要插入或刪除項時斑举,集合視圖要求其布局對象更新布局信息搅轿。具體來說,任何移動富玷、添加或刪除的項都必須更新其布局信息璧坟,以反映其新位置。對于移動的項赎懦,集合視圖使用標準方法檢索項的更新布局屬性雀鹃。對于插入或刪除的項,集合視圖調(diào)用一些不同的方法励两,你應該覆蓋這些方法來提供適當?shù)牟季中畔?
//檢索插入到集合視圖中的項的起始布局信息黎茎。
//一個布局屬性對象,用于描述要放置相應單元格的位置当悔。
//該方法在prepareForCollectionViewUpdates方法之后和
//finalizeCollectionViewUpdates方法之前被調(diào)用傅瞻,用于即將插入的任何項。
//您的實現(xiàn)應該返回描述該項的初始位置和狀態(tài)的布局信息先鱼。
//集合視圖使用此信息作為任何動畫的起點俭正。(動畫的終點是項目在集合視圖中的新位置。)
//如果返回nil焙畔,布局對象將使用項目的final屬性作為動畫的起點和終點掸读。
//此方法的默認實現(xiàn)將返回nil。
- (UICollectionViewLayoutAttributes *)initialLayoutAttributesForAppearingItemAtIndexPath:(NSIndexPath *)itemIndexPath;
//檢索即將從集合視圖中刪除的項的最終布局信息宏多。
//一個布局屬性對象儿惫,描述要用作動畫刪除單元格的終點的單元格的位置。
//該方法在prepareForCollectionViewUpdates方法之后和
//finalizeCollectionViewUpdates方法之前被調(diào)用伸但,用于將要刪除的任何項肾请。
//您的實現(xiàn)應該返回描述該項的最終位置和狀態(tài)的布局信息。
//集合視圖使用此信息作為任何動畫的結(jié)束點更胖。(動畫的起點是物品的當前位置铛铁。)
//如果你返回nil,布局對象對動畫的開始點和結(jié)束點使用相同的屬性却妨。
//此方法的默認實現(xiàn)將返回nil饵逐。
- (UICollectionViewLayoutAttributes *)finalLayoutAttributesForDisappearingItemAtIndexPath:(NSIndexPath *)itemIndexPath;
//檢索插入到集合視圖中的補充視圖的起始布局信息。
//一個布局屬性對象彪标,它描述放置相應補充視圖的位置倍权。
//該方法在prepareForCollectionViewUpdates方法之后和
//finalizeCollectionViewUpdates方法之前被調(diào)用,用于即將插入的任何補充視圖捞烟。
//您的實現(xiàn)應該返回描述視圖初始位置和狀態(tài)的布局信息薄声。
//集合視圖使用這些信息作為任何動畫的起點当船。(動畫的結(jié)束點是視圖在集合視圖中的新位置.)
//如果你返回nil,布局對象使用項目的final屬性作為動畫的開始點和結(jié)束點默辨。
//此方法的默認實現(xiàn)將返回nil德频。
- (UICollectionViewLayoutAttributes *)initialLayoutAttributesForAppearingSupplementaryElementOfKind:(NSString *)elementKind atIndexPath:(NSIndexPath *)elementIndexPath;
//檢索即將從集合視圖中刪除的補充視圖的最終布局信息。
//一個布局屬性對象缩幸,用于描述補充視圖的位置抱婉,以作為動畫刪除的結(jié)束點。
//這個方法在prepareForCollectionViewUpdates方法之后和
//finalizeCollectionViewUpdates方法之前被調(diào)用桌粉,用于將要刪除的任何補充視圖蒸绩。
//您的實現(xiàn)應該返回描述視圖的最終位置和狀態(tài)的布局信息。
//集合視圖使用此信息作為任何動畫的結(jié)束點铃肯。(動畫的起點是視圖的當前位置患亿。)
//如果你返回nil,布局對象對動畫的開始點和結(jié)束點使用相同的屬性押逼。
//此方法的默認實現(xiàn)將返回nil步藕。
- (nullable UICollectionViewLayoutAttributes *)finalLayoutAttributesForDisappearingSupplementaryElementOfKind:(NSString *)elementKind atIndexPath:(NSIndexPath *)elementIndexPath;
// 檢索要插入到集合視圖中的裝飾視圖的起始布局信息。
// 布局屬性對象挑格,用于描述放置相應裝飾視圖的位置咙冗。
//這個方法在prepareForCollectionViewUpdates方法之后和
//finalizeCollectionViewUpdates方法之前被調(diào)用,用于任何即將插入的裝飾視圖漂彤。
//您的實現(xiàn)應該返回描述視圖初始位置和狀態(tài)的布局信息雾消。
//集合視圖使用這些信息作為任何動畫的起點。(動畫的結(jié)束點是視圖在集合視圖中的新位置挫望。)
//如果你返回nil立润,布局對象使用項目的final屬性作為動畫的開始點和結(jié)束點。
//此方法的默認實現(xiàn)將返回nil媳板。
- (nullable UICollectionViewLayoutAttributes *)initialLayoutAttributesForAppearingDecorationElementOfKind:(NSString *)elementKind atIndexPath:(NSIndexPath *)decorationIndexPath;
//檢索即將從集合視圖中移除的裝飾視圖的最終布局信息桑腮。
//一個布局屬性對象,它描述裝飾視圖的位置蛉幸,用于動畫化其移除破讨。
//這個方法在prepareForCollectionViewUpdates方法之后和
//finalizeCollectionViewUpdates方法之前被調(diào)用,用于任何即將被刪除的裝飾視圖奕纫。
//您的實現(xiàn)應該返回描述視圖的最終位置和狀態(tài)的布局信息提陶。
//集合視圖使用此信息作為任何動畫的結(jié)束點。(動畫的起點是視圖的當前位置若锁。)
//如果你返回nil搁骑,布局對象對動畫的開始點和結(jié)束點使用相同的屬性斧吐。
//此方法的默認實現(xiàn)將返回nil又固。
- (nullable UICollectionViewLayoutAttributes *)finalLayoutAttributesForDisappearingDecorationElementOfKind:(NSString *)elementKind atIndexPath:(NSIndexPath *)decorationIndexPath;
除了這些方法之外仲器,您還可以重寫prepareForCollectionViewUpdates:來處理 任何與布局相關(guān)的準備工作。您也可以覆蓋 [finalizeCollectionViewUpdates[() 方法仰冠,并使用它將動畫添加到整個動畫塊中乏冀,或?qū)崿F(xiàn)任何與最終布局相關(guān)的任務。
//通知布局對象集合視圖的內(nèi)容即將更改
//插入或刪除項目時洋只,集合視圖會通知其布局對象辆沦,以便根據(jù)需要調(diào)整布局。
//這個過程的第一步是調(diào)用這個方法识虚,讓布局對象知道預期會發(fā)生什么變化肢扯。之后,
//將進行其他調(diào)用担锤,以收集將在集合視圖周圍設置動畫的插入蔚晨、刪除和移動項目的布局信息。
//updateItems 標識正在進行的更改的UICollectionViewUpdateItem對象數(shù)組肛循。
- (void)prepareForCollectionViewUpdates:(NSArray<UICollectionViewUpdateItem *> *)updateItems;
//執(zhí)行在集合視圖更新期間所需的任何其他動畫或清理铭腕。
//集合視圖調(diào)用此方法作為將任何更改動畫化之前的最后一步。
//此方法在用于執(zhí)行所有插入多糠、刪除和移動動畫的動畫塊中調(diào)用累舷,
//因此您可以根據(jù)需要使用此方法創(chuàng)建其他動畫。
//否則夹孔,您可以使用它來執(zhí)行與管理布局對象的狀態(tài)信息相關(guān)的任何最后一分鐘的任務被盈。
- (void)finalizeCollectionViewUpdates;
使用失效上下文優(yōu)化布局性能
在設計自定義布局時,您可以通過僅使布局中實際更改的部分無效來提高性能搭伤。當您更改項時害捕,調(diào)用invalidateLayout方法將強制集合視圖重新計算其所有布局信息并重新應用它。更好的解決方案是只重新計算更改的布局信息闷畸,這正是無效上下文允許您做的事情尝盼。無效上下文允許您指定布局的哪些部分被更改。然后佑菩,布局對象可以使用該信息來最小化它重新計算的數(shù)據(jù)量盾沫。
要為你的布局定義一個自定義的無效上下文,子類化UICollectionViewLayoutInvalidationContext類殿漠。在子類中赴精,定義自定義屬性,這些屬性表示布局數(shù)據(jù)中可以獨立重新計算的部分绞幌。當你需要在運行時使布局失效時蕾哟,創(chuàng)建一個invalidation context子類的實例,根據(jù)布局信息的變化配置自定義屬性,并將該對象傳遞給布局的invalidateLayoutWithContext:
方法谭确。該方法的自定義實現(xiàn)可以使用失效上下文中的信息僅重新計算已更改的布局部分帘营。
如果你為你的布局對象定義了一個自定義的無效上下文類,你也應該重寫invalidationContextClass 方法并返回你的自定義類逐哈。當集合視圖需要無效上下文時芬迄,它總是創(chuàng)建您指定的類的實例。從此方法返回您的自定義子類昂秃,確保您的布局對象始終具有它所期望的無效上下文禀梳。
UICollectionViewLayoutAttributes (布局屬性)
#pragma mark -----訪問布局屬性
@property (nonatomic) CGRect frame;
@property (nonatomic) CGRect bounds;
@property (nonatomic) CGPoint center;
@property (nonatomic) CGSize size;
//項目的三維變換。
@property (nonatomic) CATransform3D transform3D;
//項目的仿射變換肠骆。
@property (nonatomic) CGAffineTransform transform;
@property (nonatomic) CGFloat alpha;
// 指定項目在z軸上的位置算途。 默認值為0
@property (nonatomic) NSInteger zIndex;
//作為優(yōu)化,UICollectionView可能不會為隱藏屬性為YES的項創(chuàng)建視圖
@property (nonatomic, getter=isHidden) BOOL hidden;
#pragma mark -----識別被引用的項目
@property (nonatomic, strong) NSIndexPath *indexPath;
//項目的類型蚀腿。
//可以使用此屬性中的值來區(qū)分布局屬性是用于單元格郊艘、補充視圖還是裝飾視圖。
@property (nonatomic, readonly) UICollectionElementCategory representedElementCategory;
//目標視圖的特定布局標識符唯咬。
//您可以使用此屬性中的值來標識與屬性關(guān)聯(lián)的補充視圖或裝飾視圖的特定用途纱注。
//如果representtedelementcategory屬性包含值UICollectionElementCategoryCell,
//則此屬性為nil胆胰。
@property (nonatomic, readonly, nullable) NSString *representedElementKind;
#pragma mark -----創(chuàng)建布局屬性
//使用此方法可在集合視圖中為單元格創(chuàng)建布局屬性對象狞贱。
+ (instancetype)layoutAttributesForCellWithIndexPath:(NSIndexPath *)indexPath;
//使用此方法為集合視圖中的補充視圖創(chuàng)建布局屬性對象。
//與單元格一樣蜀涨,補充視圖表示由集合視圖的數(shù)據(jù)源管理的數(shù)據(jù)瞎嬉。
//但與單元格不同的是,補充視圖通常是為特殊目的而設計的厚柳。
//例如氧枣,頁眉和頁腳視圖的布局與單元格不同,可以為單個部分提供别垮,
//也可以為整個集合視圖提供便监。
//由您決定如何使用indexPath參數(shù)來標識給定的補充視圖。
//通常碳想,使用elementKind參數(shù)來標識補充視圖的類型烧董,
//使用indexPath信息來區(qū)分該視圖的不同實例。
+ (instancetype)layoutAttributesForSupplementaryViewOfKind:(NSString *)elementKind withIndexPath:(NSIndexPath *)indexPath;
//使用此方法為集合視圖中的裝飾視圖創(chuàng)建一個布局屬性對象胧奔。
//裝飾視圖是一種補充視圖逊移,但不顯示集合視圖數(shù)據(jù)源管理的數(shù)據(jù)。
//相反龙填,它們主要為一個部分或整個集合視圖提供視覺裝飾胳泉。
//由您決定如何使用indexPath參數(shù)來標識給定的裝飾視圖拐叉。
//通常,使用decorationViewKind參數(shù)來標識裝飾視圖的類型扇商,
//使用indexPath信息來區(qū)分該視圖的不同實例凤瘦。
+ (instancetype)layoutAttributesForDecorationViewOfKind:(NSString *)decorationViewKind withIndexPath:(NSIndexPath *)indexPath;
UICollectionViewUpdateItem
UICollectionViewUpdateItem 描述對集合視圖中的項所做的單個更改的對象。
您不必直接創(chuàng)建該類的實例钳吟。當更新其內(nèi)容時,集合視圖對象創(chuàng)建它們并將它們傳遞給布局對象的prepareForCollectionViewUpdates:方法窘拯,該方法可以使用它們?yōu)榧磳⒌絹淼母臏蕚洳季謱ο蟆?/p>
typedef NS_ENUM(NSInteger, UICollectionUpdateAction) {
UICollectionUpdateActionInsert,
UICollectionUpdateActionDelete,
UICollectionUpdateActionReload,
UICollectionUpdateActionMove,
UICollectionUpdateActionNone
};
//更新之前項的索引路徑红且。
//nil用于UICollectionUpdateActionInsert
@property (nonatomic, readonly, nullable) NSIndexPath *indexPathBeforeUpdate;
// 更新后項的索引路徑。
//nil用于UICollectionUpdateActionDelete
@property (nonatomic, readonly, nullable) NSIndexPath *indexPathAfterUpdate;
//正在對項目執(zhí)行的操作涤姊。
@property (nonatomic, readonly) UICollectionUpdateAction updateAction;
UICollectionViewLayoutInvalidationContext 上下文對象
一個上下文對象暇番,聲明當布局失效時需要更新布局的哪些部分。
為支持無效上下文而設計的布局對象可以使用UICollectionViewLayoutInvalidationContext對象中的信息來優(yōu)化它們在無效周期中的行為思喊。您可以創(chuàng)建一個無效上下文對象壁酬,作為使布局對象無效的前導。在配置了無效上下文對象之后恨课,將其傳遞給布局對象的invalidatelayoutithcontext:方法舆乔,該方法負責使用上下文對象有效地更新布局。集合視圖還創(chuàng)建無效上下文以響應特定的更改剂公。例如希俩,當您更改布局或數(shù)據(jù)源對象、插入或刪除項以及調(diào)用reloadData方法時纲辽,它會創(chuàng)建一個無效上下文颜武。
如果你創(chuàng)建自己的自定義布局對象,你可以子類化UICollectionViewLayoutInvalidationContext拖吼,并添加屬性來指定布局數(shù)據(jù)的哪些方面可以單獨失效鳞上。然后,必須設計布局對象以檢查這些屬性并適當?shù)馗虏季?/strong>吊档。
有關(guān)如何在布局對象中支持自定義失效上下文的更多信息篙议,請參見UICollectionViewLayout
#pragma mark -----使集合視圖數(shù)據(jù)無效
//一個布爾值,指示所有布局數(shù)據(jù)都應標記為無效怠硼。
//您不必自己設置此屬性涡上。
//集合視圖將其設置為響應特定類型的布局失效場景。
//例如拒名,當您更改當前布局對象吩愧、更改集合視圖的數(shù)據(jù)源
//或調(diào)用reloadData方法并隨后請求布局失效上下文時,
//集合視圖將其設置為YES增显。
//如果此屬性設置為YES雁佳,布局對象應該重新計算所有與布局相關(guān)的數(shù)據(jù)脐帝。
@property (nonatomic, readonly) BOOL invalidateEverything;
//一個布爾值,指示布局是否應請求新的section和item計數(shù)糖权。
//您不必自己設置此屬性堵腹。集合視圖將其設置為響應特定類型的布局失效場景。
//例如星澳,當您插入或刪除項或調(diào)用集合視圖的reloadData方法時疚顷,
//集合視圖將其設置為YES。
//如果此屬性設置為YES禁偎,布局對象應該查詢它的委托以獲得部分和項的數(shù)量腿堤,
//并根據(jù)新的項的數(shù)量更新其布局。
@property (nonatomic, readonly) BOOL invalidateDataSourceCounts;
#pragma mark -----使內(nèi)容區(qū)無效
//要應用于集合視圖的內(nèi)容偏移量的增量值如暖。
//使用此屬性可更新集合視圖的內(nèi)容偏移量笆檀。
//此屬性的默認值是CGPointZero。
//更改該值會導致集合視圖將指定的x和y值添加到其contenttoffset屬性中。
//因此,正值增加內(nèi)容偏移量但惶,負值減少內(nèi)容偏移量。
@property (nonatomic) CGPoint contentOffsetAdjustment;
//要應用于集合視圖的內(nèi)容大小的增量值樱衷。
//使用此屬性可更新集合視圖內(nèi)容區(qū)域的大小。
//該屬性的默認值是CGSizeZero酒唉。
//更改該值會導致集合視圖將指定的高度和寬度值添加到其contentSize屬性中箫老。
//因此,正值使內(nèi)容面積增大黔州,負值使內(nèi)容面積縮小耍鬓。
@property (nonatomic) CGSize contentSizeAdjustment;
#pragma mark -----使特定項目無效
//將位于指定索引路徑的單元格添加到無效項列表。
//調(diào)用此方法可識別需要更新的布局中的特定單元格流妻。
//您指定的單元格將在invalidatedItemIndexPaths屬性中添加到數(shù)組中牲蜀。
- (void)invalidateItemsAtIndexPaths:(NSArray<NSIndexPath *> *)indexPaths ;
//將指定索引路徑處的補充視圖添加到無效項列表。
//調(diào)用此方法來識別需要更新的布局的特定補充視圖绅这。
//您指定的視圖將在invalidatedcomplementary indexpaths屬性中添加到字典中涣达。
//您指定的所有視圖都應該是您在elementKind參數(shù)中指定的類型。
//如果使用相同的elementKind參數(shù)值調(diào)用此方法兩次或多次证薇,
//則該方法將新的索引路徑與先前指定的索引路徑合并度苔。
- (void)invalidateSupplementaryElementsOfKind:(NSString *)elementKind atIndexPaths:(NSArray<NSIndexPath *> *)indexPaths;
//將指定索引路徑處的裝飾視圖添加到無效項列表。
//調(diào)用此方法來識別布局屬性發(fā)生變化的特定裝飾視圖浑度。
//您指定的視圖將在invalidatedDecorationIndexPaths屬性中添加到字典中寇窑。
//您指定的所有視圖都應該是您在elementKind參數(shù)中指定的類型。//如果使用相同的elementKind參數(shù)值調(diào)用此方法兩次或多次箩张,
//則該方法將新的索引路徑與先前指定的索引路徑合并甩骏。
- (void)invalidateDecorationElementsOfKind:(NSString *)elementKind atIndexPaths:(NSArray<NSIndexPath *> *)indexPaths;
//表示無效單元格的索引路徑數(shù)組窗市。
//數(shù)組包含零個或多個NSIndexPath對象,每個NSIndexPath對象表示一個布局改變的單元格饮笛。
@property (nonatomic, readonly, nullable) NSArray<NSIndexPath *> *invalidatedItemIndexPaths;
//標識已失效的補充視圖的字典咨察。
//這個字典中的鍵是無效補充視圖的元素類型字符串。
//每個鍵的值是一個NSIndexPath對象數(shù)組福青,表示哪些特定的補充視圖有布局更改摄狱。
@property (nonatomic, readonly, nullable) NSDictionary<NSString *, NSArray<NSIndexPath *> *> *invalidatedSupplementaryIndexPaths;
//標識無效裝飾視圖的字典。
//這個字典中的鍵是無效裝飾視圖的元素類型字符串无午。
//每個鍵的值是一個NSIndexPath對象數(shù)組媒役,表示哪些特定的裝飾視圖有布局變化。
@property (nonatomic, readonly, nullable) NSDictionary<NSString *, NSArray<NSIndexPath *> *> *invalidatedDecorationIndexPaths;
#pragma mark -----無效項目的順序
//索引路徑數(shù)組指厌,表示集合視圖中移動項的先前位置刊愚。
//當交互移動正在進行或剛剛結(jié)束時踊跟,此屬性將被填充踩验。
//將此屬性與targetIndexPathsForInteractivelyMovingItems屬性一起使用,
//以確定需要對受影響的項進行哪些更改商玫。對于大多數(shù)其他更新箕憾,此屬性的值為nil。
@property (nonatomic, readonly, copy, nullable) NSArray<NSIndexPath *> *previousIndexPathsForInteractivelyMovingItems;
//索引路徑數(shù)組拳昌,表示集合視圖中移動項的新位置袭异。
//當交互移動正在進行或剛剛結(jié)束時,此屬性將被填充炬藤。
//將此屬性與previousIndexPathsForInteractivelyMovingItems屬性一起使用御铃,
//以確定需要對受影響的項進行哪些更改。對于大多數(shù)其他更新沈矿,此屬性的值為nil上真。
@property (nonatomic, readonly, copy, nullable) NSArray<NSIndexPath *> *targetIndexPathsForInteractivelyMovingItems;
//用于確定移動項目位置的當前點。
//當交互移動正在進行或剛剛結(jié)束時羹膳,此屬性將被填充睡互。該值表示用于確定
//targetIndexPathsForInteractivelyMovingItems屬性中的新索引路徑的點。
//您可以根據(jù)需要使用這個點來計算項目在布局中的位置陵像。
@property (nonatomic, readonly) CGPoint interactiveMovementTarget;
七就珠、 UICollectionViewFlowLayout 流布局
UICollectionViewFlowLayout 繼承 UICollectionViewLayout
1、配置滾動方向
//這個屬性的默認值是UICollectionViewScrollDirectionVertical醒颖。
@property(nonatomic) UICollectionViewScrollDirection scrollDirection;
2妻怎、配置item間距
//minimumLineSpacing 最小行距
@property (nonatomic) CGFloat minimumLineSpacing;
//minimumInteritemSpacing 在同一行的 item 之間的最小間距
//兩個item之間的最小列距
@property (nonatomic) CGFloat minimumInteritemSpacing;
//如果委托未實現(xiàn)collectionView:layout:sizeForItemAtIndexPath:方法,
//則流布局將使用此屬性中的值來設置每個單元格的大小泞歉。
//這導致所有單元格都具有相同的大小蹂季。
@property (nonatomic) CGSize itemSize;
//當單元格動態(tài)調(diào)整其大小時冕广,提供估計的單元格大小可以提高集合視圖的性能。
//估計值讓集合視圖推遲一些計算偿洁,以確定其內(nèi)容的實際大小撒汉。
//不在屏幕上的單元格被假定為估計高度。
//該屬性的默認值是CGSizeZero涕滋。將其設置為任何其他值睬辐,
//如UICollectionViewFlowLayoutAutomaticSize,會導致集合視圖使用
//單元格的preferredLayoutAttributesFittingAttributes:方法
//查詢每個單元格的實際大小宾肺。
//如果所有單元格大小相同溯饵,則使用itemSize屬性而不是此屬性來指定單元格大小。
@property (nonatomic) CGSize estimatedItemSize;
@property (nonatomic) UICollectionViewFlowLayoutSectionInsetReference sectionInsetReference;//iOS 11.0+锨用;
@property (nonatomic) UIEdgeInsets sectionInset;
@property (nonatomic) UICollectionViewFlowLayoutSectionInsetReference sectionInsetReference;
//用于自調(diào)整單元格大小的占位符大小丰刊。
//將此常量設置為estimatedItemSize屬性的值,
//以便為您的集合視圖啟用自調(diào)整單元格大小增拥。
//這是一個非零的占位符值啄巧,它告訴集合視圖使用單元格的
//preferredLayoutAttributesFittingAttributes:方法
//查詢每個單元格的實際大小。
UIKIT_EXTERN const CGSize UICollectionViewFlowLayoutAutomaticSize API_AVAILABLE(ios(10.0));
3掌栅、配置headers 和 footers
//section headers 的默認大小秩仆。
//如果委托未實現(xiàn)collectionView:layout:referenceSizeForHeaderInSection:方法,
//流布局對象使用該屬性中設置的默認頭大小猾封。
//默認的大小值是(0,0)澄耍。
@property (nonatomic) CGSize headerReferenceSize;
//section footers的默認大小。
//如果委托未實現(xiàn)collectionView:layout:referenceSizeForFooterInSection:
方法晌缘,
//流布局對象使用該屬性中設置的默認頭大小齐莲。
//默認的大小值是(0,0)。
@property (nonatomic) CGSize footerReferenceSize;
4磷箕、固定headers 和 footers
//一個布爾值选酗,指示滾動時頭是否固定在集合視圖邊界的頂部。
//當此屬性為YES時搀捷,section headers視圖將隨內(nèi)容滾動星掰,
//直到它們到達屏幕頂部,此時它們將固定在集合視圖的上界嫩舟。
//每個滾動到屏幕頂部的新標題視圖都會將先前固定的標題視圖推到屏幕外氢烘。
//該屬性的默認值為NO。
@property (nonatomic) BOOL sectionHeadersPinToVisibleBounds;
//一個布爾值家厌,指示滾動時頁腳是否固定在集合視圖邊界的底部播玖。
//當此屬性為YES時,節(jié)頁腳視圖將隨內(nèi)容滾動饭于,
//直到它們到達屏幕底部蜀踏,此時它們將固定在集合視圖的下界维蒙。
//每個滾動到屏幕底部的新頁腳視圖都會將先前固定的頁腳視圖推到屏幕外。
//該屬性的默認值為NO果覆。
@property (nonatomic) BOOL sectionFootersPinToVisibleBounds;
UICollectionViewDelegateFlowLayout
1颅痊、獲取項目的大小
// 向delegate詢問指定項目單元格的大小。
//指定項的寬度和高度局待。兩個值都必須大于0斑响。
//如果不實現(xiàn)此方法,流布局將使用itemSize屬性中的值來設置項的大小钳榨。
//此方法的實現(xiàn)可以返回一組固定的大小舰罚,也可以根據(jù)單元格的內(nèi)容動態(tài)調(diào)整大小。
- (CGSize)collectionView:(UICollectionView *)collectionView
layout:(UICollectionViewLayout*)collectionViewLayout
sizeForItemAtIndexPath:(NSIndexPath *)indexPath;
2薛耻、獲取分區(qū)間距
- (UIEdgeInsets)collectionView:(UICollectionView *)collectionView
layout:(UICollectionViewLayout*)collectionViewLayout
insetForSectionAtIndex:(NSInteger)section;
//同一個section中相鄰兩line之間的最小距離
- (CGFloat)collectionView:(UICollectionView *)collectionView
layout:(UICollectionViewLayout*)collectionViewLayout
minimumLineSpacingForSectionAtIndex:(NSInteger)section;
//
- (CGFloat)collectionView:(UICollectionView *)collectionView
layout:(UICollectionViewLayout*)collectionViewLayout
minimumInteritemSpacingForSectionAtIndex:(NSInteger)section;
3营罢、獲取header 和 footer 大小
- (CGSize)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout*)collectionViewLayout referenceSizeForHeaderInSection:(NSInteger)section;
- (CGSize)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout*)collectionViewLayout referenceSizeForFooterInSection:(NSInteger)section;
UICollectionViewFlowLayoutInvalidationContext
流布局對象在需要使其內(nèi)容失效以響應更改時創(chuàng)建該類的實例。您還可以在手動使流布局無效時創(chuàng)建實例饼齿。
UICollectionViewFlowLayoutInvalidationContext 繼承UICollectionViewLayoutInvalidationContext
//一個布爾值饲漾,指示是否重新計算布局中項和視圖的大小。
//該屬性的默認值為NO候醒。如果由于更改任何項的大小而使布局無效能颁,
//則將此屬性設置為YES杂瘸。
//當此屬性設置為YES時倒淫,流布局對象將重新計算其項和視圖的大小,
//并根據(jù)需要查詢委托對象以獲得該信息败玉。
@property (nonatomic) BOOL invalidateFlowLayoutDelegateMetrics;
//一個布爾值敌土,指示是否重新計算布局中項和視圖的布局屬性。
//該屬性的默認值為NO运翼。如果項目在屏幕上的位置發(fā)生變化返干,則將此屬性設置為YES。
//例如血淌,當集合視圖的邊界發(fā)生影響列或行中項數(shù)的變化時矩欠,
//流布局對象將此屬性設置為YES。
//當此屬性設置為YES時悠夯,流布局對象將為其項和視圖重新計算布局屬性癌淮。
//如果invalidateFlowLayoutDelegateMetrics屬性被設置為NO,
//它將重新計算該信息而不要求新的大小信息沦补。
@property (nonatomic) BOOL invalidateFlowLayoutAttributes;