I am trying to create a simple NSCollectionView programmatically. I am setting it up in the NSViewController:
class ViewController: NSViewController {
var scrollView: NSScrollView!
var collectionView: NSCollectionView!
override func loadView() {
self.view = NSView(frame: NSRect(x: 0, y: 0, width: 600, height: 400))
}
override func viewDidLoad() {
super.viewDidLoad()
collectionView = NSCollectionView(frame: NSZeroRect)
collectionView.backgroundView?.wantsLayer = true
collectionView.backgroundColors = [NSColor.black]
collectionView.collectionViewLayout = NSCollectionViewFlowLayout()
collectionView.dataSource = self
collectionView.delegate = self
collectionView.register(CollectionViewItem.self, forItemWithIdentifier: NSUserInterfaceItemIdentifier("CollectionViewItem"))
scrollView = NSScrollView(frame: view.frame)
scrollView.documentView = collectionView
view.addSubview(scrollView)
self.scrollView.translatesAutoresizingMaskIntoConstraints = false
self.scrollView.topAnchor.constraint(equalTo: self.view.topAnchor).isActive = true
self.scrollView.bottomAnchor.constraint(equalTo: self.view.bottomAnchor).isActive = true
self.scrollView.leadingAnchor.constraint(equalTo: self.view.leadingAnchor).isActive = true
self.scrollView.trailingAnchor.constraint(equalTo: self.view.trailingAnchor).isActive = true
}
}
extension ViewController: NSCollectionViewDataSource {
func collectionView(_ collectionView: NSCollectionView, numberOfItemsInSection section: Int) -> Int {
return 5
}
func collectionView(_ collectionView: NSCollectionView, itemForRepresentedObjectAt indexPath: IndexPath) -> NSCollectionViewItem {
let item = collectionView.makeItem(withIdentifier: NSUserInterfaceItemIdentifier("CollectionViewItem"), for: indexPath)
item.representedObject = indexPath.item
return item
}
}
extension ViewController: NSCollectionViewDelegateFlowLayout {
func collectionView(_ collectionView: NSCollectionView, layout collectionViewLayout: NSCollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> NSSize {
return NSSize(width: 25, height: 25)
}
}
Here's how I am setting up the NSCollectionViewItem:
class CollectionViewItem: NSCollectionViewItem {
var collectionViewItemView: CollectionViewItemView?
override func loadView() {
if (self.representedObject != nil) {
self.collectionViewItemView = CollectionViewItemView(frame: NSZeroRect, number: self.representedObject as! Int)
self.view = collectionViewItemView!
} else {
self.view = CollectionViewItemView(frame: NSZeroRect)
}
}
override var representedObject: Any? {
didSet {
loadView()
}
}
}
And here's how I'm creating a custom NSView to work inside the NSCollectionViewItem:
class CollectionViewItemView: NSView {
var number: Int?
override init(frame frameRect: NSRect) {
super.init(frame: frameRect)
}
convenience init(frame frameRect: NSRect, number: Int) {
self.init(frame: frameRect)
self.number = number
layoutSubviews()
}
required init?(coder: NSCoder) {
super.init(coder: coder)
}
func layoutSubviews() {
let label = NSTextField(frame: NSMakeRect(0, 0, 60, 30))
label.stringValue = "\(self.number!)"
addSubview(label)
}
}
Now, despite the fact that I am using an NSCollectionViewFlowLayout, conforming to the NSCollectionViewDelegateFlowLayout and providing a sizeForItemAt all indices, the resultant CollectionViewItemView is always sized 0, as shown below:
In sample projects online, the authors always feed an NSZeroRect to the frame of the NSCollectionViewItem. If I give it a custom NSRect, it always renders them on top of each other (since the origin of the frame is always the same).
What is the proper way of doing this? I'm at a loss. Why is the NSCollectionView not responding to the NSCollectionViewDelegateFlowLayout ?
