I have a standard UISplitViewController
, with navigation controllers in both its master and detail panes. Most of the time, the split view controller has its preferredDisplayMode
set to .allVisible
so that both the master and detail are visible.
When I push a particular view controller onto the detail navigation stack, I'd like to hide the master pane so that the user has more of a 'full screen' view. To implement this, I tried changing the preferredDisplayMode
to .primaryHidden
in viewWillAppear
of the detail view controller, and changing it back in viewWillDisappear
. However, this results in a really bad animation, and incorrectly placed views at the end of the transition.
I'm unsure how to fix this. I've tried changing the display mode at different times, placing the call to change the preferredDisplayMode
into an animation block (although it's implicitly animated anyway), and asking the view controller's view to lay itself back out. It looks a little better in an animation block, and the views end up correctly placed, but the animation is still kind of weird and jumpy.
So, how do fix the animation and achieve the appearance I'm looking for?
I put together a minimal sample project to demonstrate the problem. Simply click the 'Push' button in the detail view controller to present the view controller that reconfigures the split view controller.
Try using prepareForSegue
in the DetailViewController. This will change the .preferredDisplayStyle
of your UISplitViewController
before presenting FullscreenViewController, with smoother animations.
In storyboard, the select the show segue from the 'push' button to the FullscreenViewController and set it's identifier (I always use the name of the destination ViewController.) Then in DetailViewController:
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "FullscreenViewController" {
self.splitViewController?.preferredDisplayMode = .primaryHidden
}
}
For a quick fix when navigating 'back' to DetailViewController, I added
self.splitViewController?.preferredDisplayMode = .allVisible
to viewWillAppear
in DetailViewController. I typically use a delegate to pass data between view controllers, and set the display mode there. Hope that helps.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With