NEW: Nominations are now open for the 2019 Swift Community Awards! >>

Entering numbers with Stepper

Paul Hudson    @twostraws   

SwiftUI has two ways of letting users enter numbers, and the one we’ll be using here is Stepper: a simple - and + button that can be tapped to select a precise number. The other option is Slider, which we’ll be using later on - it also lets us select from a range of values, but less precisely.

Steppers are smart enough to work with any kind of number type you like – you can bind them to Int, Double, and more, and it will automatically adapt. For example, we might create a property like this:

@State private var sleepAmount = 8.0

We could then bind that to a stepper so that it showed the current value, like this:

Stepper(value: $sleepAmount) {
    Text("\(sleepAmount) hours")
}

When that code runs you’ll see 8.000000 hours, and you can tap the - and + to step downwards to 7, 6, 5 and into negative numbers, or step upwards to 9, 10, 11, and so on.

By default steppers are limited only by the range of their storage. We’re using a Double in this example, which means the maximum value of the slider will be 1.7976931348623157e+308. That’s scientific notation, but it means “1.79769 times 10 to the power of 308” – or, in simpler terms, A Really Very Large Number Indeed.

Now, as a father of two kids I can’t tell you how much I love to sleep, but even I can’t sleep that much. Fortunately, Stepper lets us limit the values we want to accept by providing an in range, like this:

Stepper(value: $sleepAmount, in: 4...12) {
    Text("\(sleepAmount) hours")
}

With that change, the stepper will start at 8, then allow the user to move between 4 and 12 inclusive, but not beyond. This allows us to control the sleep range so that users can’t try to sleep for 24 hours, but it also lets us reject impossible values – you can’t sleep for -1 hours, for example.

There’s a third useful parameter for Stepper, which is a step value – how far to move the value each time - or + is tapped. Again, this can be any sort of number, but it does need to match the type used for the binding. So, if you are binding to an integer you can’t then use a Double for the step value.

In this instance, we might say that users can select any sleep value between 4 and 12, moving in 15 minute increments:

Stepper(value: $sleepAmount, in: 4...12, step: 0.25) {
    Text("\(sleepAmount) hours")
}

That’s starting to look useful – we have a precise range of reasonable values, a sensible step increment, and users can see exactly what they have chosen each time.

Before we move on, though, let’s fix that text: it says 8.000000 right now, which is accurate but a little too accurate. Previously we used a string interpolation specifier such as this:

Text("\(sleepAmount, specifier: "%.2f") hours")

We could use that here, but it looks odd: “8.00 hours” seems overly clinical. This is a good example of where the “%g” specifier is useful, because it automatically removes insignificant zeroes from the end of the number. So, it will show 8, 8.25, 8.5, 8.75, 9, and so on, which is much more natural for users to read.

LEARN SWIFTUI FOR FREE I have a massive, free SwiftUI video collection on YouTube teaching you how to build complete apps with SwiftUI – check it out!

MASTER SWIFT NOW
Buy Testing Swift Buy Practical iOS 12 Buy Pro Swift Buy Swift Design Patterns Buy Swift Coding Challenges Buy Server-Side Swift (Vapor Edition) Buy Server-Side Swift (Kitura Edition) Buy Hacking with macOS Buy Advanced iOS Volume One Buy Advanced iOS Volume Two Buy Hacking with watchOS Buy Hacking with tvOS Buy Hacking with Swift Buy Dive Into SpriteKit Buy Swift in Sixty Seconds Buy Objective-C for Swift Developers Buy Beyond Code

Was this page useful? Let us know!

Average rating: 5.0/5