iOS自定义collection view的page size(width/height)分页效果
前言
想必大家工作中或多或少会遇到下图样式的UI需求吧
像这种cell长度不固定,并且还能实现的分页效果UI还是很常见的
实现
我们这里实现主要采用collection view,实现的方式是自定义一个UICollectionViewFlowLayout的子类,在这个类里对cell布局进行排列
- 当出现page size小于collection view的size的时候,可以使用ZLCollectionFreePageLayout一下子就实现分页效果
- 并且不需要设置属性collectionView.isPagingEnabled = true,只要设置了layout为ZLCollectionFreePageLayout,就可以自动实现这种效果
主要代码如下:
open override func targetContentOffset(forProposedContentOffset proposedContentOffset: CGPoint, withScrollingVelocity velocity: CGPoint) -> CGPoint {
guard let collectionView = collectionView else {
return super.targetContentOffset(forProposedContentOffset: proposedContentOffset, withScrollingVelocity: velocity)
}
var pWOrH: CGFloat = 0
var contentOffsetXOrY: CGFloat = 0
var collectionViewContentWOrH: CGFloat = 0
var velocityXOrY: CGFloat = 0
if scrollDirection == .horizontal {
pWOrH = (pageWOrH == 0 ? collectionView.frame.width : pageWOrH) + minimumLineSpacing
contentOffsetXOrY = collectionView.contentOffset.x
collectionViewContentWOrH = collectionViewContentSize.width
velocityXOrY = velocity.x
} else {
pWOrH = (pageWOrH == 0 ? collectionView.frame.height : pageWOrH) + minimumInteritemSpacing
contentOffsetXOrY = collectionView.contentOffset.y
collectionViewContentWOrH = collectionViewContentSize.height
velocityXOrY = velocity.y
}
let originalPage = contentOffsetXOrY / pWOrH
var nextPage = (velocityXOrY > 0) ? ceil(originalPage) : floor(originalPage)
if (nextPage + 1.0) * pWOrH > collectionViewContentWOrH { nextPage -= 1.0 }
let currentPage = (velocityXOrY > 0) ? floor(originalPage) : ceil(originalPage)
let pannedLessThanOnePage = abs(1 + currentPage - originalPage) > 0.5
let flicked = abs(velocityXOrY) > 0.01
var newProposedContentOffset = proposedContentOffset
if !(pannedLessThanOnePage && flicked) {
nextPage = round(originalPage)
}
newProposedContentOffset.x = nextPage * pWOrH
return newProposedContentOffset
}
- 在使用的时候,只需要将collection.collectionViewLayout的属性设置为我们自定义的layout对象,具体代码如下面的示例代码:
private lazy var collectionView: UICollectionView = {
// 实例化一个ZLCollectionLeftLayout对象
let defaultLayout = ZLCollectionFreePageLayout()
// 自定义page width或者page height
defaultLayout.pageWOrH = 200.0
defaultLayout.minimumLineSpacing = 10.0
defaultLayout.minimumInteritemSpacing = 10.0
defaultLayout.scrollDirection = .vertical
defaultLayout.sectionInset = UIEdgeInsets(top: 10.0, left: 10.0, bottom: 10.0, right: 10.0)
// 设置collection view的layout为ZLCollectionFreePageLayout
let collectionView = UICollectionView(frame: .zero, collectionViewLayout: defaultLayout)
collectionView.showsVerticalScrollIndicator = false
return collectionView
}()
-
然后就会自动实现分页效果
-
并且不需要设置属性collectionView.isPagingEnabled = true
开源代码地址
代码开源到github上了,可以直接拿来使用
开源代码地址