How it works
SensoryFeedback describes a discrete piece of haptic — and on some platforms audio — feedback that the system plays in response to something happening in your interface, such as a successful submission, a toggle flipping, or a selection landing on a new value. Rather than calling into a haptics engine imperatively, you declare the feedback you want and bind it to a value, letting SwiftUI play it whenever that value changes. Reach for SensoryFeedback when a user action deserves a physical confirmation, so the feel of your app reinforces what the UI is already showing.
Choose a feedback style from the built-in cases
SensoryFeedback offers named cases that map onto the platform's standard feedback patterns, including semantic outcomes like
.success,.warning, and.error, and interaction patterns like.selection,.impact, and.increase/.decrease. Picking the case that matches the meaning of the event lets the system render the correct intensity and texture for each device. The example asks for.success, the celebratory pattern appropriate for a completed action.Attach it with the sensoryFeedback(_:trigger:) modifier
You don't play SensoryFeedback directly; you install it on a view with the
.sensoryFeedback(_:trigger:)modifier, passing the feedback as the first argument. The modifier lives on whichever view should own the feedback, here the outerVStack, and stays dormant until its trigger fires.Drive playback by binding to a trigger value
The
triggerparameter takes anyEquatablevalue, and SwiftUI plays the feedback each time that value changes between view updates. In the example the trigger is thecountstate, so every time theButtonrunscount += 1, the.successhaptic fires exactly once. Because playback is keyed to a value change rather than to the gesture itself, the feedback follows your data instead of your event handling.Gate or vary feedback with the conditional overloads
Beyond the simple form,
sensoryFeedbackprovides overloads that take aconditionclosure to decide whether to play on a given change, and afeedbackclosure that returns an optional SensoryFeedback so you can select a different pattern — or none — based on the old and new trigger values. These let a single attachment cover cases like playing.successonly past a threshold while staying silent otherwise.
.sensoryFeedback(.success, trigger: count) to .sensoryFeedback(.impact, trigger: count) and tap the button to feel the sharper, more neutral tap replace the celebratory success pattern.Example & preview
Press Run live & edit to compile it in your browser — then edit the Swift on the left and the preview re-renders live.
struct SensoryFeedbackDemo: View {
@State private var count = 0
var body: some View {
VStack(spacing: 16) {
Text("Taps: \(count)")
.font(.title2)
Button("Tap me") {
count += 1
}
.buttonStyle(.borderedProminent)
}
.padding()
.sensoryFeedback(.success, trigger: count)
}
}