in my iOS App i need to change the rootviewController of the window in between of app .so when i change my rootviewcontroller dyncamically its flicking the view before its change.but what i want is to give a smooth transition when rootviewcontroller is changed.
i had tried with the following but its not the transition i want.
[UIView transitionWithView:self.window
duration:.8
options:UIViewAnimationOptionTransitionCurlUp
animations:^{
self.window.rootViewController = tabBarControllerMain;
[self.window makeKeyAndVisible];
}
completion:NULL];
i want specific transition like navigationcontroller pushview transition.
can any body give me idea how to achieve that?
Basing on Hardik Darji's answer I've created UIWindow extension to swap rootViewController with configurable animation type that simulates system animations - push, pop, present and dismiss.
Swift 3.
public enum SwapRootVCAnimationType {
case push
case pop
case present
case dismiss
}
extension UIWindow {
public func swapRootViewControllerWithAnimation(newViewController:UIViewController, animationType:SwapRootVCAnimationType, completion: (() -> ())? = nil)
{
guard let currentViewController = rootViewController else {
return
}
let width = currentViewController.view.frame.size.width;
let height = currentViewController.view.frame.size.height;
var newVCStartAnimationFrame: CGRect?
var currentVCEndAnimationFrame:CGRect?
var newVCAnimated = true
switch animationType
{
case .push:
newVCStartAnimationFrame = CGRect(x: width, y: 0, width: width, height: height)
currentVCEndAnimationFrame = CGRect(x: 0 - width/4, y: 0, width: width, height: height)
case .pop:
currentVCEndAnimationFrame = CGRect(x: width, y: 0, width: width, height: height)
newVCStartAnimationFrame = CGRect(x: 0 - width/4, y: 0, width: width, height: height)
newVCAnimated = false
case .present:
newVCStartAnimationFrame = CGRect(x: 0, y: height, width: width, height: height)
case .dismiss:
currentVCEndAnimationFrame = CGRect(x: 0, y: height, width: width, height: height)
newVCAnimated = false
}
newViewController.view.frame = newVCStartAnimationFrame ?? CGRect(x: 0, y: 0, width: width, height: height)
addSubview(newViewController.view)
if !newVCAnimated {
bringSubview(toFront: currentViewController.view)
}
UIView.animate(withDuration: 0.3, delay: 0, options: [.curveEaseOut], animations: {
if let currentVCEndAnimationFrame = currentVCEndAnimationFrame {
currentViewController.view.frame = currentVCEndAnimationFrame
}
newViewController.view.frame = CGRect(x: 0, y: 0, width: width, height: height)
}, completion: { finish in
self.rootViewController = newViewController
completion?()
})
makeKeyAndVisible()
}
}
Based on this Apple's documentation
UIViewController *viewControllerToBeShown=[[UIViewController alloc]init];
//viewControllerToBeShown.view.frame = self.view.frame;
viewControllerToBeShown.view.backgroundColor = [UIColor orangeColor];
AppDelegateClass *yourAppDelegate =(AppDelegateClass*)[UIApplication sharedApplication].delegate;
UIView *myView1 = yourAppDelegate.window.rootViewController.view;
UIView *myView2 = viewControllerToBeShown.view;
myView2.frame = yourAppDelegate.window.bounds;
[yourAppDelegate.window addSubview:myView2];
CATransition* transition = [CATransition animation];
transition.startProgress = 0;
transition.endProgress = 1.0;
transition.type = kCATransitionPush;
transition.subtype = kCATransitionFromRight;
transition.duration = 5.0;
// Add the transition animation to both layers
[myView1.layer addAnimation:transition forKey:@"transition"];
[myView2.layer addAnimation:transition forKey:@"transition"];
myView1.hidden = YES;
myView2.hidden = NO;
yourAppDelegate.window.rootViewController = viewControllerToBeShown;
Swift
guard let appDelegate = UIApplication.shared.delegate,
let appDelegateWindow = appDelegate.window,
let appDelegateView = window.rootViewController?.view,
let viewContollersView = viewController.view else {
return
}
viewContollersView.frame = (appDelegateWindow?.bounds)!
appDelegate.window??.addSubview(viewContollersView)
let transition = CATransition()
transition.startProgress = 0
transition.endProgress = 1.0
transition.type = kCATransitionPush
transition.subtype = kCATransitionFromRight
transition.duration = 0.35
appDelegateView.layer.add(transition, forKey: "transition")
viewContollersView.layer.add(transition, forKey: "transition")
appDelegateView.isHidden = true
viewContollersView.isHidden = false
appDelegateWindow?.rootViewController = viewController
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