首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >NSCollectionViewFlowLayout -左对齐

NSCollectionViewFlowLayout -左对齐
EN

Stack Overflow用户
提问于 2016-03-29 21:27:36
回答 4查看 1.8K关注 0票数 4

NSCollectionViewFlowLayout生成一个布局,项目在右边距对齐,或者,如果容器仅够容纳一个项目,则项目居中。我期待一个对齐选项,例如在委托上,但在文档中找不到任何东西。是否需要对NSCollectionViewFlowLayout进行子类化才能实现此目的?

EN

回答 4

Stack Overflow用户

发布于 2016-03-29 21:27:36

下面是一个子类,它产生一个左对齐的流布局:

代码语言:javascript
复制
class LeftFlowLayout: NSCollectionViewFlowLayout {

    override func layoutAttributesForElementsInRect(rect: CGRect) -> [NSCollectionViewLayoutAttributes] {

        let defaultAttributes = super.layoutAttributesForElementsInRect(rect)

        if defaultAttributes.isEmpty {
            // we rely on 0th element being present,
            // bail if missing (when there's no work to do anyway)
            return defaultAttributes
        }

        var leftAlignedAttributes = [NSCollectionViewLayoutAttributes]()

        var xCursor = self.sectionInset.left // left margin

        // if/when there is a new row, we want to start at left margin
        // the default FlowLayout will sometimes centre items,
        // i.e. new rows do not always start at the left edge

        var lastYPosition = defaultAttributes[0].frame.origin.y

        for attributes in defaultAttributes {
            if attributes.frame.origin.y > lastYPosition {
                // we have changed line
                xCursor = self.sectionInset.left
                lastYPosition = attributes.frame.origin.y
            }

            attributes.frame.origin.x = xCursor
            // by using the minimumInterimitemSpacing we no we'll never go
            // beyond the right margin, so no further checks are required
            xCursor += attributes.frame.size.width + minimumInteritemSpacing

            leftAlignedAttributes.append(attributes)
        }
        return leftAlignedAttributes
    }
}
票数 12
EN

Stack Overflow用户

发布于 2018-10-30 14:20:51

collectionViewItems的高度不一致时,@Obliquely的答案就会失败。以下是他们在Swift 4.2中为处理非统一大小项目而修改的代码:

代码语言:javascript
复制
class CollectionViewLeftFlowLayout: NSCollectionViewFlowLayout
{
    override func layoutAttributesForElements(in rect: CGRect) -> [NSCollectionViewLayoutAttributes]
    {
        let defaultAttributes = super.layoutAttributesForElements(in: rect)

        if defaultAttributes.isEmpty {
            return defaultAttributes
        }

        var leftAlignedAttributes = [NSCollectionViewLayoutAttributes]()

        var xCursor = self.sectionInset.left                            // left margin
        var lastYPosition = defaultAttributes[0].frame.origin.y         // if/when there is a new row, we want to start at left margin
        var lastItemHeight = defaultAttributes[0].frame.size.height

        for attributes in defaultAttributes
        {
            // copy() Needed to avoid warning from CollectionView that cached values are mismatched
            guard let newAttributes = attributes.copy() as? NSCollectionViewLayoutAttributes else {
                continue;
            }

            if newAttributes.frame.origin.y > (lastYPosition + lastItemHeight)
            {
                // We have started a new row
                xCursor = self.sectionInset.left
                lastYPosition = newAttributes.frame.origin.y
            }

            newAttributes.frame.origin.x = xCursor

            xCursor += newAttributes.frame.size.width + minimumInteritemSpacing
            lastItemHeight = newAttributes.frame.size.height

            leftAlignedAttributes.append(newAttributes)
        }
        return leftAlignedAttributes
    }
}
票数 4
EN

Stack Overflow用户

发布于 2019-03-24 01:47:33

swift 4.2的较短解决方案:

代码语言:javascript
复制
class CollectionViewLeftFlowLayout: NSCollectionViewFlowLayout {

    override func layoutAttributesForElements(in rect: NSRect) -> [NSCollectionViewLayoutAttributes] {
        let attributes = super.layoutAttributesForElements(in: rect)

        if attributes.isEmpty { return attributes }

        var leftMargin = sectionInset.left
        var lastYPosition = attributes[0].frame.maxY

        for itemAttributes in attributes {

            if itemAttributes.frame.origin.y > lastYPosition { // NewLine
               leftMargin = sectionInset.left
            }

            itemAttributes.frame.origin.x = leftMargin
            leftMargin += itemAttributes.frame.width + minimumInteritemSpacing
            lastYPosition = itemAttributes.frame.maxY
        }
        return attributes
    }
}
票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/36285720

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档