@@ -58,18 +58,29 @@ @implementation OneSignalTracker
5858static UIBackgroundTaskIdentifier focusBackgroundTask;
5959static NSTimeInterval lastOpenedTime;
6060static BOOL lastOnFocusWasToBackground = YES ;
61+ static BOOL willResignActiveTriggered = NO ;
62+ static BOOL didEnterBackgroundTriggered = NO ;
6163
6264+ (void )resetLocals {
6365 [OSFocusTimeProcessorFactory resetUnsentActiveTime ];
64- focusBackgroundTask = 0 ;
66+ focusBackgroundTask = 0 ;
6567 lastOpenedTime = 0 ;
6668 lastOnFocusWasToBackground = YES ;
69+ [self resetBackgroundDetection ];
6770}
6871
6972+ (void )setLastOpenedTime : (NSTimeInterval )lastOpened {
7073 lastOpenedTime = lastOpened;
7174}
7275
76+ + (void )willResignActiveTriggered {
77+ willResignActiveTriggered = YES ;
78+ }
79+
80+ + (void )didEnterBackgroundTriggered {
81+ didEnterBackgroundTriggered = YES ;
82+ }
83+
7384+ (void )beginBackgroundFocusTask {
7485 focusBackgroundTask = [[UIApplication sharedApplication ] beginBackgroundTaskWithExpirationHandler: ^{
7586 [OneSignalTracker endBackgroundFocusTask ];
@@ -81,10 +92,26 @@ + (void)endBackgroundFocusTask {
8192 focusBackgroundTask = UIBackgroundTaskInvalid;
8293}
8394
95+ /* *
96+ Returns true if application truly did come from a backgrounded state.
97+ Returns false if the application bypassed `didEnterBackground` after entering `willResignActive`.
98+ This can happen if the app resumes after a native dialog displays over the app or after the app is in a suspended state and not backgrounded.
99+ **/
100+ + (BOOL )applicationForegroundedFromBackgroundedState {
101+ return !(willResignActiveTriggered && !didEnterBackgroundTriggered);
102+ }
103+
104+ + (void )resetBackgroundDetection {
105+ willResignActiveTriggered = NO ;
106+ didEnterBackgroundTriggered = NO ;
107+ }
108+
84109+ (void )onFocus : (BOOL )toBackground {
85110 // return if the user has not granted privacy permissions
86- if ([OneSignal requiresUserPrivacyConsent ])
111+ if ([OneSignal requiresUserPrivacyConsent ]) {
112+ [self resetBackgroundDetection ];
87113 return ;
114+ }
88115
89116 // Prevent the onFocus to be called twice when app being terminated
90117 // - Both WillResignActive and willTerminate
@@ -101,6 +128,10 @@ + (void)onFocus:(BOOL)toBackground {
101128
102129+ (void )applicationForegrounded {
103130 [OneSignal onesignalLog: ONE_S_LL_DEBUG message: @" Application Foregrounded started" ];
131+
132+ BOOL fromBackgroundedState = [self applicationForegroundedFromBackgroundedState ];
133+ [self resetBackgroundDetection ];
134+
104135 [OSFocusTimeProcessorFactory cancelFocusCall ];
105136
106137 if (OneSignal.appEntryState != NOTIFICATION_CLICK)
@@ -115,7 +146,10 @@ + (void)applicationForegrounded {
115146 // This checks if notification permissions changed when app was backgrounded
116147 [OneSignal sendNotificationTypesUpdate ];
117148 [[OSSessionManager sharedSessionManager ] attemptSessionUpgrade: OneSignal.appEntryState];
118- [OneSignal receivedInAppMessageJson: nil ];
149+ if (fromBackgroundedState) {
150+ // Use cached IAMs if app truly went into the background
151+ [OneSignal receivedInAppMessageJson: nil ];
152+ }
119153 }
120154
121155 let wasBadgeSet = [OneSignal clearBadgeCount: false ];
0 commit comments