I've done a fair bit of searching for my issue, but can't find any solutions to my exact problem.
I have an app that has 3 activities in succession. The main activity (on launch), the second activity (where most of the meat and guts live), and then a final activity that is more or less a summary page of what happens in the 2nd activity.
I run into this issue semi-sporadically where if I keep the 2nd activity running in the background (turn the screen of my phone off, or just hit home) and then hit the launcher icon to go back to the app, it creates a new instance instead of returning to my 2nd activity that is running in the background. I can't find any rhyme or reason as to why it happens sometimes and not others (usually it doesn't). Most of the time it takes me right back to my 2nd activity and all is good in the world, but on occasion, it fires up another instance.
Is there anyway to check if an instance is running and ALWAYS return to that instance if there is?
When you hit Home or the screen turns off, the app automatically goes through the onStop() phase. Depending upon the available memory, the app might become a candidate to be killed by the Android OS. There really is no way to prevent the OS from killing an app that is no longer in the foreground - this is an Android OS design. This should most likely not happen if you do not have a lot of applications open.
If the first instance of the app is still around and you launch the app, it will automatically retrieve this instance. Android is designed to never create a second instance of the same app while the first one is still running. Hence there is no way to check is an instance is running. You could use logging inside onDestroy() to see when the app terminates. But again, Android does not always call onDestroy() and might just simply terminate the app.
Related
I've noticed an issue when I pause my app, say by pressing home, and then bring up the list of recent apps (via the square button) to resume it.
If I resume it shortly after pausing it, it works fine. But if I leave it paused for too long, i.e. a few hours or overnight, then when I touch its window to resume it, it just posts a "failed to start..." toast and removes the app from the list.
I've searched around, but haven't found any info about what would cause this or how to start debugging it.
My theory would be that is has to do with the activity lifecycle. You can find it here:
https://developer.android.com/training/basics/activity-lifecycle/starting.html
When an app is paused, the onPause() function is called, and if the app is paused, and the system needs memory for another app that is running in the foreground, it will stop, or destroy the activity. When you go back into the app, it calls the onCreate() and onStart() functions
I don't know how your app is structured, but my guess is that when the activity is stopped, it is leaving behind some kind of code that needs to reference something that is no longer there, or destroying the referenced thing itself. Then, when onStart() is called, it checks for that thing that is no longer there and crashes.
The best way to fix this is to make sure that each step of the life cycle isn't referencing anything that could possibly be non existent at the time it is called.
When the user leaves a task by pressing the Home button, the current activity is stopped and its task goes into the background. The system retains the state of every activity in the task. If the user later resumes the task by selecting the launcher icon that began the task, the task comes to the foreground and resumes the activity at the top of the stack.
If the user leaves a task for a long time, the system clears the task of all activities except the root activity. When the user returns to the task again, only the root activity is restored. The system behaves this way, because, after an extended amount of time, users likely have abandoned what they were doing before and are returning to the task to begin something new.
You might look up into the Android documentation regarding Tasks and Back Stack and upon some information about Pausing and Resuming an activity. :)
You issue probably related to memory management on android. It looks like android kills you app to release memory so that it can be used by another app. I have an app with very complex layout (The app loads too many images). After some times, when I run the app from recent app list, it always run the app from start. Not from the last state where I left the app. Anywa, nothing to worry about. This is normal behaviour.
As of my concern this is your problem-
you are starting an activity.
then you press home button. and the activity goes to background.
when you start the app after 5 minutes the app starts from the paused activity. but when you start app after 5 hours the app starts from the beginning.
Solution-
This is happening because the activity is being killed in background by the android system.
the application can be killed by calling the ondestroy() method of the activity.
and when the app goes to background it is added to the application stack of the android system. when ever android needs more memory for any operation it takes memory from the last application in the application stack. it kills the last application and takes its memory.
this is the reason your app is being killed after long time. your app is at the last of the stack and android has killed your app to get memory.
you can find more explanation of the process here.
How to solve this problem
this can be solved by bringing your app to front of the stack periodically.
you can run a service from your activity in background so that is stays on top side of stack.
or save the last opened activity in a shared preference and go to this activity when the app starts.
My Android app checks if a specific service is not running, in my Activity's onResume method. If it hasn't been started, then it goes into the background (via startService) and stays there for an action. Clicking on a button causes the service to go into the foreground and it works great. Now the problem:
Scenario #1 :
The foreground service has a button, which sends it back to the background and stops it. I click on it and after that I close my app (the activities from the recents view). Even the Android monitor shows me that it's not running and works as it should.
Scenario #2: (The not expected behavior)
First I close the app (the activities) and then I click on the service's close button. In this case, I can clearly see that my app still uses the same amount of memory it used while the activities were opened. When I reopen my app, I can see that it continues working where I left it (at least the internal app variables don't get garbage collected) Sometimes the CPU usage monitor shows that methods get called, but not from my app. Only Android SDK functions. I couldn't see objects kept in the memory, but a lot of chat[], String, FinalizerReferences etc...
What could cause this? Ruined context lifecycle? Memory leak?
I have an offline-online application, i found a strange issue in it, may be it is not, but i did'nt understand about it..
App requirement is that, if internet is available, even from starting app or from resuming, i call webservices and store data in sqlite, otherwise app stays in offline mode,
I have 2 activities, second activity contains an id, that i passes through intent (that point is important),
My Problem:
if i am in second activity, and internet is running, and i press home button , then this 2nd activity pauses, then stop which is a default behavior in android, i goto settings, turn wifi off, then press app icon again to get back in my app, here i got confused, i expect that my app now will be in onResume, but when i see in logcat its onCreated called and app
crashes, nullPointerException occurs, because this 2nd activity does not have that id, i passed through intent..
Note:
If i use recent app button to go to "settings", then come back again after turing wifi off, and repeat all this behavior, then working fine, its onResumes called not oncreate..
My Question
Why it is going in onCreate while i my expectation is to be onResume while i came back from app icon?
The NPE reason is clear, your second activity doesn't have the value and it crashes.
Why do you get different behavior then!?
It's because the launching intents are different. When you "task switch" Android is merely stopping your app but leaving it there (no guarantee) in case you want to switch back.
Going home (with home) is a clear indication that you want to leave the app, and although it will remain in memory and cached (as long as there is available memory), going back through the launcher (or App Icon as you call it) fires the LAUNCHER category (which goes to your Activity 1 first).
Take a look at this StackOverflow question (and answer) to better understand the consequences.
In any case, your problem is that your app must always be designed to resume in an inconsistent state and be able to recover. Android will kill your references, will destroy your variables and most likely send your app to hell overnight even if you have it running… if the phone goes on standby, chances are processes that aren't doing anything will be paused/stopped and likely killed.
Re-design your app so this is not a problem.
You say:
"I have 2 activities, second activity contains an id, that i passes
through intent (that point is important),"
Well, why not make it easier and have ONE activity and TWO fragments? Then use Fragment Arguments to pass the value?
Or why not store the value in the preferences and/or a local database and recover it during onCreate?
And also why not make it so that if Activity 2 doesn't have a value, it calls Activity 1 and closes itself (better than a crash, huh?).
Etc.
As you can see there are multiple things you should consider. All in all, never trust that your app will be alive, because it won't.
Once your activity's onStop gets called it's susceptible to be killed by the android system to collect resources for other apps which is what i think happened in your case.If it is killed, android will obviously call OnCreate when you get back to the activity.Check this for clarification. For experimenting you can try opening more than one apps from your recent apps and then return to your app. It may crash there too now.
You stated that you can see that the activitiy is stopped (onStop) if you go to the settings. That is the behaviour shown in the Android activity lifecycle. The counterpart for onStop is onCreate. So it does what the documentation tells us. Btw activities are paused if they are visible in some way and get stopped if they are not visible anymore. This would explain why your activity get paused. For further information read Managing the Activity Lifecycle. You can find a whole picture of the lifecycle here.
This type of behaviour can be seen when you change some system configurations like font type,font size or language. But turning wifi on/off won't destroy the app and recreate it again. Check http://developer.android.com/guide/topics/manifest/activity-element.html#config for more information
In my app I have a simple button that launches a second activity, starts a spinner (If that's relevant) and does some http connection work. This second activity can also be launched by a service that runs and listens to a bluetooth connection.
The problem is not happening on my milestone (2.1-update1) phone but on a colleagues phone who is running 2.3 I believe. When they press the button to launch the second activity (Ignoring the service portion completely) it will launch the activity multiple times, when they press back on that second screen they land on another instance of that second screen instead of being back on the first activity.
I mention the service part of this for two reason, the first being that this problem started happening when I implemented the service, and the second being because I had a separate problem where the clients weren't being managed correctly on the service side so that when the second activity was being launched through the service instead of the button I would see exactly this behavior. Since the message was being sent to all clients (There should only be one) I was seeing the service spawn multiple launches of this second activity. But again by pressing the button this service problem which has been fixed shouldn't be responsible.
Now, I have put two things in place to prevent this from happening anymore. I have flagged the second activity as singleTask (android:launchMode="singleTask") and noticed that I had been launching the second activity as startActivityForResult, but wasn't setting or using that when it came back. This wasn't causing any errors or anything, but I changed it to a plain startActivity.
I do not have physical access to the other phone so I can't hook it up to logcat or anything, as it is in another office elsewhere.
The other phone isn't seeing the problem anymore but I am worried that I have hidden the problem rather than really fixing it, and was wondering if anyone could provide some insight?
I've had a problem before where different phones exhibited different symptoms when starting services. Some would restart (kill and start) the service multiple times and others would not. I'm taking a guess that because your friend's phone restarts the service multiple times somehow your activity is getting called each time it restarts.
Try this, can you show notifications in your service? If so do:
startForeground(ID_NOTIFICATION, notification);
This makes the service always run in the foreground and it is less likely to be killed by android.
I thought when I exit the app on the device and it is not visible anymore in the taskmanager the app would restart from the very beginning when I start it again.
But for some reason my app keeps some variables from the previous run and does not really restart correctly.
This happens only if restarted on the device itself. Restarting with Eclipse starts the app correctly from the very start initializing all variables.
Why is this? Is my assumption wrong that when exiting the app all classes and variables will be destroyed?
Many thanks
Well, it's more complicated than just that.
First of all, you will not see the normal Android application lifecycle when you're running it in the debugger. Killing and restarting the app will indeed start you from the beginning. The normal Android app lifecycle is not very intuitive to developers, though. Normally, if a user 'backs' out of an app to the Android home-screen, one would expect your app to be killed once there are no Activities alive. This is not the case. The Android OS will keep your application alive in memory until memory pressure causes it to release the app. This is done because if the user 'opens' the application again, it will start up much, much faster. I'll point out that your Application's onDestroy() method will actually never be killed, because that surprises some developers too.
If, however, you still have Activities alive, but they are in the background, and the Android needs memory, it will kill your activities, but will call onSaveInstanceState before doing so. This will give your Activity an opportunity to save its state in a Bundle, and in fact, most of this will be done for you by the default implementation. At this point, if all of your Activities are killed, your application will be killed, but the Android will still hold onto the saved state and from the user's point of view, the application is still alive (it will still show up in the list of active applications). When the user returns to the application, the Android will re-construct the top-most Activity (onCreate will be called, but with the Bundle that contains the contents that were saved with onSaveInstanceState) and display it to the user. As the user pops Activities off the stack again, the ones below will be re-constructed, etc, etc.