Slide Segue in Swift
I test with the following modification, and it work well.
func valForDirection() -> Int {
return direction == Direction.Left ? 1 : -1
}
If sliding to left, the destView's originX should be it's width. else -width.
Creating a sliding segue in Swift
That effect is achieved using custom interactive transitions, which were introduced in iOS7. Here are a few tutorials to check out:
- See Custom Transitions Using View Controllers. https://developer.apple.com/videos/wwdc/2013/
- http://www.thinkandbuild.it/ios7-custom-transitions/
- http://objectivetoast.com/2014/04/14/interactive-transitions/
- http://www.teehanlax.com/blog/custom-uiviewcontroller-transitions/
- This one gives many examples of the effects that can be achieved. http://www.appcoda.com/custom-view-controller-transitions-tutorial/
When I was implementing this I found that, for reusability, it was best to have one subclass of UIPercentDrivenInteractiveTransition
(which we'll call TransitionManager
) that implemented the protocols UIViewControllerTransitioningDelegate
, UINavigationControllerDelegate
and UIViewControllerAnimatedTransitioning
.
- Then, if you need to present a UIViewController
modally with your custom transition: in prepareForSegue
set:
destinationViewController.modalPresentationStyle = .Custom
destinationViewController.transitioningDelegate = TransitionManager()
- If you're using a UINavigationController
it's even easier, all you need to do it set the UINavigationController
's delegate
to your TransitionManager
.
Hopefully that should start to make some sense once you've gone through the tutorials.
Slide Segue in Swift
I test with the following modification, and it work well.
func valForDirection() -> Int {
return direction == Direction.Left ? 1 : -1
}
If sliding to left, the destView's originX should be it's width. else -width.
iOS Segue - Left to Right -
This is how I achieve the effect without requiring a nav-controller. Try this instead:
Swift 4:
import UIKit
class SegueFromLeft: UIStoryboardSegue {
override func perform() {
let src = self.source
let dst = self.destination
src.view.superview?.insertSubview(dst.view, aboveSubview: src.view)
dst.view.transform = CGAffineTransform(translationX: -src.view.frame.size.width, y: 0)
UIView.animate(withDuration: 0.25,
delay: 0.0,
options: .curveEaseInOut,
animations: {
dst.view.transform = CGAffineTransform(translationX: 0, y: 0)
},
completion: { finished in
src.present(dst, animated: false, completion: nil)
}
)
}
}
Swift 3:
import UIKit
class SegueFromLeft: UIStoryboardSegue
{
override func perform()
{
let src = self.sourceViewController
let dst = self.destinationViewController
src.view.superview?.insertSubview(dst.view, aboveSubview: src.view)
dst.view.transform = CGAffineTransformMakeTranslation(-src.view.frame.size.width, 0)
UIView.animateWithDuration(0.25,
delay: 0.0,
options: UIViewAnimationOptions.CurveEaseInOut,
animations: {
dst.view.transform = CGAffineTransformMakeTranslation(0, 0)
},
completion: { finished in
src.presentViewController(dst, animated: false, completion: nil)
}
)
}
}
Then in the storyboard, click on the segue you'd like to change. In the attributes inspector change the type to 'Custom' and change the class to 'SegueFromLeft'
Create sliding animation in View Swift
To create this segue, you will need to create a UIStoryBoardSegue
file.
In that file, put this code:
override func perform() {
var firstVCView = self.sourceViewController.view as UIView!
var secondVCView = self.destinationViewController.view as UIView!
// Get the screen width and height.
let screenWidth = UIScreen.mainScreen().bounds.size.width
let screenHeight = UIScreen.mainScreen().bounds.size.height
// Specify the initial position of the destination view.
secondVCView.frame = CGRectMake(0.0, -screenHeight, screenWidth, screenHeight)
firstVCView.frame = CGRectMake(0.0, 0.0, screenWidth, screenHeight)
// Access the app's key window and insert the destination view above the current (source) one.
let window = UIApplication.sharedApplication().keyWindow
window?.insertSubview(secondVCView, aboveSubview: firstVCView)
// Animate the transition.
UIView.animateWithDuration(0.4, animations: { () -> Void in
firstVCView.frame = CGRectOffset(firstVCView.frame, 0.0, screenHeight)
secondVCView.frame = CGRectOffset(secondVCView.frame, 0.0, screenHeight)
}) { (Finished) -> Void in
self.sourceViewController.presentViewController(self.destinationViewController as! UIViewController,
animated: false,
completion: nil)
}
}
Control click to create a segue. Select 'custom'. Then, type in the segue file name in the attributes inspector. Your custom segue is good to go!
Hope this helped.
Create a sliding animation with Swift
The easiest (built-in) thing that does what you want is a UIPageViewController
. This will automatically do the gesture correctly (so it's like springboard).
Transition Screens from Left to Right?
You could write a custom transition that would not be too difficult but if you don't want to go that route here is a simple fix that will work. Click on the segue and unclick/disable animates on the segue. Then in prepareForSegue use this.
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if let _ = segue.destination as? NextViewController{
let trans = CATransition()
trans.type = kCATransitionMoveIn
trans.subtype = kCATransitionFromLeft
trans.timingFunction = CAMediaTimingFunction(name: kCAMediaTimingFunctionEaseInEaseOut)
trans.duration = 0.35
self.navigationController?.view.layer.add(trans, forKey: nil)
}
}
Feel free to explore the other options with CATransition types. You can have some serious fun with them. Now I am guessing you want to have the reverse for the back button press in the next view controllers. You will have to replace the back button and to intercept the back press and pop without animation so you can add your own animation. Here is what that would look like.
override func viewDidLoad() {
super.viewDidLoad()
self.navigationItem.leftBarButtonItem = UIBarButtonItem(title: "Back", style: .plain, target: self, action: #selector(backTapped))
}
@objc func backTapped() {
let trans = CATransition()
trans.type = kCATransitionMoveIn
trans.subtype = kCATransitionFromRight
trans.duration = 0.3
self.navigationController?.view.layer.add(trans, forKey: nil)
navigationController?.popViewController(animated: false)
}
Again the other option would be use UIViewControllerAnimatedTransitioning but depending on your skill level and comfort with animations I find the above an easy implementation.
Related Topics
Sliding One Swiftui View Out from Underneath Another
Giving Physics to Tiles of Sktilemapnode in Xcode 8
React Native Sending Events to JavaScript in Swift
How to Navigate to a New View from Navigationbar Button Click in Swiftui
Nsbutton with Round Corners and Background Color
Apple MACh-O Linker Error, After Changing Project Name
Ios-Charts Library: X-Axis Labels Without Backing Data Not Showing
Single and Double Taps on Uitableviewcell in Swift 3
Swiftui Navigationview Trying to Pop to Missing Destination (Monoceros)
Easiest Way to Find Square Root in Swift
Is Code Coverage Already Working for Swift
Centering the Camera on a Node in Swift Spritekit
Cut a Circle Out of a Uiview Using Mask
How to Specify That a Generic Is a Value Type