iOS13中如何给当前应用添加一个UIView对象window

How to add a UIView object to the current application window in iOS 13

这是我正在尝试做的事情:

当用户单击当前视图控制器上的按钮时 - 我想呈现一个占据整个屏幕的 UIView - 状态栏和所有内容 - 并且位于当前视图控制器堆栈的顶部。直到 iOS 13,我都是这样做的:

var mainWindow = UIApplication.shared.keyWindow

mainWindow!.addSubview(self.temp_view2!

leadingConstraint = NSLayoutConstraint(item: temp_view2, attribute: NSLayoutConstraint.Attribute.leading, relatedBy: NSLayoutConstraint.Relation.equal, toItem: mainWindow, attribute: NSLayoutConstraint.Attribute.leading, multiplier: 1, constant: 0)
trailingConstraint = NSLayoutConstraint(item: temp_view2, attribute: NSLayoutConstraint.Attribute.trailing, relatedBy: NSLayoutConstraint.Relation.equal, toItem: mainWindow, attribute: NSLayoutConstraint.Attribute.trailing, multiplier: 1, constant: 0)
topConstraint = NSLayoutConstraint(item: temp_view2, attribute: NSLayoutConstraint.Attribute.top, relatedBy: NSLayoutConstraint.Relation.equal, toItem: mainWindow, attribute: NSLayoutConstraint.Attribute.top, multiplier: 1, constant: 0)
bottomConstraint = NSLayoutConstraint(item: temp_view2, attribute: NSLayoutConstraint.Attribute.bottom, relatedBy: NSLayoutConstraint.Relation.equal, toItem: mainWindow, attribute: NSLayoutConstraint.Attribute.bottom, multiplier: 1, constant: 0)
mainWindow?.addConstraints([topConstraint!, bottomConstraint!, leadingConstraint!, trailingConstraint!])

这种方法似乎在 iOS13 中不起作用,我猜是因为 UIWindow 和 UIScenes 的工作方式——我还没有完全理解它。我在我的应用程序中只使用了一个 window。使用这个 SO post 我试着看看以下是否可行:

let keyWindow = UIApplication.shared.windows.filter {[=13=].isKeyWindow}.first

keyWindow?.addSubview(self.temp_view2!)

leadingConstraint = NSLayoutConstraint(item: temp_view2, attribute: NSLayoutConstraint.Attribute.leading, relatedBy: NSLayoutConstraint.Relation.equal, toItem: keyWindow, attribute: NSLayoutConstraint.Attribute.leading, multiplier: 1, constant: 0)
trailingConstraint = NSLayoutConstraint(item: temp_view2, attribute: NSLayoutConstraint.Attribute.trailing, relatedBy: NSLayoutConstraint.Relation.equal, toItem: keyWindow, attribute: NSLayoutConstraint.Attribute.trailing, multiplier: 1, constant: 0)
topConstraint = NSLayoutConstraint(item: temp_view2, attribute: NSLayoutConstraint.Attribute.top, relatedBy: NSLayoutConstraint.Relation.equal, toItem: keyWindow, attribute: NSLayoutConstraint.Attribute.top, multiplier: 1, constant: 0)
bottomConstraint = NSLayoutConstraint(item: temp_view2, attribute: NSLayoutConstraint.Attribute.bottom, relatedBy: NSLayoutConstraint.Relation.equal, toItem: keyWindow, attribute: NSLayoutConstraint.Attribute.bottom, multiplier: 1, constant: 0)
keyWindow?.addConstraints([topConstraint!, bottomConstraint!, leadingConstraint!, trailingConstraint!]) 

确实添加了视图,但一直在后面,在根视图控制器后面,我添加了一条 bringSubviewToFront 行,但这也无济于事。这是它的外观 - 实际上我添加了 3 个视图,如上所述:

如何为 >= iOS 13 执行此操作?

改变

let keyWindow = UIApplication.shared.windows.filter {[=10=].isKeyWindow}.last

从您的屏幕截图看来,视图已添加到正确的 window;它只是错误的 z 顺序。如果没有更多关于你在代码中添加它的上下文,就不可能说出为什么会这样(即你可以在之后创建 VC 并且新的子视图总是被推到现有的子视图之上,除非你指定一个 z 顺序) .测试 z 顺序是否正确的一种非常简单的方法是,只要您在前面看到的 VC 出现(即在 viewWillAppear 调用 window.bringSubviewToFront(viewThatsSupposedToBeInFront ).

如果您始终希望您的视图位于当前 window 之上,您可以创建另一个 window 更高 window 级别 onTopOfEveryThingWindow.windowLevel = .init(.greatestFiniteMagnitude)。这可以阻止应用程序中的所有内容,包括警报,直到您隐藏 window.