With the release of SwiftUI, some people have asked if UIKit is going to be dead. It’s far from dead. In iOS 15, Apple’s engineers continues to pour new features into UIKit. One of the highlights is UISheetPresentationController
. This new class lets you easily create a expandable bottom sheet with just a few lines of code.
If you have no ideas about what a bottom sheet is, open the built-in Maps app to take a look. It displays a bottom sheet for users to perform search and access their saved locations. The sheet is resizable. You can drag the bottom sheet to expand and collapse it. In fact, this type of UI pattern can be found in some popular apps such as Google Maps, Twitter, and Instagram.
In this tutorial, we will see how to work with UISheetPresentationController
and customize its properties. The demo app is very simple with just one button. When the button is tapped, the app displays the web content using a bottom sheet.
Using UISheetPresentationController for Presenting a Bottom Sheet
In iOS 15, UIViewController
has a new property called sheetPresentationController
. For view controllers that inherit from UIViewController
, you can access its sheetPresentationController
property to retrieve the instance of UISheetPresentationController
for customizing its appearance.
You can specify the size of the sheet presentation controller by setting the detents
property. Here is an example showing you how to set the size of the bottom sheet:
let webViewController = WebViewController()
if let sheet = webViewController.sheetPresentationController {
sheet.detents = [ .medium(), .large() ]
}
present(webViewController, animated: true)
The WebViewController
class is a subclass of UIViewController
, so we can retrieve the instance of UISheetPresentationController
from the sheetPresentationController
property.
The detents
property specifies the array of heights where a sheet can rest. You use .medium()
to display a sheet that occupies half the height of the screen. To display a sheet at full height, you use the .large()
detent.
The code sample above specified to use .medium()
and .large()
in the detents
property. In this case, the sheet first takes up half of the screen size. When you drag up the web view controller, the sheet will fully expand.
If you reverse the order of the values like this, the app will first display the sheet at full height.
sheet.detents = [ .large(), .medium() ]
Customizing the Sheet with Grabber
Other than controlling the size of the sheet, the UISheetPresentationController
class provides a number of options for further customizations.
For example, to show a grabber at the top of the sheet, you can set the prefersGrabberVisible
property to true
:
sheet.prefersGrabberVisible = true
When the sheet is presented, the underlying view is dimmed automatically. If you want to keep it as it is, set the value of smallestUndimmedDetentIdentifier
to .medium
:
sheet.smallestUndimmedDetentIdentifier = .medium
The system will no longer dim the underlying view when the sheet is displayed.
Customizing the Sheet for Scrolling View
When you use a medium-sized sheet to display scrollable content, you may experience a minor issue. As you scroll up the content, the sheet will also be expanded. This may not be something we want. What we expect is that the size of the sheet should keep unchanged as we scroll through the content.
UISheetPresentationController
provide a property named prefersScrollingExpandsWhenScrolledToEdge
for resolving the issue. All you need to do is set the value of the property to false
:
sheet.prefersScrollingExpandsWhenScrolledToEdge = false
Once you made the change, you can scroll through the content properly even if the sheet takes half of the screen size. To expand the sheet, simpy drag up the grabber.
Customizing the Corner Radius
The preferredCornerRadius
property allows you to change the corner radius of the sheet. A higher value gives you a more rounded corners:
sheet.preferredCornerRadius = 30.0
Summary
The addition of UISheetPresentationController
is a welcome change for UIKit. We no longer need to develop our own implementation for displaying bottom sheet. It is now so easy to apply this popular mobile UI pattern to our apps.