在SwiftUI中将环境变量合并为一个



我的应用程序适应基于水平大小类和ContentSizeCategory布局。我通常会写这样的代码:

@Environment(.horizontalSizeClass) var horizontalSizeClass
@Environment(.sizeCategory) var sizeCategory: ContentSizeCategory

private var isHorCompactLayout: Bool {
horizontalSizeClass == .compact || sizeCategory.isAccessibilityCategory
}

我这样使用

var body: some Scene {
if isHorCompactLayout {
Text("CompactLayout()")
} else {
Text("NormalLayout()")
}

我想重构第一个代码块,以避免在我调整布局的所有视图中重复它。如何做到这一点?

我想我可以创建一个新的视图,传递它的两个视图和渲染正确的一个基于isHorCompactLayout的结果。但是在需要的时候获取isHorCompactLayout的值仍然是很好的;例如,调整padding

一种可能的方法是在内容视图的根级别设置自己的环境值,这样所有其他子视图都会在根级别更改时更新它,例如

struct ContentView: View {
@Environment(.horizontalSizeClass) var horizontalSizeClass
@Environment(.sizeCategory) var sizeCategory
var body: some View {
VStack {    // some top-most container or root view
// ... all app hierarchy 
}
.environment(.isHorCompactLayout, horizontalSizeClass == .compact || sizeCategory.isAccessibilityCategory)
}
}
struct HorCompactLayoutKey: EnvironmentKey {
static let defaultValue: Bool = false
}
extension EnvironmentValues {
var isHorCompactLayout: Bool {
get { self[HorCompactLayoutKey.self] }
set { self[HorCompactLayoutKey.self] = newValue }
}
}

用Xcode 13.4测试

相关内容

最新更新