Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Resize UICollectionView to content size

Tags:

Summary: I have a child view within a stackview and that child view that is programatically sized. It has a couple of empty views to fill up the empty space. At runtime, however, attempts to resize the child don't work and it remains the same size as in the storyboard. How can I resize the child view so that the stack view honours its new size and positions it accordingly.

Details: I have a UICollectionView with a custom layout. The layout calculates the positions of subviews correctly (they display where I want) and return the correct content size. The content size is narrower than the screen but possibly longer depending upon orientation.

The custom layout returns the correct, calculated size but the collection view does not resize.

I've tried programatically changing the collection view's size on the parent's viewDidLoad. Didn't work.

I've tried programatically changing the collection view's layoutMargins on the parent's viewDidLoad. Didn't work.

I am using Swift 3, XCode 8.

like image 909
dave Avatar asked Oct 31 '16 18:10

dave


People also ask

What is Uicollectionviewflowlayout?

A layout object that organizes items into a grid with optional header and footer views for each section.


1 Answers

If I understand your question, you need your UICollectionView to have its size equals to its content, in other words, you want your UICollectionView to have an intrinsic size (just like a label which resizes automatically based on its text).

In that case, you can subclass UICollectionView to add this behaviour, then you don't need to set its size.

class IntrinsicSizeCollectionView: UICollectionView {
    // MARK: - lifecycle
    required init?(coder aDecoder: NSCoder) {
        super.init(coder: aDecoder)
        self.setup()
    }

    override init(frame: CGRect, collectionViewLayout layout: UICollectionViewLayout) {
        super.init(frame: frame, collectionViewLayout: layout)

        self.setup()
    }

    override func layoutSubviews() {
        super.layoutSubviews()
        if !self.bounds.size.equalTo(self.intrinsicContentSize) {
            self.invalidateIntrinsicContentSize()
        }
    }

    override var intrinsicContentSize: CGSize {
        get {
            let intrinsicContentSize = self.contentSize
            return intrinsicContentSize
        }
    }

    // MARK: - setup
    func setup() {
        self.isScrollEnabled = false
        self.bounces = false
    }
}

ps: In your .xib, don't forget to set your IntrinsicSizeCollectionView height constraint as a placeholder constraint (check "Remove at build time")

like image 150
ghashi Avatar answered Oct 08 '22 17:10

ghashi