Ever since apple introduced the iPhone 6s with its 3d touch features more apps have been integrating the new way of using the apps. It means that they have added some new UI interactions such as application shortcuts and the peek and pop.
Integrating the peek and pop feature into your app is a task in it self as you have to read documentation and try to understand how it works and how the 3d touch comes into to play . The idea behind the peek and pop feature is that when you have a image or a email you can press it and have a peek (preview) to see if its important or not and if it is important you can pop the screen that means if you press it harder you can maximise the screen .
This i thought would be fun to use in our end project and it would be good to learn how to do it and what the benefits of having it in your app. It was a challenge trying to implement it but nothing worth having comes easy or so they say . Below you will find a nice little explanation of how i integrated peek and pop into our app.
In order to implement the 3D touch into your app you need to check if the 3D touch is supported. You can check this by asking the trait collection object for the value of the forceTouchCapability property.
You have to do this in the viewDidLoad . the code should look something like this
if 3D Touch is available
override func viewDidLoad() {
super.viewDidLoad()
if( traitCollection.forceTouchCapability == .Available) {
registerForPreviewingWithDelegate(self, sourceView: view)
}
}
If it is available we are now able to register the view controller for the peek and pop by calling the registerForPreviewingWithDelegate:sourceView:
After we have done this we need to implement it into the delegate which we have just agreed to be the delegate of the peeking and the popping, we need to implement the delegate method. We need two methods which are declared in UIViewControlerPreviewDelegate . Before we can use these methods we need to add the protocol UIViewControlerPreviewDelegate to the superclass which looks something like this :
class StationsViewController:
UICollectionViewController, UIViewControllerPreviewingDelegate {
}
After we have implemented the preview delegate we need to setup the controller for the peeking.This method will return a view controller that we want to display in our case it will be the now playing controller.
But before we can start writing the code we need to figure out what station the user is touching so we can find the cell . For this we can ask the view controller for the index path of the item and its location. The location is then passed as an argument by the delegate method. Should the cell be empty we should get an error.
The code looks something like this
func previewingContext(previewingContext:
UIViewControllerPreviewing,viewControllerForLocation
location: CGPoint) -> UIViewController? {
let indexPath = collectionView?.indexPathForItemAtPoint(location),
cell = collectionView?.cellForItemAtIndexPath(indexPath) else { return nil }
}
The next step is that we need to create a instance of the class. we can do this by adding a storyboard ID to the now playing controller scene in the storyboard. if this view controller fails it should crash.
The code should look like this
let detailViewController
= storyboard?.instantiateViewControllerWithIdentifier("nowPlaying")
as? NowPlayingController else { return nil }
}
Once this has step works , we can fetch the data from the datasource and pass it to the nowplayingcontroller so it can set up the imageview and the current station. Which looks like this :
detailViewController.image = previewDetail.stationImage
detailViewController.currentStation = previewDetail
if you check the code in the stationsviewcontroller, you will see that the view did load method is there to check to see if they image and station property is available, if thats the case then the station and image are set.
Once we have done this we can add the preferred content size of the controller instance which i had set to this :
detailViewController.preferredContentSize = CGSize(width: 600, height: 600)
The last step is to set the sourceRect property. This property accepts a CGRect and will blur everything around it and keep everything inside the rect sharp. the rect should be the same frame as the cell and then return the instance.
previewingContext.sourceRect = cell.frame
return detailViewController
setting up the popping was a bit easier as there was only one function for this .
All you need to do is use the same view controller that we just created, and implement the delegate method and call the showviewcontroller:sender method
func previewingContext(previewingContext:
UIViewControllerPreviewing,
commitViewController viewControllerToCommit: UIViewController) {
showViewController(viewControllerToCommit, sender: nil)
}
And thats all there is to it !
Once you run the app and press on a image you should be able to peek and pop it like so :
Integrating the peek and pop feature into your app is a task in it self as you have to read documentation and try to understand how it works and how the 3d touch comes into to play . The idea behind the peek and pop feature is that when you have a image or a email you can press it and have a peek (preview) to see if its important or not and if it is important you can pop the screen that means if you press it harder you can maximise the screen .
This i thought would be fun to use in our end project and it would be good to learn how to do it and what the benefits of having it in your app. It was a challenge trying to implement it but nothing worth having comes easy or so they say . Below you will find a nice little explanation of how i integrated peek and pop into our app.
In order to implement the 3D touch into your app you need to check if the 3D touch is supported. You can check this by asking the trait collection object for the value of the forceTouchCapability property.
You have to do this in the viewDidLoad . the code should look something like this
if 3D Touch is available
override func viewDidLoad() {
super.viewDidLoad()
if( traitCollection.forceTouchCapability == .Available) {
registerForPreviewingWithDelegate(self, sourceView: view)
}
}
If it is available we are now able to register the view controller for the peek and pop by calling the registerForPreviewingWithDelegate:sourceView:
After we have done this we need to implement it into the delegate which we have just agreed to be the delegate of the peeking and the popping, we need to implement the delegate method. We need two methods which are declared in UIViewControlerPreviewDelegate . Before we can use these methods we need to add the protocol UIViewControlerPreviewDelegate to the superclass which looks something like this :
class StationsViewController:
UICollectionViewController, UIViewControllerPreviewingDelegate {
}
After we have implemented the preview delegate we need to setup the controller for the peeking.This method will return a view controller that we want to display in our case it will be the now playing controller.
But before we can start writing the code we need to figure out what station the user is touching so we can find the cell . For this we can ask the view controller for the index path of the item and its location. The location is then passed as an argument by the delegate method. Should the cell be empty we should get an error.
The code looks something like this
func previewingContext(previewingContext:
UIViewControllerPreviewing,viewControllerForLocation
location: CGPoint) -> UIViewController? {
let indexPath = collectionView?.indexPathForItemAtPoint(location),
cell = collectionView?.cellForItemAtIndexPath(indexPath) else { return nil }
}
The next step is that we need to create a instance of the class. we can do this by adding a storyboard ID to the now playing controller scene in the storyboard. if this view controller fails it should crash.
The code should look like this
let detailViewController
= storyboard?.instantiateViewControllerWithIdentifier("nowPlaying")
as? NowPlayingController else { return nil }
}
Once this has step works , we can fetch the data from the datasource and pass it to the nowplayingcontroller so it can set up the imageview and the current station. Which looks like this :
detailViewController.image = previewDetail.stationImage
detailViewController.currentStation = previewDetail
if you check the code in the stationsviewcontroller, you will see that the view did load method is there to check to see if they image and station property is available, if thats the case then the station and image are set.
Once we have done this we can add the preferred content size of the controller instance which i had set to this :
detailViewController.preferredContentSize = CGSize(width: 600, height: 600)
The last step is to set the sourceRect property. This property accepts a CGRect and will blur everything around it and keep everything inside the rect sharp. the rect should be the same frame as the cell and then return the instance.
previewingContext.sourceRect = cell.frame
return detailViewController
setting up the popping was a bit easier as there was only one function for this .
All you need to do is use the same view controller that we just created, and implement the delegate method and call the showviewcontroller:sender method
func previewingContext(previewingContext:
UIViewControllerPreviewing,
commitViewController viewControllerToCommit: UIViewController) {
showViewController(viewControllerToCommit, sender: nil)
}
And thats all there is to it !
Once you run the app and press on a image you should be able to peek and pop it like so :