1

I am facing some trouble with a bottom UIToolbar on the iPhone. The height of the bar seems to depend on the device orientation at the time when I navigate to the scene and does not update when the orientation is changed.

  1. When I navigate to the scene in portrait mode, the bottom bar has a height of 44. When I then turn the phone (an iPhone XR here), the height of the bar remains 44.
  2. When I open the scene in landscape mode, the bottom bar height is 49 and also remains 49 when I turn the phone upright.

This can easily be reproduced with as simple 2-scene app such as this one: demo app

Initially, this was not really an issue - the user would not even notice the small change. But now I am using the bottom bar in a split view. When that is initially opened in portrait, the bottom toolbar has a height of 44. Turning the phone into landscape, the detail view with its own toolbar, 49 high, opens. Then I have two toolbars with different heights right next to each other, which is rather ugly: different toolbar heights in splitview

So the question is how I can ensure the toolbar height is either updated on orientation change, or the height is always the same (as e.g. in the email app). I don't want to hard-code the height expecting that it would eventually make things worse on future iOS versions or different devices.

I am using Xcode 10.1, running the app on an iPhone with iOS 12.1.2.

  • 1
    On orientation change.. update the toolbar height https://stackoverflow.com/questions/38894031/swift-how-to-detect-orientation-changes https://stackoverflow.com/questions/2135407/is-there-a-way-to-change-the-height-of-a-uitoolbar – Mocha Jan 04 '19 at 22:44
  • 1
    Thank you, @Mocha. This might be the way to go. But, as I said, I want to avoid hardcoding the height as this might cause other problems. Preferable would be to make the toolbar, like any other standard element, assume its natural dimensions for each orientation. I'm not sure but I would consider that to be the expected, default behavior. So, I'm a bit baffled by the fact that the default dimensions of a standard element do not depend on the orientation but on the INITIAL orientation. –  Jan 05 '19 at 09:28
  • Its not _really_ hard coding the height since its based off the toolbar height though. – Mocha Jan 05 '19 at 09:48
  • Yes, you are right (sorry, I slightly misinterpreted your comment in my earlier response). This is one option. If you want to add your answer, I'll be happy to give credit and remove mine. Anyway, JoelEsli's answer is closer to what I was looking for. –  Jan 12 '19 at 11:32

2 Answers2

2

Did you add the toolbar manually on to the view or are you using the navigationController to manage the toolbar? I am assuming you did, since on rotation the height is not changing.

The navigation controller manages the height of the toolbar on rotation. Adding the following to the viewDidLoad() method will show the navigationController's toolbar.

navigationController?.setToolbarHidden(false, animated: false)

This approach requires a little less code than if your view controller manages the toolbar (one less method, one less outlet).

Here is the default template I did to check that the toolbar displayed properly on iPad and an iPhone Max model: https://github.com/joelesli/TBHeight/

iPad Pro enter image description here

iPhone XS Max enter image description here

iPad Air 2 enter image description here

iPhone 8 Plus enter image description here

JoelEsli
  • 451
  • 3
  • 8
  • True, I added the toolbar manually. This looks good and like much less of a hack than what I came up with. I will give it a try and let you know. Thank you! –  Jan 07 '19 at 14:17
  • My apologies. I haven't been in the office the past few days. I'll see if I can check it today or during the weekend at the latest and then mark the answer. It looks good and is very much appreciated. –  Jan 11 '19 at 07:30
  • Verified. This works beautifully and is exactly what I was looking for. Thank you for the great effort including the demo project. –  Jan 12 '19 at 11:18
  • Leveraging the SDK is the easiest way to go. Glad it helped. – JoelEsli Jan 12 '19 at 15:24
0

I initially solved it (based on Mocha's comment above) by overriding viewWillTransition(...) to redraw the toolbar and assume its default dimensions for each orientation.

override func viewWillTransition(to size: CGSize, with coordinator: UIViewControllerTransitionCoordinator) {
    if let bBar = bottomBar { bBar.invalidateIntrinsicContentSize() }
}

That way it should adapt to future UI changes, and I don't risk having problems in app approval (if modifying standard UI element styles would be an issue here).

Update: I prefer JoelEsli's solution though this might be a good alternative in some situations, so I'm leaving it here for completeness.