SwiftUI选项卡视图索引视图不考虑页面视图索引
我的目标是将当前TabView索引的真实来源保持在appstate中。但我并没有看到我期望从SwiftUI TabView索引指示器中看到的行为 我能做的是有两种结果中的一种:让绑定正确地更新真相的来源,或者让指标按预期工作。我似乎不能两者兼得 我已经将代码精简到下面的测试用例中。我希望TabView索引视图(指示器)更新并显示当前视图在TabView内容数组中的索引位置(当然相对而言,so+1) 结果是索引根本不更新。在原始代码中,它实际上滞后了一个 有经验的人能提供一些建议或指出我的错误吗SwiftUI选项卡视图索引视图不考虑页面视图索引,swiftui,Swiftui,我的目标是将当前TabView索引的真实来源保持在appstate中。但我并没有看到我期望从SwiftUI TabView索引指示器中看到的行为 我能做的是有两种结果中的一种:让绑定正确地更新真相的来源,或者让指标按预期工作。我似乎不能两者兼得 我已经将代码精简到下面的测试用例中。我希望TabView索引视图(指示器)更新并显示当前视图在TabView内容数组中的索引位置(当然相对而言,so+1) 结果是索引根本不更新。在原始代码中,它实际上滞后了一个 有经验的人能提供一些建议或指出我的错误吗
import SwiftUI
class Item: Identifiable {
let id = Int.random(in: 0..<1000)
}
class SourceOfTruth: ObservableObject {
@Published var items: [Item] = [Item(), Item(), Item()]
/// Source of truth for app state
var _selectedItem: Int? {
willSet {
print("\(newValue ?? 0)")
}
}
/// Exposed SwiftUI binding
public lazy var selectedItem: Binding<Int> = Binding<Int>(get: {
self._selectedItem ?? -1
}, set: {
self._selectedItem = $0
})
init () {
_selectedItem = items.first?.id
}
}
struct BindingTestView: View {
@EnvironmentObject var appState: SourceOfTruth
var body: some View {
if appState.items.count > 0 {
TabView(selection: appState.selectedItem) {
ForEach(appState.items) { item in
Text("\(item.id)")
.tag(item.id)
}
}
.tabViewStyle(PageTabViewStyle(indexDisplayMode: .always))
.indexViewStyle(PageIndexViewStyle(backgroundDisplayMode: .always))
} else {
Text("No items")
}
}
}
@main
struct SwiftUICombineTestingApp: App {
let appState = SourceOfTruth()
var body: some Scene {
WindowGroup {
BindingTestView().environmentObject(appState)
}
}
}
导入快捷界面
类别项目:可识别{
设id=Int.random(in:0..0{
选项卡视图(选择:appState.selectedItem){
ForEach(appState.items){item在
文本(“\(item.id)”)
.tag(item.id)
}
}
.tabViewStyle(页面tabViewStyle(indexDisplayMode:.始终))
.indexViewStyle(PageIndexViewStyle(背景显示模式:。始终))
}否则{
文本(“无项目”)
}
}
}
@主要
结构SwiftUICombineTestingApp:App{
让appState=SourceOfTruth()
var body:一些场景{
窗口组{
BindingTestView().environmentObject(appState)
}
}
}
您需要添加@Published
,以便视图可以观察变量:
@Published var _selectedItem: Int? {
willSet {
print("\(newValue ?? 0)")
}
}
谢谢!我最初的想法不起作用是因为我没有在视图中使用
@Binding
属性包装器吗?如果是这样,那会是更传统的方式吗?根据我最后的评论,不是注入@EnvironmentObject appState
和使用class对象,而是在视图中使用@Binding var
,然后通过应用注入tate at view init?刚刚尝试从\u selectedItem
中删除@Published
包装,并将绑定注入视图中的@Binding var
,指示器现在执行“滞后一个”操作。@Ellight我真的不知道你最初对@Binding
的想法是什么。但是@Published
的解决方案在这里应该是好的。如果你还有更多的问题,请创建一个新的职位,我会尽力帮助你。