我按照
This指南建立了一个圆形UICollectionview,一切都按预期工作但我不希望这些项目绕自己的角度/锚点旋转
最上面一行是我的圆形collectionview当前是如何工作的,底部的绘图是我想要我的collectionview的方式:
class CircularCollectionViewLayoutAttributes: UICollectionViewLayoutAttributes { var anchorPoint = CGPoint(x: 0.3,y: 0.5) var angle: CGFloat = 0 { didSet { zIndex = Int(angle*1000000) transform = CGAffineTransformMakeRotation(angle) } } override func copyWithZone(zone: NSZone) -> AnyObject { let copiedAttributes: CircularCollectionViewLayoutAttributes = super.copyWithZone(zone) as! CircularCollectionViewLayoutAttributes copiedAttributes.anchorPoint = self.anchorPoint copiedAttributes.angle = self.angle return copiedAttributes } }@H_403_9@使用以下布局类:
class CircularCollectionViewLayout: UICollectionViewLayout { let itemSize = CGSize(width: 60,height: 110) var angleAtExtreme: CGFloat { return collectionView!.numberOfItemsInSection(0) > 0 ? -CGFloat(collectionView!.numberOfItemsInSection(0)-1)*anglePerItem : 0 } var angle: CGFloat { return angleAtExtreme*collectionView!.contentOffset.x/(collectionViewContentSize().width - CGRectGetWidth(collectionView!.bounds)) } var radius: CGFloat = 400 { didSet { invalidateLayout() } } var anglePerItem: CGFloat { return 0.18 } var attributesList = [CircularCollectionViewLayoutAttributes]() override func collectionViewContentSize() -> CGSize { return CGSize(width: CGFloat(collectionView!.numberOfItemsInSection(0))*itemSize.width,height: CGRectGetHeight(collectionView!.bounds)) } override class func layoutAttributesClass() -> AnyClass { return CircularCollectionViewLayoutAttributes.self } override func prepareLayout() { super.prepareLayout() let centerX = collectionView!.contentOffset.x + (CGRectGetWidth(collectionView!.bounds)/2.0) let anchorPointY = ((itemSize.height/2.0) + radius)/itemSize.height let theta = atan2(CGRectGetWidth(collectionView!.bounds)/2.0,radius + (itemSize.height/2.0) - (CGRectGetHeight(collectionView!.bounds)/2.0)) //1 //let theta:CGFloat = 1.0 var startIndex = 0 var endIndex = collectionView!.numberOfItemsInSection(0) - 1 if (angle < -theta) { startIndex = Int(floor((-theta - angle)/anglePerItem)) } endIndex = min(endIndex,Int(ceil((theta - angle)/anglePerItem))) if (endIndex < startIndex) { endIndex = 0 startIndex = 0 } attributesList = (startIndex...endIndex).map { (i) -> CircularCollectionViewLayoutAttributes in let attributes = CircularCollectionViewLayoutAttributes(forCellWithIndexPath: NSIndexPath(forItem: i,inSection: 0)) attributes.size = self.itemSize attributes.center = CGPoint(x: centerX,y: CGRectGetMidY(self.collectionView!.bounds)) attributes.angle = self.angle + (self.anglePerItem*CGFloat(i)) attributes.anchorPoint = CGPoint(x: 0.5,y: anchorPointY) return attributes } } override func layoutAttributesForElementsInRect(rect: CGRect) -> [UICollectionViewLayoutAttributes]? { return attributesList } override func layoutAttributesForItemAtIndexPath(indexPath: NSIndexPath) -> (UICollectionViewLayoutAttributes!) { return attributesList[indexPath.row] } override func shouldInvalidateLayoutForBoundsChange(newBounds: CGRect) -> Bool { return true } override func targetContentOffsetForProposedContentOffset(proposedContentOffset: CGPoint,withScrollingVelocity velocity: CGPoint) -> CGPoint { var finalContentOffset = proposedContentOffset let factor = -angleAtExtreme/(collectionViewContentSize().width - CGRectGetWidth(collectionView!.bounds)) let proposedAngle = proposedContentOffset.x*factor let ratio = proposedAngle/anglePerItem var multiplier: CGFloat if (velocity.x > 0) { multiplier = ceil(ratio) } else if (velocity.x < 0) { multiplier = floor(ratio) } else { multiplier = round(ratio) } finalContentOffset.x = multiplier*anglePerItem/factor return finalContentOffset } }@H_403_9@我尝试了很多东西但是我无法改变细胞旋转
解决方法
我通过负角度旋转单元格视图解决了这个问题:
代码如下:
override func applyLayoutAttributes(layoutAttributes: UICollectionViewLayoutAttributes!) { super.applyLayoutAttributes(layoutAttributes) let circularlayoutAttributes = layoutAttributes as! CircularCollectionViewLayoutAttributes self.layer.anchorPoint = circularlayoutAttributes.anchorPoint viewRoot.transform = CGAffineTransformMakeRotation(-circularlayoutAttributes.angle) self.center.y += (circularlayoutAttributes.anchorPoint.y - 0.5) * CGRectGetHeight(self.bounds) }@H_403_9@