I'm currently using a Samsung Galaxy S4.
I'm developing an app and as long as I don't exit it, it works great. However, if I leave it, it sometimes restarts itself completely and brings up the Login Activity.
I could select it from the active apps list, and it won't happen. If I go and open it up through pressing its app icon, it will sometimes restart. It will definitely restart if I remove it from the active apps list. How do I have it always return to its previous state in the app? Facebook manages it even when the app is removed from the active apps list.
Is Android garbage collecting my app for memory optimization? How would I avoid this.
The onPause() and onResume() methods might be what you're looking for. Check the Facebook SDK for details on persistent authentication, even when the app is closed. Check this SO post out for more details How to keep android applications always be logged in state?
And no, I don't believe this is Android doing any garbage collection.
Add this to the activity tag of your manifest to tell Android that your app will handle any configuration changes itself: android:configChanges="orientation|keyboardHidden"
To prevent users logging in each visit you can use shared preferences to save login credentials
Related
Friends,
does anyone know how to prevent the application from restarting when restoring it? For example, the application is minimized, then restored and it restarts, any way to avoid it?
This is platform dependent, per example in android it depends on the ram available, if the device needs to free resources it will kill your app , if you add some native code to handle this you could do some things to prevent android from doing this. However. It's NOT recommended to do this. If the user exits an app, it wants that, to close the app. If the user presses the home button, it wants to go to another app, and android will keep your app running for some time in case your user comes back to the app.
The best way to do this, is to handle the default flutter lifecycle to store important data in case the system kills the app.
My Android application is being restarted when using the launcher to launch it after I have used the app store to launch it (and visa versa). Is there any way to prevent this?
By restarted I mean that the activity stack is lost. This is important as our users are setting up and returning to an activity in the app intermittently over the course of an hour or so. After first install, they will likely have installed and opened the app from the app store, set themselves up and then backgrounded the app. Later they are likely to open the app from the launcher and lose all their state!
The problem is further compounded as we start a foreground service along with the set-up activity. Clicking the services notification should bring the user back to the set-up activity but, as with the launcher, if the user originally opened the app from the Play store, they again lose all their state!
Reproducing the problem
I've made a sample application here:
https://github.com/samskiter/LaunchTest
Note: it uses the BBC weather application package Id in order to allow you to quickly open from the app store (the "Open" button will be shown on the BBC weather application if this app is installed).
Steps are as follows:
Uninstall the BBC weather app if you have it
Install the LaunchTest app
Close the LaunchTest app from recents
Open the LaunchTest app from the BBC weather app page on the Play Store
Click the button to navigate to the Second activity
Background the application (press home)
Open the LaunchTest application from the app launcher
The state is lost! you are back at the First (root) activity
What I've tried
Using singleTask launch mode hasn't helped - it causes the app to be relaunched even if you use the launcher every time.
I've tried alwaysRetainTaskState - I don't really expect this to work as this only really affects things over about a 30 minute wait.
What I think is going on
There is no mechanism in the activity manager / intent system to open a running app in it's current state. Instead, I think the UID of the launching application is taken into account. If it is different then the Intent.FLAG_ACTIVITY_NEW_TASK flag is forced and so created a new task and dropping all my users' lovely state.
Inspecting Google Maps
Google maps has a very similar interaction model to our application: a setup UI, followed by an ongoing process the user is going through for a long period of time (navigation) with a paired, foreground service (the navigation service you can see in your notification bar). BUT GMaps doesn't suffer from this problem. I think this is because it uses only a single activity for all of it's interface and uses singleTask. So now, when you tap on the launcher after originally launching from the play store, the task can be reused.
In my opinion this exposes a hole in the android intent/activity management system. The whole point of the savedInstanceState/activity lifecycle is to prevent dropping state, but here we have a way to dump everything. My current best solution is to detect app restarts by the fact the service is running and try to get the user back to where they were, which is more than a little tricky.
If someone knows a way I can prevent my state being dropped on the floor when reopening from the app launcher after opening from the store, I would really appreciate it.
This is more like a workaround to your problem, but it seems that there may be no real solution.
My first thought was - since the whole setup will take a while anyway - why don't you just save some kind of bookmark ('firstLaunch') to Preferences, post a (delayed?) notification and finish the app, so that the user has to open it again by tapping on the launcher icon. Only then you start the real setup, so you will not lose information due to the installer vs launcher problem.
But the problem seems to have been around for some time and the following SO-posts may help:
Re-launch of Activity on Home button, but…only the first time
After tap on app icon,launcher create a new instance of root activity again & again
Hope this helps!
I've created a simply web radio streaming app, and on of my app user told me that sometimes when he open another app (for example, Facebook app) my app gets close without error.
How can I trace this event?
Thank you!
It sounds like your app is simply experiencing the standard Activity lifecycle.
When the user leaves your app (eg opens the Facebook app), onStop() is called. From there, the app can either be restarted, it can just sit there, or it can be destroyed.
Since the Facebook app is fairly resource-intensive, I am guessing that the system is destroying your app to free up resources for the Facebook app, or whatever other app is being launched.
If you tell us more about what you are trying to accomplish, we can provide more suggestions on how to do that.
I created an new Android app and succeeded in its working. Its all functionality are working fine. While starting it will ask use name and password.
What my problem was "If my Application is idle for some 4 to 5 hours, then automatically it get quit , while restarting its again asking to login"
I need to know how to avoid automatic quit of my app.
I'm sorry if its simple or already asked quetions.
I need to know how to avoid automatic quit of my app.
No, you do not. Simply redirect the user to log in again, or, as #Rasel suggests, persistently cache credentials in a file or database or something.
Android applications do not and must not live forever. Phones have limited RAM. Android will terminate unused applications after a period of inactivity, to free up RAM for other applications. This is perfectly normal, just as it is perfectly normal for a user to close a Web browser after visiting a Web app.
Its completely natural for the android application.Android OS automatically kill the process when it needs to do.So if you want keep your application alive you have to think differently.To keep always running you can use service that will monitor your application states and handle the situation when it prompts for the login info again.
Another option you can write the login information in the shared preference and can clean when user intentionally leave the application.So when starting again if you find the information you can directly prompt to the user without entering the login information
Android doc say:
"When the system, rather than the user, shuts down an activity to conserve memory, ... "
But how to simulate this situation?I want to debug the onRestoreInstanceState(Bundle) method,but don't know how to.
You can't do it in an automated way b/c its completely non deterministic.
See my answer here: https://stackoverflow.com/a/15048112/909956 for details.
But good news is that all you need to do is just simulate calling onSaveInstanceState and you are indirectly testing this low memory situation.
onSaveInstanceState can be triggered by:
losing focus (by pressing home which in essence is like switching from your app to launcher app), launching another activity, pressing recents
changing orientation. this is the easier way if you are using an emulator
changing developer setting: goto developer options --> Apps --> Don't keep activities. This is best option if you are testing temporarily on an actual device.
I've used the "Don't keep activities" developer option to reproduce a crash that happened when an activity was killed due to memory pressure. You can find it in the Apps section of Settings->Developer Options.
It destroys every activity as soon as you leave it. E.g. if you press home to put your app in the background the current activity is destroyed. See https://stackoverflow.com/a/22402360/2833126 for more information.
There's two way to simulate the android killing process: using the setting "Don't keep activities" in developer settings or killing the app process by yourself.
To kill the process, open the activity you want to test, then press home button to send your app to background, and then, using the DDMS in Android Studio (Android Device Monitor), select the process and then stop the process (as seen in the image below). Your app was killed. Now, open your app again (accessing the list of open apps). Now you can test the killed state.
For the purposes of debugging onRestoreInstanceState(), just change the screen orientation ([Ctrl]-[F11] in the emulator). Your activity will be destroyed and recreated, and the onSaveInstanceState()/onRestoreInstanceState() pair will be invoked.
Use the SetAlwaysFinish app (works on a real device and in the emulator) or use the Google DevTools app (works in the emulator only).
These apps use the hidden AlwaysFinish setting of the ActivityManagerNative class to change the behavior of the OS and cause it to immediate unload every activity as soon as it's no longer in the foreground. This will reliably trigger the onSaveInstanceState and onRestoreInstanceState events.
See link below for more details:
http://bricolsoftconsulting.com/how-to-test-onsaveinstancestate-and-onrestoreinstancestate-on-a-real-device/
To debug onRestoreInstanceState you could do the following:
make sure you can debug application right after its start (calling android.os.Debug.waitForDebugger() from your constructor helps, it hangs your application until debugger is connected),
put you application in some state,
causally kill it from Settings->Apps,
causally switch back to it through Recent Apps button (it will still be in the list),
at this moment your application will be started anew and onRestoreInstanceState will be immediately called on the top activity.
Good answers here.
Now, residing in the distant future, using Instant Run in Android Studio will also trigger a save and restore when activities are restarted with code changes.
There's a decent solution for this in Android 6 and newer. See my answer here: Simulate killing of activity in emulator