Transferring to another ViewController - ios

I am currently loading another viewcontroller on this code
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
NewViewController *controller = [[NewController alloc]init];
controller.licensed =#"NO";
controller.delegate = self;
self.window.rootViewController = controller;
self.window.backgroundColor = [UIColor clearColor];
[self.window makeKeyAndVisible];
But the problem is when the NewViewController loads. The subviews of the previous view controller is in the background of the NewViewController
[self.rectHolder performSelectorOnMainThread:#selector(removeFromSuperview) withObject:nil waitUntilDone:NO];
[self.btnSignup performSelectorOnMainThread:#selector(removeFromSuperview) withObject:nil waitUntilDone:NO];
[self.view removeFromSuperview];
I tried to use this, but the subviews is still in the background of the new view controller
Edit:
I also tried to use this
NewViewController* viewController = [[NewViewController alloc] init];
viewController.licensed = #"NO";
[self presentViewController:viewController animated:YES completion:nil];
But the subViews of my previous viewcontroller is still in the background

Related

Switching root view controller

I've an app with UINavigationController already, but i want to switch to UITabBarController, the problem is when i switch to UItab from beginning it doesn't work, so i'm switching it in a delegate method but it doesn't work either!
all code in the app delegate.
self.navigationController = [[UINavigationController alloc] initWithRootViewController:[[UIViewController alloc] init]];
self.tabBarController = [[UITabBarController alloc] init];
if ([PFUser currentUser]) {
// Present wall straight-away
[self presentWallViewControllerAnimated:NO];
} else {
// Go to the welcome screen and have them log in or create an account.
[self presentLoginViewController];
}
[PFAnalytics trackAppOpenedWithLaunchOptions:launchOptions];
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
self.window.rootViewController = self.navigationController;
[self.window makeKeyAndVisible];
The delegate method i want to switch on it:
- (void)presentWallViewControllerAnimated:(BOOL)animated {
NSLog(#"Called:presentWallViewControllerAnimated ");
// self.navigationController = nil;
self.tabBarController = [[UITabBarController alloc] init];
PAWWallViewController *wallViewController = [[PAWWallViewController alloc] initWithNibName:nil bundle:nil];
wallViewController.delegate = self;
// Set up the first View Controller
UIViewController *vc1 = [[UIViewController alloc] init];
vc1.view.backgroundColor = [UIColor orangeColor];
vc1.tabBarItem.title = #"Orange";
vc1.tabBarItem.image = [UIImage imageNamed:#"heart"];
// Set up the second View Controller
UIViewController *vc2 = [[UIViewController alloc] init];
vc2.view.backgroundColor = [UIColor purpleColor];
vc2.tabBarItem.title = #"Purple";
vc2.tabBarItem.image = [UIImage imageNamed:#"star"];
// Set up the Tab Bar Controller to have two tabs
[self.tabBarController setViewControllers:#[ vc1, vc2]];
self.window.rootViewController = self.tabBarController;
[self.window makeKeyAndVisible];
// [self.window addSubview:tabBarController.view];
// [self.navigationController setViewControllers:#[ tabBarController ] animated:animated];
}
Remember to handle the view transition:
UIViewController *vc = // any vc that's initialized properly
window.rootViewController = vc;
[UIView transitionWithView:window
duration:0.3 // 0.0 for immediate
options:UIViewAnimationOptionTransitionCrossDissolve // several enums to choose from here
animations:nil
completion:nil];
and you don't need makeKeyAndVisible after the first time.
You called - (void)presentWallViewControllerAnimated:(BOOL)animated but in the end of didFinishLaunchingWithOptions you called
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
self.window.rootViewController = self.navigationController;
[self.window makeKeyAndVisible];
So the tab bar will never works !

Custom Navigation controller in Storyboard

Inside this i am creating the custom navigation controller and i have view as storyboard but that view is not loading
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
//create the navigation controller and add the controllers view to the window
_navigationController = [[UINavigationController alloc] init];
[self.window addSubview:[self.navigationController view]];
//check if the first viewcontroller eixsts, otherwise create it
if(self.firstViewController == nil)
{
ViewController *firstView = (ViewController *)[mainStoryBoard instantiateViewControllerWithIdentifier:#"mainView123"];
// ViewController *firstView = [[ViewController alloc] init];
self.firstViewController = firstView;
}
//push the first viewcontroller into the navigation view controller stack
[self.navigationController pushViewController:self.firstViewController animated:YES];
self.window.backgroundColor = [UIColor whiteColor];
[self.window makeKeyAndVisible];
firs you should set your navigation as rootviewcontroller then try something like this.
UIStoryboard *storyboard =[UIStoryboardstoryboardWithName:#"MainStoryboard_iPhone" bundle:nil];
MyNewViewController *myVC = (MyNewViewController *)[storyboard instantiateViewControllerWithIdentifier:#"myViewCont"];
self.firstViewController = myVc;

Customize View Controller Stack on didFinishLaunching

I am trying to present a tutorial/login/introduction view controller for my app on first launch using the following code:
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
self.window.backgroundColor = [UIColor whiteColor];
[self.window makeKeyAndVisible];
UIViewController *firstController = [[UIViewController alloc] init];
[self.window setRootViewController:firstController];
if ([self shouldShowIntro]) {
IntroViewController *introViewController = [[IntroViewController alloc] init];
[firstController presentViewController:introViewController animated:NO completion:nil];
}
return YES;
}
This works fine, but there is an annoying visual effect that takes place... Before you see the IntroViewController, there is a split second where the firstController is visible. I tried presenting the IntroViewController before setting the rootViewController of the window, but this (not surprisingly) results in the following warning:
Warning: Attempt to present <IntroViewController: 0x7fd8eb3362f0> on <UIViewController: 0x7fd8eb335180> whose view is not in the window hierarchy!
How can I modally present the IntroViewController without this annoying visual flash? I want IntroViewController to already be showing after the launch screen disappears and be able to be dismissed modally.
The following works for me with no flicker running on iOS 8.1 on an iPhone 6 and in the simulator. I used SDK version 8.1 and I think your SDK level is different because I got different warnings and results than you using your provided code.
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
self.window.backgroundColor = [UIColor whiteColor];
[self.window makeKeyAndVisible];
UIViewController *firstController = [[UIViewController alloc] init];
firstController.view.backgroundColor = [UIColor blueColor];
[self.window setRootViewController:firstController];
dispatch_async(dispatch_get_main_queue(), ^{
UIViewController* modalViewController = [[UIViewController alloc] init];
modalViewController.view.backgroundColor = [UIColor grayColor];
[firstController presentViewController: modalViewController animated: NO completion: nil];
});
// dismiss after a few seconds..
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(5 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
[firstController dismissViewControllerAnimated: YES completion: nil];
});
return YES;
}
Update with MMDrawerController:
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
self.window.backgroundColor = [UIColor whiteColor];
[self.window makeKeyAndVisible];
MMDrawerController *drawerController = [[MMDrawerController alloc] init];
drawerController.centerViewController = [[UIViewController alloc] init];
drawerController.centerViewController.view.backgroundColor = [UIColor blueColor];
drawerController.rightDrawerViewController = [[UIViewController alloc] init];
drawerController.rightDrawerViewController.view.backgroundColor = [UIColor greenColor];
drawerController.openDrawerGestureModeMask = MMOpenDrawerGestureModeAll;
drawerController.closeDrawerGestureModeMask = MMOpenDrawerGestureModeAll;
[self.window setRootViewController:drawerController];
dispatch_async(dispatch_get_main_queue(), ^{
UIViewController* modalViewController = [[UIViewController alloc] init];
modalViewController.view.backgroundColor = [UIColor grayColor];
[drawerController presentViewController: modalViewController animated: NO completion: nil];
});
// dismiss after a few seconds..
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(5 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
[drawerController dismissViewControllerAnimated: YES completion: nil];
});
return YES;
}
Also, per you comment it sounds as if having the pre-loaded view is key. Try invoking [firstController view] and [modalController view] before you present to ensure they're loaded.
try moving this line below the code where you set your view controllers.
[self.window makeKeyAndVisible];
something like this:
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
self.window.backgroundColor = [UIColor whiteColor];
UIViewController *firstController = [[UIViewController alloc] init];
[self.window setRootViewController:firstController];
if ([self shouldShowIntro]) {
IntroViewController *introViewController = [[IntroViewController alloc] init];
[firstController presentViewController:introViewController animated:NO completion:nil];
}
[self.window makeKeyAndVisible];
return YES
}
Put
if ([self shouldShowIntro]) {
IntroViewController *introViewController = [[IntroViewController alloc] init];
[firstController presentViewController:introViewController animated:NO completion:nil];
}
in to the viewDidAppear function of FirstViewController rather than in the AppDelegate. That should suppress the warning and perform the operation smoothly.

Can't pop iOS viewController. Not sure, but I think it's something with the Navigation Controller

I'm having trouble trying to pop a view
App Delegate
#implementation MAAppDelegate
#synthesize navController;
#synthesize detailViewController;
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
// Init the navController for the Master Detail View of the grade cells
UINavigationController *navController = [[UINavigationController alloc] init];
detailViewController = [[UIViewController alloc] init]; //step6
navController = [[UINavigationController alloc] initWithRootViewController:[[MAController alloc] init]]; //step7
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
self.window.backgroundColor = [UIColor whiteColor];
self.window.rootViewController = navController; //step8
[self.window makeKeyAndVisible];
// Set MAController as rootViewController
//self.window.rootViewController = [[MAController alloc] init];
self.window.backgroundColor = [UIColor whiteColor];
[self.window makeKeyAndVisible];
// Use the insanely cool TSMessages to show network alerts
[TSMessage setDefaultViewController: self.window.rootViewController];
return YES;
}
First part of viewController
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view.
[self.navigationController setNavigationBarHidden:YES];
UIBarButtonItem *newBackButton = [[UIBarButtonItem alloc] initWithTitle:#"Home" style:UIBarButtonItemStyleBordered target:self action:#selector(home:)];
self.navigationItem.leftBarButtonItem=newBackButton;
Later, when I change the viewController
NSLog(#"Opened progress report");
UIViewController *detailViewControl = [[UIViewController alloc] init];
// Set progress report as the view controller
[self.navigationController pushViewController:detailViewControl animated:YES];
UIImage *background = [UIImage imageNamed:#"bg"];
// Add static image bg
self.backgroundImageView = [[UIImageView alloc] initWithImage:background];
self.backgroundImageView.contentMode = UIViewContentModeScaleAspectFill;
[self.view addSubview:self.backgroundImageView];
// Add blurred layer to image when tableView goes in front of it
self.blurredImageView = [[UIImageView alloc] init];
self.blurredImageView.contentMode = UIViewContentModeScaleAspectFill;
self.blurredImageView.alpha = 0;
[self.blurredImageView setImageToBlur:background blurRadius:10 completionBlock:nil];
[self.view addSubview:self.blurredImageView];
[self.navigationController setNavigationBarHidden:NO];
So I don't understand why that when I do this, a selector from the button (that I know fires, because I get Righthtere in my log):
-(void)home:(UIBarButtonItem *)sender {
NSLog(#"Righthtere");
// Set progress report as the view controller
[self.navigationController popToViewController:self animated:YES];
}
It doesn't go back to the initial view controller.
You seem to be confusing popToViewController and popViewControllerAnimated. popViewControllerAnimated removes the current view from the stack and brings the new stack top the active view controller. popToViewController pops the stack until the listed view controller is on top of the stack.
Since you are calling popToViewController with self, it will look and see that the requested view controller is already on top of the stack and do nothing. If you wish to go back one view controller then your call should be.
[self.navigationController popViewControllerAnimated:YES];
I use the below code to pop the previous viewcontroller in iOS 8.
[self presentModalViewController:viewcontroller animated:YES];

Issue Presenting View modally after a UISplitView loads

I'm new to UISplitView development, so I'm sure there is something obvious I'm doing wrong. I have a basic UISplitView iPad app that loads up with two UITableView controllers when the app launches. This works just fine.
What I am trying to do is immediately upon launch, presenting an "authentication" view modally so that a user will need to login before continuing. Here is the code I have so far which compiles and works without breaking, but the view is not showing.
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
MasterViewController *masterViewController = [[MasterViewController alloc] initWithNibName:#"MasterViewController" bundle:nil];
UINavigationController *masterNavigationController = [[UINavigationController alloc] initWithRootViewController:masterViewController];
DetailViewController *detailViewController = [[DetailViewController alloc] initWithNibName:#"DetailViewController" bundle:nil];
UINavigationController *detailNavigationController = [[UINavigationController alloc] initWithRootViewController:detailViewController];
self.splitViewController = [[UISplitViewController alloc] init];
self.splitViewController.delegate = detailViewController;
self.splitViewController.viewControllers = [NSArray arrayWithObjects:masterNavigationController, detailNavigationController, nil];
masterViewController.detailViewController = detailViewController;
masterViewController.managedObjectContext = self.managedObjectContext;
self.window.rootViewController = self.splitViewController;
[self presentAuthenticate];
[self.window makeKeyAndVisible];
applicationDidLaunch = YES;
return applicationDidLaunch;
}
- (void) presentAuthenticate {
AuthenticateViewController *loginController = [[AuthenticateViewController alloc] initWithNibName:#"AuthenticateViewController" bundle:nil];
[loginController setModalTransitionStyle:UIModalTransitionStyleCoverVertical];
[loginController setModalPresentationStyle:UIModalPresentationFormSheet];
if ([self.splitViewController respondsToSelector:#selector(presentViewController:animated:completion:)]) {
[self.splitViewController presentViewController:loginController animated:NO completion:nil];
} else {
[self.splitViewController presentModalViewController:loginController animated:NO]; //iOS 4 works fine with or without animation
}
}
I defined the AuthenticateViewController as a View with a few textfields in it and have it wired to the File's Owners view.
Thanks ahead of time!
A viewcontroller will not allow to push/present on anotherview unless and until the view is complete loading.
Simple saying we are not allow to call presentModalViewController/pushViewController in a viewcontroller viewDidLoad/viewWillAppear. we need to call this in viewDidAppear.
I had the same issue you said.
Some Solution I can say are,
Do the loading of AuthenticateViewController after [self.window makeKeyAndVisible]; and in a performSelctor (may be with a delay).
Move the code to display AuthenticateViewController in SplitView's DetailView controller viewDidAppear.
thanks,
Naveen Shan

Resources