【问题标题】:SwiftUI confirmation button - Reset state when any other view interactionSwiftUI 确认按钮 - 在任何其他视图交互时重置状态
【发布时间】:2021-04-27 20:07:27
【问题描述】:

我想要一个按钮,按下时会变为“确认”。在第二次按下时,它执行操作。到目前为止很简单。

我还希望每当显示按钮的“确认”版本时,与任何其他视图的任何交互都会将该按钮重置为其原始状态。这可能是触摸背景、按下另一个按钮、转到另一个选项卡等。

我的尝试是这样的:

struct ContentView: View {
    @State private var confirmShowing = false

    var body: some View {
        ZStack {
            // Tappable background just to remove the confirmation
            Color(.systemBackground)
                .edgesIgnoringSafeArea(.all)
                .onTapGesture {
                    withAnimation {
                        confirmShowing = false
                    }
                }

            VStack {
                // Button which needs confirmation
                Button(action: {
                    if confirmShowing {
                        print("Executing")
                    }
                    withAnimation {
                        confirmShowing.toggle()
                    }
                }) {
                    Text( confirmShowing ? "Confirm" : "Do something" )
                }
                .padding()
                .background( Rectangle().foregroundColor( Color(.secondarySystemBackground) ) )
                .padding()

                // Completely different button which also should first reset confirmation
                Button("Do something else") {
                    withAnimation {
                        confirmShowing = false
                    }
                    // do some other stuff
                }
                    .padding()
                    .background( Rectangle().foregroundColor( Color(.secondarySystemBackground) ) )
                    .padding()
            }
        }
    }
}

它适用于这个非常简单的示例,但它不可扩展。如果我有 50 个视图,我将不得不为每个视图添加一些内容来控制这个按钮。

有没有更好的方法?我很高兴使用 UIViewRepresentable/UIViewControllerRepresentable。

UIKit 应该有这个功能吧?我经常在其他应用程序和 iOS 中看到它。

【问题讨论】:

    标签: ios swiftui uikit


    【解决方案1】:

    我能想到的最好方法是使用枚举来控制按钮的状态。例如。请原谅任何语法错误,我目前没有打开 XCode。

    @State var buttonState: ButtonState = .initial
    
    Button(action: {
        switch buttonState {
              case .initial:
                  buttonState = .second
              case .second:
                   //Perform whatever action after second.
              default:
                   buttonState = .initial
         }
    }, label: {
        switch buttonState {
            case .initial:
                  Text("Some Initial Action")
            case .second:
                  Text("Some Second Action")
            default:
                  Text("Default Action")
        }
    })
    

    然后,一旦你有了它,创建一个枚举来处理它。

    enum ButtonState {
        case initial, second
    }
    

    进一步的用法是简单地将buttonState = .initial 添加到您想要触发它返回默认值的任何其他按钮。

    【讨论】:

    • 我对这种方法的主要问题是我必须将该行添加到可能的许多按钮和其他视图中。在理想的世界中,我会喜欢 onOtherViewTouched 修饰符之类的东西,我可以用它来重置状态。
    • 看看这个“全局点击手势”的解决方案 - stackoverflow.com/questions/62400806/… 我认为这应该正是您正在寻找的。请注意,这最终会导致问题。按钮本身也会触发该全局手势,因此您需要确保处理好它。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2020-06-06
    • 2022-10-22
    • 1970-01-01
    • 1970-01-01
    • 2022-12-04
    • 1970-01-01
    • 2013-11-05
    相关资源
    最近更新 更多