From my onboarding viewcontroller i need to transition to my tabBarController which is also a navigationController and i want to make it as a root viewcontroller afterwards.
#objc func willGoToMain(sender: UIButton!) {
let tabBarController = TabBarController()
let navigationController = UINavigationController(rootViewController: tabBarController)
navigationController.isNavigationBarHidden = true
self.present(tabBarController, animated: true, completion: nil)
}
Thread 1: "Application tried to present modally a view controller <MyStarterProject.TabBarController: 0x7f9bd8011400> that has a parent view controller <UINavigationController: 0x7f9bd7022800>
I like to transition it like a modal presentation or cross dissolve. not just to appeared as a rootviewcontroller all of a sudden.
Here's what i'm trying to do and this solves my problem.
#objc func willGoToMain(sender: UIButton!) {
guard let window = UIApplication.shared.keyWindow else {
return
}
let tabbarController = TabBarController()
let navigationController = UINavigationController(rootViewController: tabbarController)
navigationController.isNavigationBarHidden = true
window.rootViewController = navigationController
window.makeKeyAndVisible()
let options: UIView.AnimationOptions = .transitionCrossDissolve
let duration: TimeInterval = 0.3
UIView.transition(with: window, duration: duration, options: options, animations: {}, completion:
{ completed in
// maybe do something on completion here
})
}
Change this:
self.present(tabBarController, animated: true, completion: nil)
with this:
self.present(navigationController, animated: true, completion: nil)
Please try this one.
let storyboard = UIStoryboard(name: "Main", bundle: nil)
let mainTabBarController = storyboard.instantiateViewController(identifier: "MainTabBarController")
mainTabBarController.modalPresentationStyle = .fullScreen
self.present(mainTabBarController, animated: true, completion: nil)
If you need more details. please visit this blog
https://fluffy.es/how-to-transition-from-login-screen-to-tab-bar-controller/
I am trying to navigate from one view controller to other using tap gesture navigation. I want add transition animation into it. I tried with two ways but it didn't worked for me. -
First approach :
UIView.animate(withDuration: 0.5) { ()-> Void in
let storyBoard: UIStoryboard = UIStoryboard(name: "Main", bundle: nil)
let myTabBarController = storyBoard.instantiateViewController(withIdentifier: "profileViewController") as! ProfileViewController
var appDel = UIApplication.shared.delegate as! AppDelegate
appDel.window?.rootViewController = myTabBarController
self.view.layoutIfNeeded()
}
Second approach :
UIView.animate(withDuration: 0.25,
delay: 0.0,
options: [.curveEaseIn],
animations: {
let controller = self.storyboard!.instantiateViewController(withIdentifier: "mainMenuViewController") as! MainMenuViewController
self.addChild(controller)
self.view.addSubview(controller.view)
controller.didMove(toParent: self)
}, completion: nil)
Can anybody please tell me whats the solution ?
try this to present
let storyBoard : UIStoryboard = UIStoryboard(name: "Main", bundle:nil)
let nextViewController = storyBoard.instantiateViewController(withIdentifier: "profileViewController") as! ProfileViewController
self.present(nextViewController, animated:true, completion:nil)
If you present a ViewController then you can only Dismiss it, It can be done by below code
self.dismiss(animated: true, completion: nil)
To push
let storyBoard : UIStoryboard = UIStoryboard(name: "Main", bundle:nil)
let nextViewController = storyBoard.instantiateViewController(withIdentifier: "profileViewController") as! ProfileViewController
self.navigationController?.pushViewController(nextViewController, animated:true)
If you push a ViewController then you can only Pop it, It can be done by below code
self.navigationController?.popViewController(animated: true)
I'm trying to change my rootViewController with a slide-from-right animation.
I know how to do it with a flip animation:
let mainStoryboard: UIStoryboard = UIStoryboard(name: "Main", bundle: nil)
let viewController = mainStoryboard.instantiateViewControllerWithIdentifier("LandingViewController")
UIView.transitionWithView( UIApplication.sharedApplication().keyWindow!,
duration: 0.5,
options: UIViewAnimationOptions.TransitionFlipFromLeft,
animations: { UIApplication.sharedApplication().keyWindow?.rootViewController = viewController; },
completion: nil)
However, UIViewAnimationOptions does NOT have a slide-from-right animation.
How can I achieve this?
on the very first launch of my app i wanna show a Specific View Controller say firstLaunchVC and for that i'm doing this
in my didFinishLaunchingWithOptions
if (itsFirstLaunch){
self.window = UIWindow(frame: UIScreen.mainScreen().bounds)
let mainStoryboard: UIStoryboard = UIStoryboard(name: "Main", bundle: nil)
var initialViewController: UIViewController
initialViewController = mainStoryboard.instantiateViewControllerWithIdentifier("SignupViewController") as! SignupViewController
self.window?.rootViewController = initialViewController
self.window?.makeKeyAndVisible()
}
its working fine but now after completing my signup i want to change my RootViewController to my default ViewController say DefaultVC
appDelegate.window = UIWindow(frame: UIScreen.mainScreen().bounds)
let mainStoryboard: UIStoryboard = UIStoryboard(name: "Main", bundle: nil)
var initialViewController: UIViewController
initialViewController = mainStoryboard.instantiateViewControllerWithIdentifier("DefaultVC") as! UITabBarController
UIView.transitionWithView(self.appDelegate.window!, duration: 0.3, options: .TransitionFlipFromBottom, animations: {() -> Void in
self.appDelegate.window?.rootViewController = initialViewController
self.appDelegate.window?.makeKeyAndVisible()
}, completion: { _ in }
)
its working fine and you can also see that i added animation in this Transition
UIView.transitionWithView(self.appDelegate.window!, duration: 0.3, options: .TransitionFlipFromBottom, animations: {()....
but this animation is not good enough also here we have a lot of options like :
TransitionFlipFromLeft
TransitionFlipFromRight
TransitionCurlUp
TransitionCurlDown
TransitionCrossDissolve
TransitionFlipFromTop
TransitionFlipFromBottom etc...
but none of them are meeting my requirements (the are totally hideous) what i want is the Animation when a ViewController being dismissed i want to slide out the vc from the frame in a direction if anybody can guide me how to do this then it'll be so helpful for me
I had referred to this question and several question about view / view controller transition but still couldn't find an satisfied answer. Most of the solutions suggest to flip the views instead of view controllers. However, the two view controllers in my app have totally different operation and implementation logic, thus I'm avoiding to mix them together.
In my app, I have a modal view controller FrontViewController which is embedded in a NavigationController. After pushing one button on the view, the modal view controller should flip to BackViewController, and vice versa. I had ever tried the following in FrontViewController:
let navi = UINavigationController(rootViewController: backController)
navi.modalPresentationStyle = .CurrentContext
navi.modalTransitionStyle = .FlipHorizontal
self.presentViewController(backController, animated: true, completion: nil)
This works almost as what I want, except that it flips navigation bar as well. Moreover, if I dismiss the modal view, only the view controller on the top of the stack is dismissed, while I failed to get the right parent/presenting controller to dismiss all the other stack controllers in the modal view.
Thus I further tried to prevent viewcontroller stack and use transitionFromViewController in FrontViewController using the same navigation controller instead:
self.navigationController!.addChildViewController(backController)
self.willMoveToParentViewController(nil)
self.navigationController!.transitionFromViewController(self, toViewController: backViewController, duration: 1, options: .TransitionFlipFromLeft, animations: {}, completion: ({Bool -> Void in
self.removeFromParentController()
c.didMoveToParentViewController(self)
}))
Then I got this run time error on executiing: Parent view controller is using legacy containment in call to -[UIViewController transitionFromViewController:toViewController: duration:options:animations:completion:]
So, how to transition between two view controllers while preventing them remain in the view controller stack?
You can add custom transition to the navigation controllers layer just before pushing the view controller.
let transition = CATransition()
transition.duration = 0.3
transition.type = "flip"
transition.subtype = kCATransitionFromLeft
self.navigationController?.view.layer.addAnimation(transition, forKey: kCATransition)
self.navigationController?.pushViewController(viewController!, animated: false)
Note that the animated parameter should be false. Otherwise the default sliding animation will takes place
See this demo for you :
Swift code for flipAnimation :
let mainStory = UIStoryboard(name: "Main", bundle: nil)
let search = mainStory.instantiateViewControllerWithIdentifier("SecondViewController") as! SecondViewController
UIView.beginAnimations("animation", context: nil)
UIView.setAnimationDuration(1.0)
self.navigationController!.pushViewController(search, animated: false)
UIView.setAnimationTransition(UIViewAnimationTransition.FlipFromLeft, forView: self.navigationController!.view, cache: false)
UIView.commitAnimations()
FlipViewController Animation
Output :
Swift 5 - I personally like using this approach.
//PUSH
let secondVC = UIStoryboard.init(name: "Main", bundle: Bundle.main).instantiateViewController(withIdentifier: "secondVC") as! SecondVC
self.navigationController?.pushViewController(secondVC, animated: false)
UIView.transition(from: self.view, to: secondVC.view, duration: 0.85, options: [.transitionFlipFromLeft])
//POP
let firstVC = self.navigationController?.viewControllers[(self.navigationController?.viewControllers.count ?? 2) - 2] as? FirstVC
if let firstView = firstVC?.view{
self.navigationController?.popViewController(animated: false)
UIView.transition(from: self.view, to: firstView, duration: 0.85, options: [.transitionFlipFromRight])
} else {
self.navigationController?.popViewController(animated: true)
}
Swift 3.0 +
Should use UIView's animation block, make sure your viewController in UINavigationController stacks:
let viewController = ViewController(nibName: "xxx", bundle: nil)
UIView.transition(with: self.navigationController!.view, duration: 1.0, options: .transitionFlipFromLeft, animations: {
self.navigationController?.pushViewController(viewController, animated: false)
}, completion: nil)
override func viewWillDisappear(_ animated: Bool) {
super.viewWillDisappear(true)
// for back button
changeTransition()
}
//btnMap.addTarget(self, action: #selector(searchHotelsResultVC.goToMap), for: .touchUpInside)
//btnMap.addTarget(self, action: #selector(MapViewController.backToList), for: .touchUpInside)
func goToMap() {
// for pushing
changeTransition()
navigationController?.pushViewController(settingsVC, animated: false)
}
func backToList() {
// for dismiss
changeTransition()
navigationController?.popViewController(animated: false)
dismiss(animated: true, completion: nil)
}
func changeTransition() {
let transition = CATransition()
transition.duration = 0.5
transition.timingFunction = CAMediaTimingFunction(name: kCAMediaTimingFunctionEaseInEaseOut)
//transition.type = kCATransitionPush
transition.type = "flip"
transition.subtype = kCATransitionFromLeft
navigationController?.view.layer.add(transition, forKey: kCATransition)
}
here Student is NSObjectClass
var Arraydata:[Student] = []
func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) {
let arr = Arraydata[indexPath.row]
if indexPath.row == arr
{
let story = self.storyboard?.instantiateViewController(withIdentifier: "SecondViewController") as! SecondViewController
UIView.beginAnimations("", context: nil)
UIView.setAnimationDuration(1.0)
UIView.setAnimationCurve(UIViewAnimationCurve.easeInOut)
UIView.setAnimationTransition(UIViewAnimationTransition.flipFromRight, for: (self.navigationController?.view)!, cache: false)
self.navigationController?.pushViewController(story, animated: true)
UIView.commitAnimations()
}
}