SwiftUI 列表行不同系统图像的不同高度
SwiftUI List Rows Different Heights for Different System Images
在我的 SwiftUI 应用程序中,我在侧边栏 NavigationView
内有一个 List
,有 2 行,如下所示:
List {
NavigationLink(destination: MyView1()) {
Label("Test Row 1", systemImage: "list.bullet")
}
NavigationLink(destination: MyView2()) {
Label("Test Row 2", systemImage: "shippingbox")
.frame(maxWidth: .infinity, alignment: .leading)
}
}
然而,第二行比第一行高,我相信是图像的原因。如果我将图像更改为:
NavigationLink(destination: MyView2()) {
Label("Test Row 2", systemImage: "list.number")
.frame(maxWidth: .infinity, alignment: .leading)
}
行现在高度相同。我不想固定行的高度,但我想知道是否有一种解决方案可以使行的高度相同。
如果要保证行是均匀的,可以使用PreferenceKeys
设置行高为最高行的高度,像这样:
struct EvenHeightListRow: View {
@State var rowHeight = CGFloat.zero
var body: some View {
List {
NavigationLink(destination: Text("MyView1")) {
Label("Test Row 1)", systemImage: "list.bullet")
// This reads the height of the row
.background(GeometryReader { geometry in
Color.clear.preference(
key: HeightPreferenceKey.self,
value: geometry.size.height
)
})
.frame(height: rowHeight)
}
NavigationLink(destination: Text("MyView2")) {
Label("Test Row 2)", systemImage: "shippingbox")
.background(GeometryReader { geometry in
Color.clear.preference(
key: HeightPreferenceKey.self,
value: geometry.size.height
)
})
.frame(height: rowHeight)
.frame(maxWidth: .infinity, alignment: .leading)
}
}
// this sets backgroundSize to be the max value of the tallest row
.onPreferenceChange(HeightPreferenceKey.self) {
rowHeight = max([=10=], rowHeight)
}
}
}
// This is the actual preferenceKey that makes it work.
fileprivate struct HeightPreferenceKey: PreferenceKey {
static var defaultValue: CGFloat = .zero
static func reduce(value: inout CGFloat, nextValue: () -> CGFloat) {}
}
在我的 SwiftUI 应用程序中,我在侧边栏 NavigationView
内有一个 List
,有 2 行,如下所示:
List {
NavigationLink(destination: MyView1()) {
Label("Test Row 1", systemImage: "list.bullet")
}
NavigationLink(destination: MyView2()) {
Label("Test Row 2", systemImage: "shippingbox")
.frame(maxWidth: .infinity, alignment: .leading)
}
}
然而,第二行比第一行高,我相信是图像的原因。如果我将图像更改为:
NavigationLink(destination: MyView2()) {
Label("Test Row 2", systemImage: "list.number")
.frame(maxWidth: .infinity, alignment: .leading)
}
行现在高度相同。我不想固定行的高度,但我想知道是否有一种解决方案可以使行的高度相同。
如果要保证行是均匀的,可以使用PreferenceKeys
设置行高为最高行的高度,像这样:
struct EvenHeightListRow: View {
@State var rowHeight = CGFloat.zero
var body: some View {
List {
NavigationLink(destination: Text("MyView1")) {
Label("Test Row 1)", systemImage: "list.bullet")
// This reads the height of the row
.background(GeometryReader { geometry in
Color.clear.preference(
key: HeightPreferenceKey.self,
value: geometry.size.height
)
})
.frame(height: rowHeight)
}
NavigationLink(destination: Text("MyView2")) {
Label("Test Row 2)", systemImage: "shippingbox")
.background(GeometryReader { geometry in
Color.clear.preference(
key: HeightPreferenceKey.self,
value: geometry.size.height
)
})
.frame(height: rowHeight)
.frame(maxWidth: .infinity, alignment: .leading)
}
}
// this sets backgroundSize to be the max value of the tallest row
.onPreferenceChange(HeightPreferenceKey.self) {
rowHeight = max([=10=], rowHeight)
}
}
}
// This is the actual preferenceKey that makes it work.
fileprivate struct HeightPreferenceKey: PreferenceKey {
static var defaultValue: CGFloat = .zero
static func reduce(value: inout CGFloat, nextValue: () -> CGFloat) {}
}