一、UICollectionView 的介绍
UICollectionViewLayout类是一个抽象类的子类化来定义自定义布局集合。定义一个自定义的布局是一种先进的复杂操作的应用程序的需求。
UICollectionViewFlowLayout 是 UICollectionViewLayout 的子类,是一个方便于处理页面布局的类。即是可以直接使用不需要其他操作。
二、 UICollectionViewFlowLayout 的创建和参数的介绍
// TODO: 一般UICollectionViewFlowLayout 的创建
func ctreateFlowLayout() -> UICollectionViewFlowLayout {
let FlowLayout = UICollectionViewFlowLayout.init()
// 最小间隔
FlowLayout.minimumLineSpacing = 1
// 临时的最小间隔
FlowLayout.minimumInteritemSpacing = 0.5
// 设置大小
FlowLayout.itemSize = CGSize.init(width: self.view.frame.width, height: 200)
// 设置 Item 的滚动方向
FlowLayout.scrollDirection = .horizontal
// 设置 UICollectionView 的headerView 和 footerView 的大小
FlowLayout.headerReferenceSize = CGSize.zero
FlowLayout.footerReferenceSize = CGSize.zero
// 设置 UICollectionView 的Section 的偏移
FlowLayout.sectionInset = UIEdgeInsets.zero
// 设置 UICollectionView 的 headerView 和 footerView 能够悬浮在屏幕的顶部
FlowLayout.sectionFootersPinToVisibleBounds = true
FlowLayout.sectionHeadersPinToVisibleBounds = true
return FlowLayout
}
三、 UICollectionView 的简单创建 和 参数的介绍使用
1> 简单的创建 UICollectionView的对象
// 创建一个 CollectionView 的对象
let collectionView = UICollectionView.init(frame: self.view.frame, collectionViewLayout: self.ctreateFlowLayout())
// 设置 CollectionView 的两个代理,分别是 UICollectionViewDelegate 和 UICollectionViewDataSource
collectionView.delegate = self
collectionView.dataSource = self
// 预加载的代理
collectionView.prefetchDataSource = self
// 进行渲染
self.view.addSubview(collectionView)
// 注册 UICollectionView 的 cell / headerView /footerView
collectionView .register(UICollectionViewCell.self, forCellWithReuseIdentifier: "cell_id")
collectionView.register(UICollectionReusableView.self, forSupplementaryViewOfKind: UICollectionElementKindSectionHeader, withReuseIdentifier: "header_id")
collectionView.register(UICollectionReusableView.self, forSupplementaryViewOfKind: UICollectionElementKindSectionFooter, withReuseIdentifier: "footer_id")
2> 参数的介绍
// 设置背景View
collectionView.backgroundView = UIView.init()
// Collection 是否允许预加载
collectionView.isPrefetchingEnabled = true
// 设置 UICollectionView 的 item 是否能够被选中
collectionView.allowsSelection = true
// 设置 UICollectionView 的item 能够多选
collectionView.allowsMultipleSelection = true
// 让 UICollectionView 自动滑动到指定Section的Item 的位置
collectionView.scrollToItem(at: IndexPath.init(row: 2, section: 2), at: .top, animated: true)
// 让 UICollectionView 自动选择指定的Item。并将选中的Item滑动到指定的位置
collectionView.selectItem(at: IndexPath.init(row: 1, section: 3), animated: true, scrollPosition: .top)
// 取消选中的item
collectionView.deselectItem(at: IndexPath.init(row: 1, section: 3), animated: true)
// UICollectionView 的整体更新数据的方法
collectionView.reloadData()
// 设置 UICollectionView 的新的布局,从一个布局到另一个布局的转变
collectionView.setCollectionViewLayout(self.ctreateFlowLayout(), animated: true)
collectionView.setCollectionViewLayout(self.ctreateFlowLayout(), animated: true) { (isFinsish) in
// 这里可以等布局完成后在做一些其他的操作
}
// 准备好动画,调用该方法开始动画对collectionView进行布局,成功后就会回调 setCollectionViewLayout:animated :{} 方法
collectionView.finishInteractiveTransition()
// 取消对collectionView布局的动画,并回调 setCollectionViewLayout:animated :{} 该方法
collectionView.cancelInteractiveTransition()
// 获取 collectionView 的整个 Section 的个数
let totalSection = collectionView.numberOfSections
print(totalSection)
// 获取 collectionView 的某一个 Section 中 item 的个数
let itemCount = collectionView.numberOfItems(inSection: 2)
print(itemCount)
// 获取 collectionView 的 Item 属性
let ItemLayoutAttributes = collectionView.layoutAttributesForItem(at: IndexPath.init(row: 1, section: 2))
// UICollectionViewLayoutAttributes 属性我们可以获取一些关于itme的属性,例如:大小、透明度、是否隐藏、IndexPath ... 等
print((ItemLayoutAttributes?.frame,ItemLayoutAttributes?.size,ItemLayoutAttributes?.indexPath,ItemLayoutAttributes?.alpha))
// 获取 collectionView 的 ReusableView 的一些属性
let ReusableViewLayoutAttributes = collectionView.layoutAttributesForSupplementaryElement(ofKind: UICollectionElementKindSectionHeader, at: IndexPath.init(item: 0, section: 2))
// UICollectionViewLayoutAttributes 属性我们可以获取一些关于ReusableView的属性,例如:大小、透明度、是否隐藏、IndexPath ... 等
print((ReusableViewLayoutAttributes?.frame,ReusableViewLayoutAttributes?.size,ReusableViewLayoutAttributes?.indexPath,ReusableViewLayoutAttributes?.alpha))
// 通过collectionView 的Item上某一点获取改 Item 的 indexPath
let point_indexPath = collectionView.indexPathForItem(at: CGPoint.init(x: 100, y: 200))
// 通过 point_indexPath 就可以知道你点击的是哪个 Section 的 item
print((point_indexPath?.row ,point_indexPath?.section))
// 通过 UICollectionViewCell 来获取 indexPath
let cell_indexPath = collectionView.indexPath(for: UICollectionViewCell.init())
// 通过 cell_indexPath 就可以知道你点击的是哪个 Section 的 item
print((cell_indexPath?.row ,cell_indexPath?.section))
// 通过indexPath 来获取 cell
let Index_cell = collectionView.cellForItem(at: IndexPath.init(row: 2, section: 2))
print(Index_cell!)
// 获取 UICollectionView 视图可见的 Cell
let AbleCells = collectionView.visibleCells
print(AbleCells)
// 获取视图上可见的 Item 的 indexPath
let Item_indexPaths = collectionView.indexPathsForVisibleItems
print(Item_indexPaths)
// 通过指定的indexPath 还获取 UICollectionView的 headerView & fotterView
let XReusableView = collectionView.supplementaryView(forElementKind: UICollectionElementKindSectionHeader, at: IndexPath.init(row: 0, section: 2))
print(XReusableView!)
// 通过给定的类型(UICollectionElementKindSectionHeader、UICollectionElementKindSectionFooter)来获取视图可见的 headerView & footerView
let XReusableViews = collectionView.visibleSupplementaryViews(ofKind: UICollectionElementKindSectionHeader)
print(XReusableViews)
// 通过给定的类型 (UICollectionElementKindSectionHeader、UICollectionElementKindSectionFooter)来获取视图可见的 indexPath
let indexPaths = collectionView.indexPathsForVisibleSupplementaryElements(ofKind: UICollectionElementKindSectionHeader)
print(indexPaths)
// MARK: UICollectionView 的Section 的增加、删除、刷新、移动
let set = NSIndexSet.init(indexesIn: NSRange.init(location: 0, length: 3))
// UICollectionView 的Section 的插入操作
collectionView.insertSections(set as IndexSet)
// UICollectionView 的Section 的删除操作
collectionView.deleteSections(set as IndexSet)
// UICollectionView 的Section 的数据刷新操作
collectionView.reloadSections(set as IndexSet)
// UICollectionView 的Section 移动到另一个新的位置
collectionView.moveSection(0, toSection: 3)
// MARK: UICollectionView 的 Item 的增加、删除、刷新、移动
// UICollectionView 的 Item 的插入操作
collectionView.insertItems(at: [IndexPath.init(row: 1, section: 1)])
// UICollectionView 的 Item 的删除操作
collectionView.deselectItem(at: IndexPath.init(row: 0, section: 1), animated: true)
// UICollectionView 的 Item 的刷新操作
collectionView.reloadItems(at: [IndexPath.init(row: 0, section: 1)])
// UICollectionView 的 Item 的移动操作
collectionView.moveItem(at: IndexPath.init(row: 0, section: 1), to: IndexPath.init(row: 0, section: 2))
// UICollectionView 的Section 或者 Item 的增加、删除、刷新、移动调用的函数
collectionView.performBatchUpdates({
// 要更新的 Layout
}) { (isFinsh) in
// 判断是否完成,再做其他事情
}
// 是否在移动的时候,对 UICollectionView 的 Item 进行排序,返回一个BOOl 值,默认情况是 true
collectionView.beginInteractiveMovementForItem(at: IndexPath.init(row: 0, section: 2))
// 更新 UICollectionView 的 Item 移动时的点(位置)
collectionView.updateInteractiveMovementTargetPosition(CGPoint.init(x: 100, y: 30))
// 移动Item到新的点
collectionView.endInteractiveMovement()
// 将item恢复到原始的点
collectionView.cancelInteractiveMovement()
四、 UICollectionView 的代理方法的介绍
1> UICollectionViewDelegate 的所有代理介绍
// MARK: UICollectionViewDelegate 的代理方法的实现
// TODO: 设置CollectionView 的 Item 是否点击Item变为高亮状态。返回结果: true 点击Item 变为高亮状态;false 点击不变为高亮状态
func collectionView(_ collectionView: UICollectionView, shouldHighlightItemAt indexPath: IndexPath) -> Bool {
return true
}
// TODO: UICollectionView 哪一个Item 被点击成为高亮状态后调用该函数
func collectionView(_ collectionView: UICollectionView, didHighlightItemAt indexPath: IndexPath) {
print("高亮" + "\(indexPath.section)" + "--" + "\(indexPath.row)")
}
// TODO: UICollectionView的Item有高亮状态变为非高亮状态时调用的函数
func collectionView(_ collectionView: UICollectionView, didUnhighlightItemAt indexPath: IndexPath) {
print("不高亮" + "\(indexPath.section)" + "--" + "\(indexPath.row)")
}
// TODO: 设置 UICollectionView 是否允许取消选中
func collectionView(_ collectionView: UICollectionView, shouldDeselectItemAt indexPath: IndexPath) -> Bool {
return true
}
// TODO: UICollectionView 的 Item 点击选中触发该方法
func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) {
print("Item 被选中")
}
// TODO: UICollectionView 的取消选中操作时调用的函数
func collectionView(_ collectionView: UICollectionView, didDeselectItemAt indexPath: IndexPath) {
}
// TODO: UICollectionViewCell 将要显示在视图上的时候调用该函数
func collectionView(_ collectionView: UICollectionView, willDisplay cell: UICollectionViewCell, forItemAt indexPath: IndexPath) {
print("将要显示的cell" + "\(indexPath.section)" + "\(indexPath.row)")
}
// TODO: UICollectionViewCell 显示结束,指的是Cell滑动移出视图时调用该函数
func collectionView(_ collectionView: UICollectionView, didEndDisplaying cell: UICollectionViewCell, forItemAt indexPath: IndexPath) {
print("cell 显示结束" + "\(indexPath.section)" + "\(indexPath.row)")
}
// TODO: UICollectionView 的headerView 和 footerView 将要出视图的时调用
func collectionView(_ collectionView: UICollectionView, willDisplaySupplementaryView view: UICollectionReusableView, forElementKind elementKind: String, at indexPath: IndexPath) {
print("headerView 和 footerView 将要出现在当前视图")
}
// TODO: UICollectionView 的headerView 和 footerView 滑动移出视图的时调用
func collectionView(_ collectionView: UICollectionView, didEndDisplayingSupplementaryView view: UICollectionReusableView, forElementOfKind elementKind: String, at indexPath: IndexPath) {
print("headerView 和 footerView 被移出当前视图")
}
// TODO: 是否允许 Item 是否显示菜单(Cut/Copy/Paste)
func collectionView(_ collectionView: UICollectionView, shouldShowMenuForItemAt indexPath: IndexPath) -> Bool {
return true
}
// TODO: 设置是否允许菜单内显示那些按钮
func collectionView(_ collectionView: UICollectionView, canPerformAction action: Selector, forItemAt indexPath: IndexPath, withSender sender: Any?) -> Bool {
// 我们可以控制菜单内的按钮显示
if action == #selector(UIResponderStandardEditActions.cut(_:)){
return false
}
return true
}
// TODO: 用户点击菜单内的按钮触发的函数
func collectionView(_ collectionView: UICollectionView, performAction action: Selector, forItemAt indexPath: IndexPath, withSender sender: Any?) {
print("菜单内的按钮被点击")
}
// TODO: 设置 UICollectionView 的 Item 是否可以选择。返回结果:true 可以选择 、 false 不可以选择
func collectionView(_ collectionView: UICollectionView, shouldSelectItemAt indexPath: IndexPath) -> Bool {
return true
}
// TODO: UICollectionView 重新布局调用该方法
func collectionView(_ collectionView: UICollectionView, transitionLayoutForOldLayout fromLayout: UICollectionViewLayout, newLayout toLayout: UICollectionViewLayout) -> UICollectionViewTransitionLayout {
let TransitionLayout = UICollectionViewTransitionLayout.init(currentLayout: self.ctreateFlowLayout(), nextLayout: self.ctreateFlowLayout())
return TransitionLayout
}
2> UICollectionViewDataSource 代理的介绍
// MARK: UICollectionViewDataSource 的代理事件
// TODO: 设置 UICollectionView 的每一个组(Section),含有Item 的个数
func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
return 6
}
// TODO: 设置UICollectionView返回的组数(Section)
func numberOfSections(in collectionView: UICollectionView) -> Int {
return 6
}
// TODO: 这是设置 UICollectionView 的cell 的布局函数
func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
// 创建 CollectionView 的cell
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "cell_id", for: indexPath)
// 设置简单的样式
cell.contentView.backgroundColor = UIColor.red
// 返回变量
return cell
}
// TODO: 设置 UICollectionView 的 headerView & footerView
func collectionView(_ collectionView: UICollectionView, viewForSupplementaryElementOfKind kind: String, at indexPath: IndexPath) -> UICollectionReusableView {
// 创建一个中间变量
var IdentifierStr = String.init()
// 判断是headerView & footerView
if kind == UICollectionElementKindSectionHeader {
IdentifierStr = "header_id"
}else if (kind == UICollectionElementKindSectionFooter) {
IdentifierStr = "footer_id"
}
// 创建一个 UICollectionReusableView 对象
let reusableView = collectionView.dequeueReusableSupplementaryView(ofKind: kind, withReuseIdentifier: IdentifierStr, for: indexPath)
if kind == UICollectionElementKindSectionHeader {
reusableView.backgroundColor = UIColor.magenta
}else if (kind == UICollectionElementKindSectionFooter){
reusableView.backgroundColor = UIColor.green
}
// 返回 UICollectionReusableView 类的对象
return reusableView
}
// TODO: CollectionView 的编辑时设置是否可以移动 Item
func collectionView(_ collectionView: UICollectionView, canMoveItemAt indexPath: IndexPath) -> Bool {
return true
}
// TODO: UICollectionView 的 Items 移动后,数据资源也要变更
func collectionView(_ collectionView: UICollectionView, moveItemAt sourceIndexPath: IndexPath, to destinationIndexPath: IndexPath) {
/* 这更新原始数据库为变更后的数据结构 */
}
// TODO: UICollectionView 的索引返回参数
func indexTitles(for collectionView: UICollectionView) -> [String]? {
return ["A","B","C","D","E","s"]
}
func collectionView(_ collectionView: UICollectionView, indexPathForIndexTitle title: String, at index: Int) -> IndexPath {
print(title)
print(index)
return IndexPath.init()
}
3> UICollectionViewDelegateFlowLayout 的代理介绍
// MARK: UICollectionViewDelegateFlowLayout 的代理事件
// TODO:设置 UICollectionView 的 Item 的大小(宽、高)
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize {
return CGSize.init(width: collectionView.frame.width, height: 60)
}
// TODO: 设置 UICollectionView 的 Section 的上、下、左、右 的偏移
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, insetForSectionAt section: Int) -> UIEdgeInsets {
return UIEdgeInsets.init(top: 20, left: 0, bottom: 40, right: 0)
}
// TODO: 设置 UICollectionView 的 Section 的 HeaderView 的大小(宽、高)
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, referenceSizeForHeaderInSection section: Int) -> CGSize {
return CGSize.init(width: self.view.frame.width, height: 30)
}
// TODO: 设置 UICollectionView 的 Section 的 footerView 的大小(宽、高)
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, referenceSizeForFooterInSection section: Int) -> CGSize {
return CGSize.init(width: self.view.frame.width, height: 30)
}
// TODO: 设置 UICollectionView 的 items 之间的上下临时最小间距
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, minimumInteritemSpacingForSectionAt section: Int) -> CGFloat {
return 3
}
// TODO: 设置 UICollectionView 的 items 之间的上下最小间距
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, minimumLineSpacingForSectionAt section: Int) -> CGFloat {
return 5
}
4> UICollectionViewDataSourcePrefetching 的代理方法的介绍
// MARK: UICollectionView 预先加载的数据
func collectionView(_ collectionView: UICollectionView, prefetchItemsAt indexPaths: [IndexPath]) {
//获取cell ,赋值数据
}
// MARK: UICollectionView 取消预先加载的数据
func collectionView(_ collectionView: UICollectionView, cancelPrefetchingForItemsAt indexPaths: [IndexPath]) {
// 取消预加载
}