Widgets – Adapting content to rendering modes
How to support widgetRenderingMode on visionOS.
Overview
Users on visionOS can apply a tint color to their widgets. We can use widgetRenderingMode to provide alternative views as needed.
struct RenderWidgetsEntryView : View {
@Environment(\.widgetRenderingMode) var renderingMode
var body: some View {
if renderingMode == .fullColor {
// Provide a main version of the widget content
} else if renderingMode == .accented {
// Provide an alternative view in accented mode
}
}
}The documentation includes three modes, but only two seem to be used on visionOS.
fullColor: default SwiftUI contentaccented: applying a user selected tint colorvibrant: used on iOS Lock Screen (does not appear to be used in visionOS widgets)
We have a couple of ways we can adapt our content to support accented mode. Content in this mode is separate into two groups. The default group and the accent group. We can use widgetAccentable to mark views as part of the accent group.
VStack {
Text("Default Group")
Text("Accent Group")
.widgetAccentable(true)
}For images, we can use the widgetAccentedRenderingMode modifier to tell visionOS how to change the image. There are a handful of options.
accentedwill make the image part of the “accented” group. Most of the time, this turns the entire image to the accent color, making it essentially useless. For reasons, I don’t understand, this seems to be the default that visionOS applies to images if we don’t use this modifier to specify another value.desaturatedandaccentedDesaturatedwill map the alpha channel to ether the default or accent group.fullColorwill display the original image.
Image(.jsWidget)
.widgetAccentedRenderingMode(.accentedDesaturated)Let’s see this in action.
A caveat: When using SwiftUI spaces and fills it can be tricky to get accented mode looking good. For example, the Clock Widget we made in the timeline post uses a lot of Circle views. As of Beta 5, visionOS doesn’t provide enough control over accented rendering mode to make this viable. Instead, we could swap out the detailed clock view with a much simpler view. Perhaps one with only the hours and clock hands.


What about widget background? WidgeKit has a system for defining background views and allowing the system to remove them. This is mostly applicable on other platforms, but on visionOS we may see background views removed when using accented mode. If we do this by using containerBackground.
EmojiWidgetEntryView(entry: entry)
.containerBackground(.white.gradient, for: .widget)Sometimes we may not want the background removed or tinted by accented mode. In those cases, we can remove the containerBackground and use .containerBackgroundRemovable(false).
AppIntentConfiguration(kind: kind, intent: EmojiConfigurationAppIntent.self, provider: EmojiProvider()) { entry in
ClockWidgetEntryView(entry: entry)
// .containerBackground(.white.gradient, for: .widget)
}
.containerBackgroundRemovable(false)When we use this on the Clock Widget, visionOS will stop accenting our SwiftUI shapes, allowing us to show the original clock view.

Documentation
- https://developer.apple.com/documentation/widgetkit/widgetrenderingmode
- https://developer.apple.com/documentation/swiftui/image/widgetaccentedrenderingmode(_:)
- https://developer.apple.com/documentation/swiftui/view/widgetaccentable(_:)
- https://developer.apple.com/documentation/widgetkit/displaying-the-right-widget-background
- https://developer.apple.com/documentation/SwiftUI/WidgetConfiguration/containerBackgroundRemovable(_:)
Support our work so we can continue to bring you new examples and articles.

Follow Step Into Vision