|
@@ -56,11 +56,11 @@ extension NSResponder: KMWindowSheetProtocol {
|
|
|
|
|
|
func km_can_beginSheet(windowC: NSWindowController) -> Bool {
|
|
|
guard let _ = windowC.window else {
|
|
|
- KMPrint("窗口弹起失败, 窗口为空.")
|
|
|
+ self._log("窗口弹起失败, 窗口为空.", needAssert: false)
|
|
|
return false
|
|
|
}
|
|
|
guard let _ = self.km_window() else {
|
|
|
- KMPrint("窗口弹起失败, 当前窗口为空.")
|
|
|
+ self._log("窗口弹起失败, 当前窗口为空.", needAssert: false)
|
|
|
return false
|
|
|
}
|
|
|
return true
|
|
@@ -68,7 +68,7 @@ extension NSResponder: KMWindowSheetProtocol {
|
|
|
|
|
|
func km_can_endSheet() -> Bool {
|
|
|
guard let _ = self.kmCurrentWindowC?.window else {
|
|
|
- KMPrint("窗口收起失败, 当前窗口为空.")
|
|
|
+ self._log("窗口收起失败, 当前窗口为空.", needAssert: false)
|
|
|
return false
|
|
|
}
|
|
|
|
|
@@ -76,7 +76,7 @@ extension NSResponder: KMWindowSheetProtocol {
|
|
|
return true
|
|
|
}
|
|
|
|
|
|
- KMPrint("窗口收起失败, sheetWindow为空.")
|
|
|
+ self._log("窗口收起失败, sheetWindow为空.", needAssert: false)
|
|
|
return false
|
|
|
}
|
|
|
|
|
@@ -86,6 +86,10 @@ extension NSResponder: KMWindowSheetProtocol {
|
|
|
}
|
|
|
// 强持有窗口控制器
|
|
|
self.kmCurrentWindowC = windowC
|
|
|
+ // 反向弱持有
|
|
|
+ windowC._setSheetParentResponder(self)
|
|
|
+ // 存储哨兵
|
|
|
+ windowC.sheetFlag = true
|
|
|
if let _window = windowC.window {
|
|
|
self.km_window()?.beginSheet(_window)
|
|
|
}
|
|
@@ -99,20 +103,50 @@ extension NSResponder: KMWindowSheetProtocol {
|
|
|
if let _currentW = self.kmCurrentWindowC?.window {
|
|
|
self._km_sheetParent()?.endSheet(_currentW)
|
|
|
}
|
|
|
+ // 置空指针,避免野指针
|
|
|
+ self.kmCurrentWindowC?._setSheetParentResponder(nil)
|
|
|
+ // 释放哨兵
|
|
|
+ self.kmCurrentWindowC?.sheetFlag = false
|
|
|
// 释放窗口控制器
|
|
|
self.kmCurrentWindowC = nil
|
|
|
}
|
|
|
|
|
|
+ func km_quick_endSheet() {
|
|
|
+ if let _ = self.kmCurrentWindowC {
|
|
|
+ self.km_endSheet()
|
|
|
+ return
|
|
|
+ }
|
|
|
+
|
|
|
+ guard let windowC = self as? NSWindowController else {
|
|
|
+ self._log("windowC is nil")
|
|
|
+ return
|
|
|
+ }
|
|
|
+
|
|
|
+ // 不是通过 km_endSheet 或 km_safe_beginSheet 方法弹出
|
|
|
+ if windowC.sheetFlag == false {
|
|
|
+ // 直接结束弹出就好,不需要处理数据
|
|
|
+ if let _win = windowC.window {
|
|
|
+ windowC.window?.sheetParent?.endSheet(_win)
|
|
|
+ return
|
|
|
+ }
|
|
|
+ self._log("windowC is nil")
|
|
|
+ return
|
|
|
+ }
|
|
|
+
|
|
|
+ // 不是 km_endSheet 或 km_safe_beginSheet 的调起者
|
|
|
+ windowC.sheetParentResponder?.km_endSheet()
|
|
|
+ }
|
|
|
+
|
|
|
func km_safe_beginSheet(windowC: NSWindowController?) {
|
|
|
guard let _windowC = windowC else {
|
|
|
- #if DEBUG
|
|
|
- assert(false, "windowC is nil")
|
|
|
- #endif
|
|
|
+ self._log("windowC is nil")
|
|
|
return
|
|
|
}
|
|
|
return self.km_beginSheet(windowC: _windowC)
|
|
|
}
|
|
|
|
|
|
+ // MARK: - Private Methods
|
|
|
+
|
|
|
fileprivate func _km_sheetParent() -> NSWindow? {
|
|
|
var sheetParent: NSWindow?
|
|
|
if let data = self.km_window() {
|
|
@@ -123,7 +157,43 @@ extension NSResponder: KMWindowSheetProtocol {
|
|
|
return sheetParent
|
|
|
}
|
|
|
|
|
|
+ private func _log(_ string: String?, needAssert: Bool = true) {
|
|
|
+ #if DEBUG
|
|
|
+ if needAssert {
|
|
|
+ assert(false, string ?? "")
|
|
|
+ } else {
|
|
|
+ KMPrint(string as Any)
|
|
|
+ }
|
|
|
+ #endif
|
|
|
+ }
|
|
|
+
|
|
|
@objc func km_window() -> NSWindow? {
|
|
|
return nil
|
|
|
}
|
|
|
}
|
|
|
+
|
|
|
+// MARK: - Sheet
|
|
|
+
|
|
|
+extension NSWindowController {
|
|
|
+ private static var _sheetParentResponderKey = "KMSheetParentResponderKey"
|
|
|
+ unowned var sheetParentResponder: NSResponder? {
|
|
|
+ get {
|
|
|
+ return objc_getAssociatedObject(self, &Self._sheetParentResponderKey) as? NSResponder
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ private static var _sheetFlagKey = "KMSheetFlagKey"
|
|
|
+ var sheetFlag: Bool {
|
|
|
+ get {
|
|
|
+ return objc_getAssociatedObject(self, &Self._sheetFlagKey) as? Bool ?? false
|
|
|
+ }
|
|
|
+ set {
|
|
|
+ objc_setAssociatedObject(self, &Self._sheetFlagKey, newValue, .OBJC_ASSOCIATION_ASSIGN)
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ // MARK: - Private Methods
|
|
|
+ fileprivate func _setSheetParentResponder(_ newValue: NSResponder?) {
|
|
|
+ objc_setAssociatedObject(self, &Self._sheetParentResponderKey, newValue, .OBJC_ASSOCIATION_ASSIGN)
|
|
|
+ }
|
|
|
+}
|