After some experimentation, this also seems to be related to how you compose your CollectionView.
Tl; dr: Use AutoLayout, not autoresizingMask.
So, at the heart of the problem, the best solutions that I found for handling orientation changes use the following code, which makes sense:
override func viewWillTransition(to size: CGSize, with coordinator: UIViewControllerTransitionCoordinator) { super.viewWillTransition(to: size, with: coordinator) coordinator.animate(alongsideTransition: { (context) in self.collectionView.collectionViewLayout.invalidateLayout() }, completion: nil) }
However, there are situations where you may receive a warning about the size of an element. For me, if I am in the landscape on one tab, switch to another tab, rotate to portrait and return to the previous tab. I tried to invalidate the layout in willAppear, willLayout, all the usual suspects, but no luck. In fact, even if you call invalidateLayout before super.willAppear() , you will still get a warning.
And ultimately, this problem is tied to the size of updating the boundaries of the collection before the delegate asks for the itemize element.
So, keeping in mind, I tried to use AutoLayout instead of collectionView.autoresizingMask = [.flexibleWidth, .flexibleHeight] , and this solved the problem! (I use SnapKit to do AutoLayout so I don't pull my hair out all the time). You also just need invalidateLayout in viewWillTransition (without coordinator.animate , just like in your example), as well as invalidateLayout at the bottom of viewWillAppear(:) . This is like all situations.
I don't know if you use autoresist or not - it would be interesting to know if my theory / solution works for everyone.
Loz Dec 19 '16 at 10:11 2016-12-19 10:11
source share