import SwiftUI
struct ContentView: View {
@State var showSecond = false
@State var showThird = false
var body: some View {
VStack(spacing: 50) {
Text("FirstView")
Button("to SecondView") {
self.showSecond = true
}
.sheet(isPresented: $showSecond) {
VStack(spacing: 50) {
Text("SecondView")
Button("to ThirdView") {
self.showThird = true
}
.sheet(isPresented: self.$showThird) {
VStack(spacing: 50) {
Text("ThirdView")
Button("back") {
self.showThird = false
}
Button("back to FirstView") {
self.showThird = false
self.showSecond = false
}
}
}
Button("back") {
self.showSecond = false
}
}
}
}
}
}
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView()
}
}
以上代码从FirstView过渡到SecondView,并且从SecondView过渡到ThirdView。然后,SecondView和ThirdView中的“返回”按钮通常会返回到上一个屏幕。
但是,如果您在ThirdView中点击“返回FirstView”按钮,将显示SecondView而不会返回FirstView。在执行此操作后,当您点击SecondView的“后退”按钮时,它不会返回到FirstView。
如何直接从ThirdView返回FirstView?
答案 0 :(得分:1)
目前根本没有办法(而且IMO永远不会-这是两个模式会议)...我发现了两种可能值得考虑的方法:
A。从一个地方顺序关闭
Button("back to FirstView") {
DispatchQueue.main.async {
self.showThird = false
DispatchQueue.main.async {
self.showSecond = false
}
}
}
B。从不同位置顺序关闭
.sheet(isPresented: self.$showThird, onDismiss: {
self.showSecond = false // with some additional condition for forced back
})...
...
Button("back to FirstView") {
self.showThird = false
}
答案 1 :(得分:1)
另一个 /咳嗽/ “解决方案”-可能情况略有不同 -但无论如何:
struct ContentView: View {
var body: some View {
NavigationView {
NavigationLink(destination: SecondView()) {
Text("Show Second View")
.font(.largeTitle)
}
}
.navigationViewStyle(StackNavigationViewStyle())
}
}
struct SecondView: View {
@Environment(\.presentationMode) var presentationMode
@State private var showModal = false
var body: some View {
GeometryReader { geometry in
ZStack {
Rectangle()
.foregroundColor(.gray)
.frame(width: geometry.size.width, height: geometry.size.height)
Button(action: {
withAnimation {
self.showModal.toggle()
}
}) {
Text("Show Third View")
.font(.largeTitle)
.foregroundColor(.white)
}
if self.showModal {
VStack {
Button(action: {
self.presentationMode.wrappedValue.dismiss()
} ) {
Text("Show First View")
.font(.largeTitle)
.foregroundColor(.white)
}
}
.frame(width: geometry.size.width, height: geometry.size.height)
.background(Rectangle().foregroundColor(.orange))
.transition(.move(edge: .trailing))
}
}
.frame(width: geometry.size.width, height: geometry.size.height)
}
}
}
答案 2 :(得分:1)
Asperi的解决方案可一次消除两个屏幕,但不适用于更多屏幕。在这种情况下,我们需要在两种方法中都添加DispatchQueue.main.asyncAfter(deadline: .now() + .milliseconds(300))
:
self.showFourth = false
DispatchQueue.main.asyncAfter(deadline: .now() + .milliseconds(300)) {
self.showThird = false
DispatchQueue.main.asyncAfter(deadline: .now() + .milliseconds(300)) {
self.showSecond = false
}
}
.milliseconds(200)
不够。