当不在小部件中时如何设置 .widgetFamily @Environment 变量?

Lew*_*s42 5 widgetkit swiftui

我想在我的主应用程序中预览我的 WidgetKit 小部件。

小部件的布局.systemSmall.systemMedium大小不同。

当我.environment(\.widgetFamily, .systemSmall)在主应用程序中设置时,出现构建错误:

Key path value type 'WritableKeyPath<EnvironmentValues, WidgetFamily>' cannot be converted to contextual type 'KeyPath<EnvironmentValues, WidgetFamily>'
Run Code Online (Sandbox Code Playgroud)

如果我不设置值,则默认为.systemMedium.

有办法使用吗.systemSmall

Emi*_*aez 12

由于显而易见的原因,环境widgetFamily密钥未在应用程序中设置,但您可以自己实现。

首先你需要像这样WidgetFamily遵守EnvironmentKey

extension WidgetFamily: EnvironmentKey {
    public static var defaultValue: WidgetFamily = .systemMedium
}
Run Code Online (Sandbox Code Playgroud)

然后您需要添加自定义环境密钥,如下所示:

extension EnvironmentValues {
  var widgetFamily: WidgetFamily {
    get { self[WidgetFamily.self] }
    set { self[WidgetFamily.self] = newValue }
  }
}
Run Code Online (Sandbox Code Playgroud)

.environment()现在您可以在应用程序中使用修饰符:

struct ContentView: View {
    var body: some View {
        InterestingWidgetEntryView(entry: .init(date: .init()))
            .environment(\.widgetFamily, .systemSmall)
    }
}
Run Code Online (Sandbox Code Playgroud)

这就是我创建小部件视图的方式:

struct InterestingWidgetEntryView : View {
    @Environment(\.widgetFamily) var family
    var entry: Provider.Entry
    
    var body: some View {
        switch family {
        case .systemSmall:
            Text("Small")
        case .systemMedium:
            Text("Medium")
        case .systemLarge:
            Text("Large")
        default:
            Text("Some other WidgetFamily in the future.")
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

这是结果:

使用正确的系列在应用程序中加载小部件视图

请记住,小部件视图不会有小部件大小,您必须自己计算。