@@ -208,6 +208,7 @@ open class SwiftMessagesSegue: UIStoryboardSegue {
208
208
override open func perform( ) {
209
209
( source as? WindowViewController ) ? . install ( )
210
210
selfRetainer = self
211
+ startReleaseMonitor ( )
211
212
if overrideModalPresentationStyle {
212
213
destination. modalPresentationStyle = . custom
213
214
}
@@ -222,6 +223,19 @@ open class SwiftMessagesSegue: UIStoryboardSegue {
222
223
}
223
224
224
225
fileprivate let safeAreaWorkaroundViewController = UIViewController ( )
226
+
227
+ /// The self-retainer will not allow the segue, presenting and presented view controllers to be released if the presenting view controller
228
+ /// is removed without first dismissing. This monitor handles that scenario by setting `self.selfRetainer = nil` if
229
+ /// the presenting view controller is no longer in the heirarchy.
230
+ private func startReleaseMonitor( ) {
231
+ DispatchQueue . main. asyncAfter ( deadline: . now( ) + 2 ) { [ weak self] in
232
+ guard let self = self else { return }
233
+ switch self . source. view. window {
234
+ case . none: self . selfRetainer = nil
235
+ case . some: self . startReleaseMonitor ( )
236
+ }
237
+ }
238
+ }
225
239
}
226
240
227
241
extension SwiftMessagesSegue {
@@ -288,20 +302,21 @@ extension SwiftMessagesSegue {
288
302
extension SwiftMessagesSegue : UIViewControllerTransitioningDelegate {
289
303
public func animationController( forPresented presented: UIViewController , presenting: UIViewController , source: UIViewController ) -> UIViewControllerAnimatedTransitioning ? {
290
304
let shower = TransitioningPresenter ( segue: self )
291
- messenger. defaultConfig. eventListeners. append { [ unowned self] in
305
+ let hider = self . hider
306
+ messenger. defaultConfig. eventListeners. append { [ weak self] in
292
307
switch $0 {
293
308
case . didShow:
294
309
shower. completeTransition ? ( true )
295
310
case . didHide:
296
- if let completeTransition = self . hider. completeTransition {
311
+ if let completeTransition = hider. completeTransition {
297
312
completeTransition ( true )
298
313
} else {
299
314
// Case where message is internally hidden by SwiftMessages, such as with a
300
315
// dismiss gesture, rather than by view controller dismissal.
301
316
source. dismiss ( animated: false , completion: nil )
302
317
}
303
318
( source as? WindowViewController ) ? . uninstall ( )
304
- self . selfRetainer = nil
319
+ self ? . selfRetainer = nil
305
320
default : break
306
321
}
307
322
}
0 commit comments