我正在按照底部要点创建一个标签栏视图。 一切正常,除了在索引更改时,不会执行ForEach语句中的以下内容。因此内容视图不会改变。
ForEach(views.indices) { i in
self.views[i].view
.opacity(self.selectedIndex == i ? 1 : 0)
}
我还有其他解决方案可以实现我的目标,但是我想知道为什么ForEach不能按预期工作。 任何帮助
import SwiftUI
struct TabView: View {
var views: [TabBarItem]
@State var selectedIndex: Int = 0
init(_ views: [TabBarItem]) {
self.views = views
}
var body: some View {
ZStack {
ForEach(views.indices) { i in // it is not stepping into this when selectedIndex changes!!
self.views[i].view
.opacity(self.selectedIndex == i ? 1 : 0)
}
GeometryReader { geometry in
VStack {
Spacer()
ZStack(alignment: .top) {
LinearGradient(gradient: Gradient(colors: [Color.black.opacity(0.5), Color.black.opacity(0)]), startPoint: .top, endPoint: .bottom)
.frame(height: 49 + geometry.safeAreaInsets.bottom)
HStack {
ForEach(self.views.indices) { i in
Button(action: {
self.selectedIndex = i
}) {
VStack {
if self.selectedIndex == i {
self.views[i].image
.foregroundColor(.white)
.padding(.top, 8)
} else {
self.views[i].image
.foregroundColor(Color.white.opacity(0.5))
.padding(.top, 8)
}
Text(self.views[i].title)
.foregroundColor(.white)
.font(Font.system(size: 12, weight: .bold))
.opacity(0)
}
.frame(maxWidth: .infinity)
}
}
}
}
}
.edgesIgnoringSafeArea(.bottom)
.animation(.easeInOut)
}
}
}
}
struct TabBarItem {
var view: AnyView
var image: Image
var title: String
init<V: View>(view: V, image: Image, title: String) {
self.view = AnyView(view)
self.image = image
self.title = title
}
}
struct ContentView: View {
var body: some View {
TabView([
TabBarItem(view: FeedView(),
image: Image("house.fill"),
title: "Feed"),
TabBarItem(view: SearchView(),
image: Image("loupe"),
title: "Explore"),
TabBarItem(view: CreateView(),
image: Image("plus.circle"),
title: "Create"),
TabBarItem(view: LoginView(),
image: Image("person.fill"),
title: "Profile"),
])
}
}
https://gist.github.com/kishikawakatsumi/562028c46e7549aba658c88366417f6b
答案 0 :(得分:0)
SwiftUI需要知道如何唯一地标识每个项目,否则它将无法比较视图层次结构以找出发生了什么变化,这是因为您缺少id
内部的ForEach
。 / p>
ForEach(views.indices, id: \.self) { i in
self.views[i].view
.opacity(self.selectedIndex == i ? 1 : 0)
}
我个人喜欢其中的说明: