UIAlertController 不立即显示

UIAlertController not displaying immediately

我是 Swift 编程新手,但找不到我的问题的答案,即...

当我呈现一个带有 UIAlertAction 处理程序的简单 UIAlertController 时,我希望在用户响应之前显示警报,然后执行处理程序,然后再继续剩余的代码。

没想到,它似乎在显示警报和执行处理程序之前完成了代码块。

我搜索了 Whosebug,并重新阅读了 UIAlertController 和 UIAlertAction 的 Apple 开发者文档,但我不明白为什么代码在用户响应之前不会暂停。

我已尝试将 UIAlertController 代码放入它自己的函数中,但警报显示的顺序似乎仍然不正确。我在想也许需要延迟以允许在下一行代码执行之前绘制 Alert(?)。

@IBAction func buttonTapped(_ sender: Any) {

    let alert = UIAlertController(title: "Ouch", message: "You didn't have to press me so hard!", preferredStyle: .alert)
    alert.addAction(UIAlertAction(title: "Sorry", style: .default, handler: { _ in
        self.handleAlert()
    }))
    self.present(alert, animated: true, completion: nil)

    print("Should be printed last!")
}

func handleAlert() {
    print("UIAlertAction handler printed me")
}

在上面的代码中,我希望调试控制台显示:

UIAlertAction 处理程序打印我 应该最后打印!

而是显示:

Should be printed last!
UIAlertAction handler printed me

不是添加一个单独的函数,你能不能像这样把它放在警报操作中...

let alert = UIAlertController(title: "Ouch", message: "You didn't have to press me so hard!", preferredStyle: .alert)

alert.addAction(UIAlertAction(title: "Sorry", style: .default, handler: { action in

// code for action goes here

}))

self.present(alert, animated: true)

UIAlertController 设计为 运行 异步(这就是为什么它让您在执行操作时传递一段代码来执行,而不是给出 return 值)

因此,要修复您的代码,请将您想要的代码放在 运行 在另一个函数中选择一个动作之后,然后在每个 UIAlertAction 处理程序的末尾调用该函数。

private var currentlyShowingAlert = false

@IBAction func buttonTapped(_ sender: Any) {

    if currentlyShowingAlert {

        return

    }

    let alert = UIAlertController(title: "Ouch", message: "You didn't have to press me so hard!", preferredStyle: .alert)
    alert.addAction(UIAlertAction(title: "Sorry", style: .default, handler: { _ in
        self.handleAlert()
        self.alertCleanup()
    }))
    self.present(alert, animated: true, completion: nil)
    currentlyShowingAlert = true

}

func handleAlert() {

    print("UIAlertAction handler printed me")

}

func alertCleanup() {

     print("Should be printed last!")
     currentlyShowingAlert = false

}

在按下视图控制器(或调用会堆积的任何地方)以直接响应按钮按下之类的事情时要小心。 当主线程繁忙时,可以在第一次 buttonTapped 调用发生之前多次按下按钮,在这种情况下 buttonTapped 可以连续调用多次, currentlyShowingAlert 将阻止问题。