I have an iPhone storyboard with a UITableView that segues to a detail view using a navigation controller. I'm trying to reuse my classes in the iPad version of the same app inside a master-detail UI.
Here's how my storyboards look to visualize what I'm doing:
I want to reuse as much code as possible, and so far I've been successful in reusing my PPAircraftViewController class with its aircraftTableView.
Question: Since the iPad app already uses PPAircraftViewController to hold the table and detail views, how can I reuse my PPAircraftDetailViewController class with all its code and IBOutlets?
Xcode 5, targeting iOS 6 & 7, UISplitViewController not an option since all of this is embedded within a parent navigation controller.
I finally found what I was looking for. I can't believe it took me so long to remember it, but the perfect solution for this scenario is a UIContainerView.
It lets me embed the PPAircraftDetailViewController inside its containing view controller as pictured below.
Thanks, everyone!
On the iPhone your PPAircraftDetailViewController gets pushed on the navigation stack by the PPAircraftViewController.
That makes either the one or the other visible to the user.
On the iPad, Apple provides a mechanism to show a MasterView and a DetailView side by side in a UISplitViewController.
In that case, the MasterViewController does not "push" the DetailViewController, but activates it through IBOutlets and Delegation.
You can have your PPAircraftViewController as (part of) the MasterViewController and your PPAircraftDetailViewer as (part of) the DetailViewController.
It will require some tweaking, but will also save you a lot of effort as sizing and rotating will be done by the SplitViewController.
Related
I’m maintaining a universal iOS App whose development has started on iOS 6. I’m about the renew the UI for iOS 7. Now I’ve got a weird problem with the iPad part of the app. This part follows the „normal“ Master-Detail view pattern using a UISplitViewController. The UI is configured in a storyboard. The UISplitViewController is the root view controller as requested by Apples docs.
Here comes the weird part: When the detail view controller is embedded in a UINavigationController the navigation controller will be sized incorrectly by the UISplitViewController and so the whole interface looks broken. It appears as if the navigation controller remains in portrait orientation even if the device orientation is landscape. In portrait orientation the detail view controller is looking fine though.
If I avoid embedding the detail view controller in a navigation controller and connect it directly as detail view controller with the UISplitViewController everything is working perfectly in both orientations.
I tried to reproduce the problem in a simple sample App based on the Master-Detail project template provided by Apple without luck. There it works even with a detail view controller embedded in a navigation controller. No matter what I’ve tried so far (looking for categories interfering, rotation settings, method swizzling etc. pp.) I couldn’t find the cause for this problem. As I’m running out of options (if possible I’d rather avoid rolling my container view controller) I respectfully ask if anybody around here has a solution to this problem or further ideas on how to track down the problem.
Thanks in advance
Tino
Found the solution to my own problem. I created a category on UISplitViewController and added a method 'detailViewController' only meant to be a convenience method to access the detail view. Unfortunately the UISplitViewController has an equally named internal method which is was replacing. Would I have followed Apples guidelines to always prefix category methods in order to avoid name clashes I would have saved a lot of my own time. :(
I have finished iPhone version of my app and want my app to support iPads as well. I used a tabbar controller for iphone.. I could use the same for iPad, however, I would have too much free space on iPad if I use a Tabbar. so I have decided to use Split View Controller. Left part(table view) should be visible all the time even if it's not in landscape mode. And every time a cell is clicked, the corresponding view should be loaded to the right hand side.. By the way I am using storyboards.. Seems like it makes everything more difficult. Are there some examples of it? Thanks..
I have faced a similar situation recently. Basically you can use the split view project template to generate the basic code. After that, I created a DetailedViewControllerContainer interface and used it as the view controller for the right side view of the split view, replacing the generated DetailViewController.
After that I created several view controllers, each of them corresponds to a selection in the left side view(master view controller). And add these view controllers as the child view controllers for the DetailedViewControllerContainer.
The catch is that you will need to use code to load the child view controllers. The benefit is that the child view controllers do not need to be modified from the iPhone version. The DetailedViewControllerContainer remains the only SplitView delegate.
Take a look at the sample code I wrote on github:
https://github.com/raoying/SplitView-Sample
I'm still relatively unfamiliar with all the new features of iOS 5, and what I can do in Xcode now. So, a good explanation would be appreciated.
I'm designed a single-view application and I have both an iPhone and iPad storyboard. I chose 'Single View Application' when I first started, so Xcode created a ViewController for me. Both storyboards list this view controller as their own.
Back in iOS 4 the way that I linked button actions to my view controller was to Right-Click on the button on the nib, pick the action that I wanted, then drag it over into the view controller's '.h' file, which auto-created a method/property for me.
I am confused about how to accomplish this now, since I have multiple storyboards but only one view controller. Do I need to have multiple links for each button; one for the button on the iPhone and one for the iPad? Or is there a better way to accomplish what I am trying to do now?
You do it the same way you did it in iOS4. But obviously you never built an universal app there ;-)
It's totally okay to have a single UIViewController class for two different nib files.
And if you use storyboards it's fine to use different storyboards and a single viewController too.
You can even use the same viewController for different scenes inside a single storyboard.
The connections to the viewController are saved in the nib or storyboard. So you can't overwrite them while designing the other user interface.
Open the iPhone storyboard, make your connections to actions and outlets. Then open the iPad storyboard and make totally independent connections.
In response to the first reply, I was under the impression that a view controller could only support two scenes in a storyboard layout. I say that because I found this thread.
I'm trying to create an iOS 5 application with a SplitView Controller that uses multiple detailviews. Here's the rub. I'm trying to do it using Storyboards. I've found a number of tutorials explaining how to do it in previous versions of Xcode, but none addressing Storyboards.
The one exception creates a tab bar controller in the master view, which is not something I want to use. I tried removing the tab bar and modifying the code but was unsuccessful.
I did figure out that I could attach a replace Segue to a static cell in the master view. It allows me to specify the type as a detail split, which accomplishes most of what I'm trying to do. It loads the new detail controller.
However, the button that shows the master popover disappears during he transition. I believe I can probably prevent that from happening using this method:
(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
Unfortunately, I'm not sure exactly what code to place there to prevent the button from disappearing. Do I need each detail controller as a delegate to the master somehow?
Has anyone gotten multiple detail views to work using storyboards and if so can you point me in the direction of a good tutorial? Thank you so much for the help!
I faced a similar situation and checked the link to the raywenderlich.com. However I found managing the splitview delegate kind of too complicated, and it makes reuse between iPhone and iPad difficult. My solution is to create a DetailedContainerViewController as the right side view controller. And add the view controllers to be displayed on the right side as the child view controllers of the container controller. In this way only the DetailedContainerViewController needs to implement the SplitView delegate. So there is no need to worry about the delegate.
Take a look at the sample code I wrote on github:
https://github.com/raoying/SplitView-Sample
I am trying to implement a split view controller like UISplitViewController on the iPad, but I don't want the left pane to be hidden when the device is in portrait orientation.
So I've created a UIViewController subclass for this in IB and it works fine without any sub-view controllers. Now I'm trying to wrap my head around what is required to setup and manage the two UIViewController objects for the left and right panes. In my app, they are going to both be UINavigationController with a UITableView in them.
I've hit a mental road block about how to set this up and was hoping someone could point me to some sample code or give me a recommendation for architecture here...
The only reason to use the UISplitView controller is the show/hide logic it gets you for free. I would think it a lot easier to simply take the two view controllers (Root View & Detail View) and lay them on a standard UIViewController. You can then manage them more diorectly without overriding the intended behavior of the implemented controller.
THe settings app on the iPad does what you are looking for and I believe this is the approach that app takes.
Good Luck!
is setHidesMasterViewInPortrait still a private Api and the app will get rejected?
Create your UISplitViewController instance and then call:
[splitViewController setHidesMasterViewInPortrait:NO];
The compiler will give you a warning message but it will do what you want. You can get rid of the compiler warning by making a category on UISplitViewController that implements that method.