NSCollectionViewFlowLayout - 左对齐

时间:2016-03-29 13:27:36

标签: layout flow nscollectionview leftalign

NSCollectionViewFlowLayout生成一个布局,其右边距上的项目对齐,或者,如果容器只有一个项目的宽度,则居中项目。我期待一个对齐选项,例如代表,但我没有在文档中找到任何东西。它是否需要子类化NSCollectionViewFlowLayout来实现这一目标?

4 个答案:

答案 0 :(得分:11)

这是一个产生左对齐流布局的子类:

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
    }
}

答案 1 :(得分:1)

list的高度不一致时,

@Obliquely的答案将失败。这是修改后的代码,以处理Swift 4.2中大小不一致的项目:

collectionViewItems

答案 2 :(得分:0)

如果您的商品宽度相同...

在另一个委托方法中,您应该更改NSCollectionViewLayoutAttributes的框架

- (NSCollectionViewLayoutAttributes *)layoutAttributesForItemAtIndexPath:(NSIndexPath *)indexPath
{
    NSCollectionViewLayoutAttributes *attributes = [[super layoutAttributesForItemAtIndexPath:indexPath] copy];
    NSRect                           modifiedFrame = [attributes frame];

    modifiedFrame.origin.x = floor(modifiedFrame.origin.x / (modifiedFrame.size.width + [self minimumInteritemSpacing])) * (modifiedFrame.size.width + [self minimumInteritemSpacing]);

    [attributes setFrame:modifiedFrame];

    return [attributes autorelease];
}

答案 3 :(得分:0)

快速4.2的较短解决方案:

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
}
}