When the iPhone application is running in background and it receive a remote notification. So it will execute the didReceiveRemoteNotification call back. In that I am going to push to a new UIViewController. But before that its noticed that its calling the applicationWillEnterForeground callback.
In that I am also doing some location update using a modal dialog. So when this notification arrives this both scenarios happens and the app is getting crashed. So is there any way to block the applictiaonWillEnterBackground processing on remote notification. As the moment is little bit hard cos this processing is done after applicationWillEnterBackground controller.
Thank you.
The callback application:didReceiveRemoteNotification: should only be invoked when the application is running in the foreground. When running in the background you should instead get a call to application:didFinishLaunchingWithOptions:.
Since you are asking the question and also using core location it might be that application:didReceiveRemoteNotification: is called when the application is in the background but I would think that would be a bug. At least according to Apple's documentation.
Anyway, NO, you can't block applicationWillEnterForeground:. Without knowing exactly what you are doing in the different callbacks I would recommend that you set a flag in applicationWillEnterForeground: if you are doing something there and then check that flag in application:didReceiveRemoteNotification:
- (void)applicationWillEnterForeground:(UIApplication *)application {
if (somehingHappend) {
somethingHappended = YES;
}
}
- (void)application:(UIApplication *)application didReceiveRemoteNotification:(NSDictionary *)userInfo {
if (!somethingHappened) {
// push your view controllers or whatever
}
}
Where somethingHappened is a BOOL defined in the same class as an ivar.
Related
I have a Tab bar app with 3 view controllers and I use "viewWillAppear" to detect which view is opend.
When I close the app, it still works "in the background" and when I open the app again "viewWillAppear" is not detecting this opening.
Is there any other option to detect this opening? Thanks
You can observe the UIApplicationWillEnterForegroundNotification or implement applicationWillEnterForeground: in your app delegate.
Firstly, You should see the necessary delegation method in UIApplicationDelegate
When you close application that currently open, It will call this method:
- (void)applicationDidEnterBackground:(UIApplication *)application
After the application has been closed but still in dock, you open them again. In the transition state before entering the application, It will call this method:
- (void)applicationWillEnterForeground:(UIApplication *)application
When the application completely presented on previous state before you closed them. It finally call thid method:
- (void)applicationDidBecomeActive:(UIApplication *)application
If you would like to do something in viewWillAppear you should implement in applicationDidBecomeActive to send some message to your current view or other to do what do you want to do after application became actived.
When your app is resumed from the background, it will receive the applicationWillEnterForground: method. It'll get the applicationDidEnterBackground: when it is suspended too.
- (void)applicationWillEnterForeground:(UIApplication *)application {
NSLog(#"app will enter foreground");
[viewController refresh:NULL];
}
i think this will work.
write this in your app delegate
I am trying to have my app reload data when it is brought to the foreground via the applicationWillEnterForeground method. I can get the function to work and write to the NSLog, but I have a function that I want to be called from another class, how would I go about this?
I have tried below:
- (void)applicationWillEnterForeground:(UIApplication *)application {
//Re-run...
[MainViewController reRun];
}
Be gentle bit of a newbie...
You can register to UIApplicationDidBecomeActiveNotification, and reload your data when your receive it.
The applicationWillTerminate delegate method is not getting called in iOS 4.0
When I hit the Home button I am seeing the applicationWillResignActive and applicationDidEnterBackground delegate methods getting called.
- (void)applicationWillResignActive:(UIApplication *)application
{
NSLog(#"Application Did Resign Active");
}
- (void)applicationDidEnterBackground:(UIApplication *)application
{
NSLog(#"Application Did Enter Background");
}
And when I double Tap the Home button and again launch the Application the i find the applicationWillEnterForeground and applicationDidBecomeActive delegate methods are getting called.
- (void)applicationWillEnterForeground:(UIApplication *)application
{
NSLog(#"Application Will Enter Foreground");
}
- (void)applicationDidBecomeActive:(UIApplication *)application
{
NSLog(#"Application Did Become Active");
}
But I want to know when the applicationWillTerminate delegate method will be called , where I do some DB/file backup routines.
- (void)applicationWillTerminate:(UIApplication *)application{
}
I even tried to hit the minus sign and deleted the App running in the Background , but still it did not call any delegate method.
Any Ideas ???
From the iPhone Application Programming Guide:
Even if you develop your application using iPhone SDK 4 and later, you must still be prepared for your application to be terminated. If memory becomes constrained, the system might remove applications from memory in order to make more room. If your application is currently suspended, the system removes your application from memory without any notice. However, if your application is currently running in the background, the system does call the applicationWillTerminate: method of the application delegate. Your application cannot request additional background execution time from this method.
So yes, applicationWillTerminate: will generally not be called very often in iOS 4. If you have to save data, you should do so in both applicationWillTerminate: and applicationDidEnterBackground:.
The WWDC 2010 Session Adopting Multitasking on iPhone OS (Part 2) explains the application state transitions extremely well.
I got one solution for terminating apps when user hits the Home button in iOS4.
This will call the applicationWillTerminate delegate method instead of entering into background process.
Open your info.plist file
Add The Key UIApplicationExitsOnSuspend
Set the new key to YES
Actually you can also use this step to do so.
Open your info.plist file
Add The Key -> Application does not run in background
Set this key value to YES
I want to implement this function on my apps but i cant seem to figure out how to use this line of codes.
- (void)applicationWillResignActive:(UIApplication *)application {
//our app is going to loose focus since there is an incoming call
[self pauseGame];
}
- (void)applicationDidBecomeActive:(UIApplication *)application{
//the user declined the call and is returning to our app
[self resumeGame];
}
I've read that this must be placed in appdelegates but i cant seem to figure out how could i call my pause action when the game is currently in the viewcontroller.
Thank you.
Instead of sending the messages to self (which is the app delegate), you would send them to your view controller.
For example, if your app delegate had a property for your main game view controller named "gameViewController" (where the methods to pause and resume were implemented):
- (void)applicationWillResignActive:(UIApplication *)application {
// our app is going to loose focus since there is an incoming call
[self.gameViewController pauseGame];
}
- (void)applicationDidBecomeActive:(UIApplication *)application {
// the user declined the call and is returning to our app
[self.gameViewController resumeGame];
}
I know that this was answered a long time ago. But I wanted to add that another (more scalable) solution is to have interested parties (e.g., UIViewControllers) register an interest in UIApplicationDidEnterBackgroundNotification and UIApplicationWillEnterForegroundNotification.
This approach has the advantage that the Application Delegate doesn't need to have direct knowledge of the objects that might need to respond to entering background/foreground.
What's the code to subscribe to an event like applicationWillResignActive in any place in your iphone application?
[UPDATE]
Let me rephrase my question. I don't want to respond to this in my application delegate, but rather listen to this event from another class. Is that possible or I need to pass the event from the application delegate to the concerning class?
Looks like you are looking for this code.
- (void) applicationWillResign {
NSLog(#"About to lose focus");
}
- (void) myMethod {
[[NSNotificationCenter defaultCenter]
addObserver:self
selector:#selector(applicationWillResign)
name:UIApplicationWillResignActiveNotification
object:NULL];
}
Take a look at the documentation for the method you're talking about:
applicationWillResignActive:
Tells the delegate that the application will become inactive. This method is optional.
- (void)applicationWillResignActive:(UIApplication *)application
[...]
Discussion
[...]
Just before it becomes inactive, the application also posts a UIApplicationWillResignActiveNotification.
Implement the method below in your application delegate:
-(void)applicationWillResignActive:(UIApplication *)application
This allows you to react when the application becomes inactive - when this is the case, it is executing but not dispatching incoming events. This happens, for example, when an overlay window pops up or when the device is locked.
Just before it becomes inactive, the application also posts a UIApplicationWillResignActiveNotification.
Your topic and question are asking slightly different things.
Your application will receive applicationWillResignActive, along with applicationWillTerminate, automatically. No subscription is necessary, just implement the function in your app.
As to how to respond, this is down to the application. While you can choose to do nothing the recommended behavior is that you cease or slow any non-critical functionality. E.g. if you were a game you would stop updating the display and/or pause the game.