问题:我要在三个视图之间切换,但是一旦选择了每个视图,就无法取消选择每个视图并关闭框架。
如果选择View1或其他任何视图后将其取消选择,则看起来像这样:
您可以将下面的代码复制并粘贴到Xcode中,以查看其当前工作方式:
import SwiftUI
struct ContentView: View {
@State var selectedView: Int? = nil
var body: some View {
ZStack {
NavigationView {
VStack {
Section {
Color(red: 0.88, green: 0.88, blue: 0.88)
.frame(maxWidth: .infinity, maxHeight: .infinity).edgesIgnoringSafeArea(.all)
HStack {
Button(action: {
withAnimation(.spring())
{
self.selectedView = 1
}
}) {
Text("View1")
.font(.headline)
.fontWeight(.regular)
.lineLimit(nil)
.padding(EdgeInsets.init(top: -5, leading: 15, bottom: 0, trailing: 15))
.foregroundColor(self.selectedView == 1 ? .blue : .gray)
}.foregroundColor(self.selectedView == 1 ? .blue : .gray)
.padding()
Button(action: {
withAnimation(.spring())
{
self.selectedView = 2
}
}) {
Text("View2")
.font(.headline)
.fontWeight(.regular)
.lineLimit(nil)
.padding(EdgeInsets.init(top: -5, leading: 15, bottom: 0, trailing: 15))
.foregroundColor(self.selectedView == 2 ? .blue : .gray)
}.foregroundColor(self.selectedView == 2 ? .blue : .gray)
.padding()
Button(action: {
withAnimation(.spring())
{
self.selectedView = 3
}
}) {
Text("View3")
.font(.headline)
.fontWeight(.regular)
.lineLimit(nil)
.padding(EdgeInsets.init(top: -5, leading: 15, bottom: 0, trailing: 10))
.foregroundColor(self.selectedView == 3 ? .blue : .gray)
}.foregroundColor(self.selectedView == 3 ? .blue : .gray)
.padding()
}}}
}
VStack (alignment: .center) {
if self.selectedView == 1 {
ShowView1().transition(
AnyTransition.move(edge: .bottom).combined(with: .move(edge: .bottom)).combined(with: .opacity))
}
if self.selectedView == 2 {
ShowView2().transition(
AnyTransition.move(edge: .bottom).combined(with: .move(edge: .bottom)).combined(with: .opacity))
}
if self.selectedView == 3 {
ShowView3().transition(
AnyTransition.move(edge: .bottom).combined(with: .move(edge: .bottom)).combined(with: .opacity))
}
}}}}
struct ShowView1: View {
var body: some View {
ZStack() {
Color.white
.frame(maxWidth: .infinity, maxHeight: 52)
}
}
}
struct ShowView2: View {
var body: some View {
ZStack() {
Color.white
.frame(maxWidth: .infinity, maxHeight: 600)
}
}
}
struct ShowView3: View {
var body: some View {
ZStack() {
Color.white
.frame(maxWidth: .infinity, maxHeight: 300)
}
}
}
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView()
}
}
您可以通过将所选状态更改为等于button's
(如果当前处于选中状态)来更改nil
操作内的代码,从而取消选择视图。
self.selectedView == 1 ? (self.selectedView = nil) : (self.selectedView = 1)
有效的解决方案:
struct ContentView: View {
@State var selectedView: Int? = nil
var body: some View {
ZStack {
NavigationView {
VStack {
Section {
Color(red: 0.88, green: 0.88, blue: 0.88)
.frame(maxWidth: .infinity, maxHeight: .infinity).edgesIgnoringSafeArea(.all)
HStack {
Button(action: {
withAnimation(.spring())
{
self.selectedView == 1 ? (self.selectedView = nil) : (self.selectedView = 1)
}
}) {
Text("View1")
.font(.headline)
.fontWeight(.regular)
.lineLimit(nil)
.padding(EdgeInsets.init(top: -5, leading: 15, bottom: 0, trailing: 15))
.foregroundColor(self.selectedView == 1 ? .blue : .gray)
}.foregroundColor(self.selectedView == 1 ? .blue : .gray)
.padding()
Button(action: {
withAnimation(.spring())
{
self.selectedView == 2 ? (self.selectedView = nil) : (self.selectedView = 2)
}
}) {
Text("View2")
.font(.headline)
.fontWeight(.regular)
.lineLimit(nil)
.padding(EdgeInsets.init(top: -5, leading: 15, bottom: 0, trailing: 15))
.foregroundColor(self.selectedView == 2 ? .blue : .gray)
}.foregroundColor(self.selectedView == 2 ? .blue : .gray)
.padding()
Button(action: {
withAnimation(.spring())
{
self.selectedView == 3 ? (self.selectedView = nil) : (self.selectedView = 3)
}
}) {
Text("View3")
.font(.headline)
.fontWeight(.regular)
.lineLimit(nil)
.padding(EdgeInsets.init(top: -5, leading: 15, bottom: 0, trailing: 10))
.foregroundColor(self.selectedView == 3 ? .blue : .gray)
}.foregroundColor(self.selectedView == 3 ? .blue : .gray)
.padding()
}}}
}
VStack (alignment: .center) {
if self.selectedView == 1 {
ShowView1().transition(
AnyTransition.move(edge: .bottom).combined(with: .move(edge: .bottom)).combined(with: .opacity))
}
if self.selectedView == 2 {
ShowView2().transition(
AnyTransition.move(edge: .bottom).combined(with: .move(edge: .bottom)).combined(with: .opacity))
}
if self.selectedView == 3 {
ShowView3().transition(
AnyTransition.move(edge: .bottom).combined(with: .move(edge: .bottom)).combined(with: .opacity))
}
}}}}