Just as an app utilizes different storyboards for iPad and iPhone, I would like my app to use a different storyboard for the iPhone 5. Since there is no option in the Info.plist to select default storyboard for iPhone 5, how would I programmatically call the storyboard?
I do not want to use AutoLayout for this app unless it is absolutely the last resort. I understand how to detect if a user is using an iPhone 5 or other device with the same screen size. I just need to know how to set the default storyboard without the plist.
I was looking for the same answer couple of weeks ago here's my solution hope helps..
-(void)initializeStoryBoardBasedOnScreenSize {
if ([UIDevice currentDevice].userInterfaceIdiom == UIUserInterfaceIdiomPhone)
{ // The iOS device = iPhone or iPod Touch
CGSize iOSDeviceScreenSize = [[UIScreen mainScreen] bounds].size;
if (iOSDeviceScreenSize.height == 480)
{ // iPhone 3GS, 4, and 4S and iPod Touch 3rd and 4th generation: 3.5 inch screen (diagonally measured)
// Instantiate a new storyboard object using the storyboard file named Storyboard_iPhone35
UIStoryboard *iPhone35Storyboard = [UIStoryboard storyboardWithName:#"Storyboard_iPhone35" bundle:nil];
// Instantiate the initial view controller object from the storyboard
UIViewController *initialViewController = [iPhone35Storyboard instantiateInitialViewController];
// Instantiate a UIWindow object and initialize it with the screen size of the iOS device
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
// Set the initial view controller to be the root view controller of the window object
self.window.rootViewController = initialViewController;
// Set the window object to be the key window and show it
[self.window makeKeyAndVisible];
}
if (iOSDeviceScreenSize.height == 568)
{ // iPhone 5 and iPod Touch 5th generation: 4 inch screen (diagonally measured)
// Instantiate a new storyboard object using the storyboard file named Storyboard_iPhone4
UIStoryboard *iPhone4Storyboard = [UIStoryboard storyboardWithName:#"Storyboard_iPhone4" bundle:nil];
// Instantiate the initial view controller object from the storyboard
UIViewController *initialViewController = [iPhone4Storyboard instantiateInitialViewController];
// Instantiate a UIWindow object and initialize it with the screen size of the iOS device
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
// Set the initial view controller to be the root view controller of the window object
self.window.rootViewController = initialViewController;
// Set the window object to be the key window and show it
[self.window makeKeyAndVisible];
}
} else if ([UIDevice currentDevice].userInterfaceIdiom == UIUserInterfaceIdiomPad)
{ // The iOS device = iPad
UISplitViewController *splitViewController = (UISplitViewController *)self.window.rootViewController;
UINavigationController *navigationController = [splitViewController.viewControllers lastObject];
splitViewController.delegate = (id)navigationController.topViewController;
}
}
Call this method under AppDelegate ddiFinishLaunchingWithOptions: method
And also don't forget the name your storyboards properly
Hope helps...
This worked for me - slight refinement with wrapping getting the storyboard in a function
-(UIStoryboard*) getStoryboard {
UIStoryboard *storyBoard = nil;
if ([UIDevice currentDevice].userInterfaceIdiom == UIUserInterfaceIdiomPad) {
storyBoard = [UIStoryboard storyboardWithName:#"MainStoryboard_iPad" bundle:nil];
}else{
if ([UIDevice currentDevice].userInterfaceIdiom == UIUserInterfaceIdiomPhone){
// The iOS device = iPhone or iPod Touch
CGSize iOSDeviceScreenSize = [[UIScreen mainScreen] bounds].size;
if (iOSDeviceScreenSize.height == 480){
// iPhone 3/4x
storyBoard = [UIStoryboard storyboardWithName:#"MainStoryboard_iPhone_4" bundle:nil];
}else if (iOSDeviceScreenSize.height == 568){
// iPhone 5 etc
storyBoard = [UIStoryboard storyboardWithName:#"MainStoryboard_iPhone_5" bundle:nil];
}
}
}
ASSERT(storyBoard);
return storyBoard;
}
UIStoryboard* mainStoryBoard = [self getStoryboard];
self.initialViewController = [mainStoryBoard instantiateInitialViewController];
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
self.window.rootViewController = self.initialViewController;
[self.window makeKeyAndVisible];
Related
I'm trying to create 2 storyboards, one for iPhone 4 and one for iPhone 5. I want it to be detected at launch which device the user is using. I've used the following code and implemented it in my app delegate.m, but receive the error:
Use of undeclared identifier "initializeStoryBoardBasedOnScreenSize"
Here's the code I've used:
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
-(void)initializeStoryBoardBasedOnScreenSize {
if ([UIDevice currentDevice].userInterfaceIdiom == UIUserInterfaceIdiomPhone)
{ // The iOS device = iPhone or iPod Touch
CGSize iOSDeviceScreenSize = [[UIScreen mainScreen] bounds].size;
if (iOSDeviceScreenSize.height == 480)
{ // iPhone 3GS, 4, and 4S and iPod Touch 3rd and 4th generation: 3.5 inch screen (diagonally measured)
// Instantiate a new storyboard object using the storyboard file named Storyboard_iPhone35
UIStoryboard *iPhone35Storyboard = [UIStoryboard storyboardWithName:#"Storyboard_iPhone35" bundle:nil];
// Instantiate the initial view controller object from the storyboard
UIViewController *initialViewController = [iPhone35Storyboard instantiateInitialViewController];
// Instantiate a UIWindow object and initialize it with the screen size of the iOS device
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
// Set the initial view controller to be the root view controller of the window object
self.window.rootViewController = initialViewController;
// Set the window object to be the key window and show it
[self.window makeKeyAndVisible];
}
if (iOSDeviceScreenSize.height == 568)
{ // iPhone 5 and iPod Touch 5th generation: 4 inch screen (diagonally measured)
// Instantiate a new storyboard object using the storyboard file named Storyboard_iPhone4
UIStoryboard *iPhone4Storyboard = [UIStoryboard storyboardWithName:#"Storyboard_iPhone4" bundle:nil];
// Instantiate the initial view controller object from the storyboard
UIViewController *initialViewController = [iPhone4Storyboard instantiateInitialViewController];
// Instantiate a UIWindow object and initialize it with the screen size of the iOS device
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
// Set the initial view controller to be the root view controller of the window object
self.window.rootViewController = initialViewController;
// Set the window object to be the key window and show it
[self.window makeKeyAndVisible];
}
} else if ([UIDevice currentDevice].userInterfaceIdiom == UIUserInterfaceIdiomPad)
{ // The iOS device = iPad
UISplitViewController *splitViewController = (UISplitViewController *)self.window.rootViewController;
UINavigationController *navigationController = [splitViewController.viewControllers lastObject];
splitViewController.delegate = (id)navigationController.topViewController;
}
Is there maybe something I need to import to fix the error?
You have tried to define a method inside application:didFinishLaunchingWithOptions::
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
-(void)initializeStoryBoardBasedOnScreenSize {
// ... your code ...
}
return YES;
}
This is not what you want and btw. nested functions (or methods) are not supported
in Objective-C.
What you probably meant is to define a method and call it
inside application:didFinishLaunchingWithOptions::
-(void)initializeStoryBoardBasedOnScreenSize {
// ... your code ...
}
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
[self initializeStoryBoardBasedOnScreenSize];
return YES;
}
maybe it could just be an error here, but you're entering an action void in didFinishApplicationLaunchingWithOptions?
did you try to fit everything in didFinishApplicationLaunchingWithOptions without simply use this action void?
So I've created an app for iPhone and I wanted to convert it to iPad, by following steps from this answer.
Duplicate your iPhone-Storyboard and rename it MainStoryboard_iPad.storyboard
Open this file any text editor.
Search for targetRuntime="iOS.CocoaTouch"and change it to targetRuntime="iOS.CocoaTouch.iPad"
Now save everything and reopen Xcode -> the iPad-Storyboard contains the same as the iPhone-file but everyting could be disarranged
Everything is done correctly but iPad simulator/device anyways uses iPhone storyboard. Any suggestions?
I've set iPad storyboard in summary->ipad deployment info->Main storyboard. And main.plist-> Main storyboard file base name (iPad) is set to iPad storyboard.
Please tell me what I am missing.
UPD. Interesting Thing, when I delete iPad storyboard name from ipad deployment info it still uses my iPhone storyboard on device.
You could always pick the proper storyboard in the appDelegate and present the appropriate root view controller programatically
#interface AppDelegate : UIResponder <UIApplicationDelegate>
{
UIViewController *rvc;
}
Implementation
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
self.window = [[[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]] autorelease];
if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad) {
UIStoryboard *storyboard = [UIStoryboard storyboardWithName:#"IPAD_Storyboard" bundle:nil];
rvc = [storyboard instantiateViewControllerWithIdentifier:#"identifierForController"];
}
else {
UIStoryboard *storyboard = [UIStoryboard storyboardWithName:#"Storyboard" bundle:nil];
rvc = [storyboard instantiateViewControllerWithIdentifier:#"identifierForController"];
}
[self.window addSubview:rvc.view];
self.window.backgroundColor = [UIColor whiteColor];
[self.window makeKeyAndVisible];
return YES;
}
Dont forget to add following things in project's info.plist file (Main Storyboard file base name/ Main Storyboard file base name (iPad))
Hope this helps.
I have duplicated iphone xib into iPad xib by duplicating the target, now my most of the xibs are converted properly into iPad size, however some xibs still showing as iphone size only. Apart from that most of the GUI functionalities like Alert View showing, Action sheet are all not as per iPad. What changes do I need to make to work perfectly for iPad.
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
// Override point for customization after application launch.
self.viewController = [[ViewController alloc] initWithNibName:#"ViewController" bundle:nil];
self.window.rootViewController = self.viewController;
[self.window makeKeyAndVisible];
return YES;
}
Edit: GUI ISSUE I have given two option in that Action sheet YES and NO, only YES showing NO is hiding somewhere..
thanks
Problem is not with conversion, Its with the usage of Action sheet in ipad. Check how to use Action sheet in ipad,
http://developer.apple.com/library/ios/#documentation/uikit/reference/UIActionSheet_Class/Reference/Reference.html
it may fix your problem
You aren't loading the correct NIB when the app starts. This is the code provided by the Xcode "Single View" App Template, which detects the device and loads the appropriate NIB file:
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
// Override point for customization after application launch.
if ([[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPhone) {
self.viewController = [[MainViewController alloc] initWithNibName:#"MainViewController_iPhone" bundle:nil];
} else {
self.viewController = [[MainViewController alloc] initWithNibName:#"MainViewController_iPad" bundle:nil];
}
self.window.rootViewController = self.viewController;
[self.window makeKeyAndVisible];
return YES;
}
If my project supports iOS versions 4.3 and up, how can I enable autolayout in iOS6 only, but disable it to the lower versions?
if you are using storyboards, create two storyboards, one with auto-layout on, and other with auto-layout off. Then one way to check is to load either one based on os version.
i used this little macro
#define SYSTEM_VERSION_GREATER_THAN_OR_EQUAL_TO(v) ([[[UIDevice currentDevice] systemVersion] compare:(v) options:NSNumericSearch] != NSOrderedAscending)
this should work too (probably better in some cases then above):
if ([NSLayoutConstraint class]) {
// >= 6.0
} else {
// < 6.0
}
and then in my appDelegate:
UIStoryboard *mainStoryboard = nil;
if (SYSTEM_VERSION_GREATER_THAN_OR_EQUAL_TO(#"6.0"))
{
mainStoryboard = [UIStoryboard storyboardWithName:#"AutoLayoutStoryboard" bundle:nil];
}
else
{
mainStoryboard = [UIStoryboard storyboardWithName:#"NoAutoLayoutStoryboard" bundle:nil];
}
//load initial view controller
UIViewController *rootView = [mainStoryboard instantiateInitialViewController];
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
self.window.rootViewController = rootView;
[self.window makeKeyAndVisible];
ADD: if you are using nibs, and want to enable auto-layout for iOS6 only, you can create a storyboard (or nibs) with auto-layout on, and load them using above version check
Either you should use two xib files or you should check it programmatically before writing code of auto layouts and constraints.
I am attempting to use both storyboards for my iOS project, but I cannot get the code to switch to the appropriate storyboards. Instead, the code does absolutely nothing. Is it that I do not have a setting set correctly that controls the switch? The main storyboard for devices not of the iPhone 5, is called MainStoryboard. The iphone 5 appropriate layout is called iphone5. I'm thinking this may be a project configuration setting issue. (This is in my appdelegate.m file).
-(void)initializeStoryBoardBasedOnScreenSize {
if ([UIDevice currentDevice].userInterfaceIdiom == UIUserInterfaceIdiomPhone)
{ // The iOS device = iPhone or iPod Touch
CGSize iOSDeviceScreenSize = [[UIScreen mainScreen] bounds].size;
if (iOSDeviceScreenSize.height == 480)
{ // iPhone 3GS, 4, and 4S and iPod Touch 3rd and 4th generation: 3.5 inch screen (diagonally measured)
// Instantiate a new storyboard object using the storyboard file named Storyboard_iPhone35
UIStoryboard *iPhone35Storyboard = [UIStoryboard storyboardWithName:#"MainStoryboard" bundle:nil];
// Instantiate the initial view controller object from the storyboard
UIViewController *initialViewController = [iPhone35Storyboard instantiateInitialViewController];
// Instantiate a UIWindow object and initialize it with the screen size of the iOS device
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
// Set the initial view controller to be the root view controller of the window object
self.window.rootViewController = initialViewController;
// Set the window object to be the key window and show it
[self.window makeKeyAndVisible];
}
if (iOSDeviceScreenSize.height == 568)
{ // iPhone 5 and iPod Touch 5th generation: 4 inch screen (diagonally measured)
// Instantiate a new storyboard object using the storyboard file named Storyboard_iPhone4
UIStoryboard *iPhone4Storyboard = [UIStoryboard storyboardWithName:#"iphone5" bundle:nil];
// Instantiate the initial view controller object from the storyboard
UIViewController *initialViewController = [iPhone4Storyboard instantiateInitialViewController];
// Instantiate a UIWindow object and initialize it with the screen size of the iOS device
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
// Set the initial view controller to be the root view controller of the window object
self.window.rootViewController = initialViewController;
// Set the window object to be the key window and show it
[self.window makeKeyAndVisible];
}
} else if ([UIDevice currentDevice].userInterfaceIdiom == UIUserInterfaceIdiomPad)
{ // The iOS device = iPad
UISplitViewController *splitViewController = (UISplitViewController *)self.window.rootViewController;
UINavigationController *navigationController = [splitViewController.viewControllers lastObject];
splitViewController.delegate = (id)navigationController.topViewController;
}
}
I suggest just using 1 storyboard for handling the iPhone 5 vs iPhone 3-4S screen sizes.
When your Storyboard is open, there is a button at the bottom that toggles between the 2 sizes-- you can see in real-time how things will look.
The button is to the left of the Zoom in % Zoom out buttons in the bottom right corner, and looks like this:
To handle how your object's frame & position will be affected by the screen size change-- you need to set the autosizing properties for each object in your view. You can do this by selecting an object, and in the right Inspector panel, Select the Size inspector like so:
You see those red lines in the Autosizing box? Play around with them to see how they will effect your object. The inner ones relate to the size (if the width, or height stretches), and the outer ones relate to the position.
I'm not sure about your apps layout but from experience you will probably have to mess with the inner vertical line (how the height will change), and the bottom line (you want that to stay near the bottom).
The more you mess around with each the more you will see what each does.