zoukankan      html  css  js  c++  java
  • Collection View 自定义布局(custom flow layout)

    Collection view自定义布局

    一般我们自定义布局都会新建一个类,继承自UICollectionViewFlowLayout,然后重写几个方法:

    • prepareLayout():当准备开始布局时调用这个方法,可以在这里计算一些属性,比如cell的尺寸。
    • layoutAttributesForElementsInRect(rect: CGRect) -> [UICollectionViewLayoutAttributes]?:在这里返回布局属性。

    实例(比较简单的例子,实际开发中可以进行更多的封装)

    第一步:声明两个属性

        // MARK: 属性
        /** cell的个数 */
        var itemCount: Int?
        
        /** 布局信息 */
        var layoutAttributes = [UICollectionViewLayoutAttributes]()
    

    第二步:重写prepareLayout方法,计算布局属性

        // MARK: 准备布局
        override func prepareLayout() {
            super.prepareLayout()
            
            // 计算每个cell的宽度
            let width = (UIScreen.mainScreen().bounds.size.width - self.sectionInset.left - self.sectionInset.right - minimumInteritemSpacing) / 2.0
            
            // 判断itemCount是否为空
            if itemCount != nil {
                // 开始计算每个cell的布局属性
                calculationAttribute(withItemWidth: width)
            }
        }
    
    func calculationAttribute(withItemWidth itemWidth: CGFloat) {
            // 声明数组 保存每一列的总高度 (两列)
            let column1 = sectionInset.top, column2 = sectionInset.top
            var columnArray: [CGFloat] = [column1, column2]
            
            for index in 0..<itemCount! {
                // 创建indexPath 因为是示例 所以排版固定在一组
                let indexPath = NSIndexPath(forItem: index, inSection: 0)
                // 创建布局属性 通过indexPath
                let attribute = UICollectionViewLayoutAttributes(forCellWithIndexPath: indexPath)
                // 创建一个随机高度
                let itemHeight = CGFloat(arc4random()%150 + 100)
                
                // columnNumber 记录定义的是哪一列
                var columnNumber: CGFloat
                if columnArray[0] < columnArray[1] {
                    columnArray[0] += itemHeight + self.minimumLineSpacing
                    columnNumber = 0
                } else {
                    columnArray[1] += itemHeight + self.minimumLineSpacing
                    columnNumber = 1
                }
                
                // 设置item的位置
                let x = self.sectionInset.left + (self.minimumLineSpacing + itemWidth) * columnNumber
                let y = columnArray[Int(columnNumber)] - itemHeight - self.minimumLineSpacing
                attribute.frame = CGRectMake(x, y, itemWidth, itemHeight)
                
                layoutAttributes.append(attribute)
            }
            // 当设置完所有item的位置后需要设置itemsize 这样才能保证滚动时能显示所有的cell
            // itemsize的height属性 是取最高的那列的平均值
            if columnArray[0] > columnArray[1] {
                self.itemSize = CGSizeMake(itemWidth, (columnArray[0] - sectionInset.top) * 2 / CGFloat(itemCount!) - self.minimumLineSpacing)
            } else {
                self.itemSize = CGSizeMake(itemWidth, (columnArray[1] - sectionInset.top) * 2 / CGFloat(itemCount!) - self.minimumLineSpacing)
            }
        }
    

     第三步:返回布局信息数组

        override func layoutAttributesForElementsInRect(rect: CGRect) -> [UICollectionViewLayoutAttributes]? {
            return layoutAttributes
        }
    

    总结:这个例子是瀑布流的布局,如果需要别的布局需要在准备布局时计算,然后返回布局信息数组就可以了

  • 相关阅读:
    POJ 2253 Frogger(最短路 Floyd)
    POJ 1062 昂贵的聘礼 (最短路 Dijkstra)
    POJ 3259 Wormholes(最短路Bellman_Ford)
    POJ 3414 Pots(容量BFS)
    POJ 3087 Shuffle'm Up(模拟题)
    POJ 3216 Prime Path(数字BFS)
    refresh的停车场
    基于邻接表的广度优先搜索遍历
    判断给定图是否存在合法的拓扑排序
    威威猫系列故事——篮球梦
  • 原文地址:https://www.cnblogs.com/Alex-sk/p/5572275.html
Copyright © 2011-2022 走看看