To bring my widgets to iPad lock screen, i need to detect my widget that has a background to display different contents, watch the wwdc 23 video it tells we can use .showsWidgetContainerBackground environment to apply that goal, but the problem is this code wouldn't compile because .showsWidgetContainerBackground only available in iOS 17
@available(iOS 14.0, *)
struct MyWidgetView: View
{
@Environment(\.showsWidgetContainerBackground) var showsBackground
var body: some View {
...
}
}
So, my solution is use a environment wrapper, like this:
@available(iOS 17.0, *)
struct EnvironmentWrapper: View
{
@Environment(\.showsWidgetContainerBackground) var showsWidgetContainerBackground
var body: some View {
VStack(alignment: .leading) {
Text("Wrapper Has Background: \(showsWidgetContainerBackground ? "YES" : "NO")")
}
}
}
extension View
{
var showsWidgetContainerBackground: Bool {
if #available(iOS 17.0, *)
{
return EnvironmentWrapper().showsWidgetContainerBackground
}
else
{
return true
}
}
}
But it didn't work, this is the example:
@available(iOS 17.0, *)
struct EnvironmentWrapper: View
{
@Environment(\.showsWidgetContainerBackground) var showsWidgetContainerBackground
var body: some View {
VStack(alignment: .leading) {
Text("Wrapper has background: \(showsWidgetContainerBackground ? "YES" : "NO")")
}
}
}
@available(iOS 17.0, *)
struct ExampleView: View
{
@Environment(\.showsWidgetContainerBackground) var showsBackground
var body: some View {
VStack(alignment: .leading) {
Text("Read from self: \(showsBackground ? "YES" : "NO")")
EnvironmentWrapper()
Text("Read from wrapper: \(EnvironmentWrapper().showsWidgetContainerBackground ? "YES" : "NO")")
}
.font(.system(size: 12, weight: .medium))
}
}
As you can see, if i read it directly from self, it works, but if i read from outside, it always return true
i also try to load a view first in the wrapper, but it didn't work either
func getShowsBackground() -> Bool
{
let _ = body
return showsWidgetContainerBackground
}