Am trying to implementent onPause() and onResume(), such that when am out of the activity the the text in my text view is still there, but its displaying "null" when i start the the activity please assist!
#Override
protected void onPause() {
// TODO Auto-generated method stub
super.onPause();
etPassenger.setText(""+ gotPassenger );
etStaffNumber.setText("" + gotStaffNumber);
}
#Override
protected void onResume() {
// TODO Auto-generated method stub
super.onResume();
etPassenger.setText(""+ gotPassenger );
etStaffNumber.setText("" + gotStaffNumber);
}
I think gotPassenger and gotStaffNumber vars are null - if you want to save them than you have to use prefs or save them to some bundle to restore later.
When you are minimizing your activity your variables becoming null.
Add the following code in your activity,
#Override
public void onSaveInstanceState(Bundle savedInstanceState)
{
savedInstanceState.putString("gotPassenger",gotPassenger);
savedInstanceState.putString("gotStaffNumber",gotStaffNumber);
}
And, in your onCreate() method, add the following,
if(savedInstanceState!=null)
{
etPassenger.setText(savedInstanceState.getString("gotPassenger"));
etStaffNumber.setText(savedInstanceState.getString("gotStaffNumber"));
}
When you are leaving your activity, you will loose the data stored inside gotPassenger and gotStaffNumber.
If you want to reuse them after exiting your application, you have to use SharedPreferences to save them first and retrieve them when you are back.
If you want to save your data even when closing your app you need to use sharedPreferences. Here's how you use them
Related
I'm trying to save a TextView value that changes on a button click and keep it stored until I kill the app.
I am trying to use onSaveInstanceState and onRestoreInstanceState to save and restore as long as the app is running. It doesn't work for me. Here is my code.
TextView questionText;
Button button ;
String perso1;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_settings);
perso1 = MainActivity.perso;
questionText = (TextView)findViewById(R.id.perso);
questionText.setText(perso1));
getSupportActionBar().setIcon(R.drawable.ic_back_icon);
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
getSupportActionBar().setTitle(R.string.settings);
button = (Button) findViewById(R.id.button1);
button.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
resetConsent();
questionText.setText("You clicked on the button");
}
});
}
#Override
protected void onSaveInstanceState(Bundle outState) {
// TODO Auto-generated method stub
super.onSaveInstanceState(outState);
String newtext = questionText.getText().toString();
outState.putString("TEXT", newtext);
}
#Override
protected void onRestoreInstanceState(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onRestoreInstanceState(savedInstanceState);
questionText.setText(savedInstanceState.getString("TEXT"));
}
I'm trying to keep the new value of textview when I click on the button until I kill the app. What am I doing wrong?
ViewModel is what you need!
Why
The ViewModel class is designed to store and manage UI-related data in a lifecycle conscious way. The ViewModel class allows data to survive configuration changes such as screen rotations.
It makes your life easier. You don't need to think on how to save it in youe savedInstanceState, but you can just store the String in your ViewModel (as a LiveData), then observe it.
With LiveData, you can change the value everytime the button clicked, and observe the value everytime it changes.
You can always try to save state in a different way.
#Override
protected void onSaveInstanceState(Bundle outState) {
// TODO Auto-generated method stub
super.onSaveInstanceState(outState);
String newtext = questionText.getText().toString();
outState.putString("TEXT", newtext);
}
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_settings);
//check if there was a previous saved state
if(savedInstanceState != null){
//get the value you stored earlier in onSaveInstanceState()
perso1 = savedInstanceState.getString("TEXT");
}
questionText = (TextView)findViewById(R.id.perso);
questionText.setText(perso1));
//....
}
But this is just another way to save state.
I think i your error is explained below.
//you did this correctly- look, you set questionText here
onRestoreInstanceState(Bundle savedInstanceState){
super.onRestoreInstanceState(savedInstanceState);
//set the questionText below
questionText.setText(savedInstanceState.getString("TEXT"));
}
but then in onCreate() you set the questionText again. This time to an incorrect value.
perso1 = MainActivity.perso;//< -- setting perso1 to nothing?
questionText = (TextView)findViewById(R.id.perso);
questionText.setText(perso1));//<-- setting questionText again
onRestoreInstanceState
This method is called between onStart() and onPostCreate(Bundle).
In onSaveInstanceState() you did it correctly, in onRestoreInstanceState() you did it correctly, in onCreate() you set the value again to the wrong value.
Additionally read this when deciding to keep saving state this way or using a ViewModel
For simple data, the activity can use the onSaveInstanceState() method and restore its data from the bundle in onCreate(), but this approach is only suitable for small amounts of data that can be serialized then deserialized, not for potentially large amounts of data like a list of users or bitmaps.
I have an activity with "singleTask" mode. when this activity goes to background by taping on home key or other application, which methods will be called if it backs to foreground?
onCreate(Bundle savedInstanceState) with savedInstanceState != null
onRestoreInstanceState(Bundle savedInstanceState)
I think because there is one instance of this activity, it doesn't need to save and restore its state and it retain its own state always. am I right?
The sequence of methods that will be invoked is as follows,(in case when Android has killed the process hosting the Activity while the application was in the background, ) when Activity with singleTask mode comes in foreground:
1.onCreate 2.onStart 3.onRestoreInstanceState and 4.onResume
Below is sample code to demonstrate the concept: Activity Declaration in AndroidManifest.xml: <activity android:name="Second" android:launchMode="singleTask"></activity>
public class Second extends Activity {
EditText mEdit;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.imageview_not);
if (savedInstanceState!=null){
Log.e("onCreate of Actiity", savedInstanceState.getString("editval")); }
mEdit=(EditText) findViewById(R.id.editText1);
}
#Override
protected void onResume() {
// TODO Auto-generated method stub
super.onResume();
Log.e("Second", "onResume");
}
#Override
protected void onStart() {
// TODO Auto-generated method stub
super.onStart();
Log.e("Second", "onStart");
}
#Override
protected void onSaveInstanceState(Bundle outState) {
// TODO Auto-generated method stub
super.onSaveInstanceState(outState);
outState.putString("editval", mEdit.getText().toString());
}
#Override
protected void onRestoreInstanceState(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onRestoreInstanceState(savedInstanceState);
Log.e("Second", "onRestoreInstanceState");
if (savedInstanceState!=null){
Log.e("onRestoreInstanceState", savedInstanceState.getString("editval"));
}
}
}
For illustration purpose, I am just using Edit Text and Android saves its state during configuration change, or when user press HOME etc.
Note that onSaveInstanceState(Bundle outState) is called before an activity may be killed so that when it comes back some time in the future it can restore its state using onRestoreInstanceState(Bundle savedInstanceState).
Also as mentioned by David in another Answer,If Android has not killed the process hosting the Activity, then bringing the task from the background to the foreground will not cause either onCreate() nor onRestoreInstanceState() to be called.
If Android has not killed the process hosting the Activity, then bringing the task from the background to the foreground will not cause either onCreate() nor onRestoreInstanceState() to be called. The Activity doesn't need to be created (it already exists) and the state doesn't need to be restored, because it hasn't been changed.
If, however, Android has killed the process hosting the Activity while the application was in the background, when the user returns to the application Android will create a new process for the application, create a new instance of the Activity, call onCreate() passing the saved instance Bundle as a parameter. It will also call onRestoreInstanceState() passing the saved instance Bundle as a parameter.
I am creating a calculator application, when my activity is sent to background and then brought to front.The result in it becomes zero. How can i save the data nd retrive it next time hen activity is recreated.
For that specific case, you want to use the Activity lifecycle methods onSaveInstanceState and onRestoreInstanceState. Override both those methods, and then save the necessary data in onSaveInstanceState. In the onCreate or the onRestoreInstanceState check for the existence of the saved data and then restore it to the right place.
Note: you can use preferences or a database as well, but those are generally to be used for data that should last more than a single background/restore cycle. The onSaveInstanceState/onRestoreInstanceState methods are specifically for the case where an Activity gets sent to the background and then restored later.
Use SharedPreferences like :
SharedPreferences preferences = null;
SharedPreferences.Editor editor = null;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
preferences = PreferenceManager.getDefaultSharedPreferences(this);
}
in onDestory() write :
#Override
protected void onDestroy() {
// TODO Auto-generated method stub
super.onDestroy();
editor = preferences.edit();
editor.putInt(YOUR_KEY, YOUR_VALUE);
editor.commit();
}
and in onStart() write :
#Override
protected void onStart() {
// TODO Auto-generated method stub
super.onStart();
int result = preferences.getInt(YOUR_KEY, YOUR_VALUE);
}
Hope this will help you
So in my application I am using SharedPreferences to save fragment state. But I would like to delete those entries inside the SharedPreferences once the user steps outside of the application. I tried the following:
In my main class:
#Override
protected void onPause() {
// TODO Auto-generated method stub
super.onPause();
if(isFinishing() == true)
{
SM.removePreferences();
}
}
where SM is an instance of a helper class I created. removerPreferences does the following:
public void removePreferences(){
editor.clear();
editor.commit();
}
But I noticed that this was never executed. With the log, I did see that the app goes inside the isFinishing() if statement, but the method is never executed. I also did try the onDestroy(), but the method never got called.
Can someone help me on this ?
use onstop override to do that
like this:
#Override
protected void onStop() {
// TODO Auto-generated method stub
super.onStop();
if(isFinishing() == true)
{
SM.removePreferences();
}
}
Don't save your Fragment's instance state in SharedPreferences, but in the Bundle that is meant to do that. You can access it like this:
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
if ((savedInstanceState != null) {
// get your values, for example:
mID = savedInstanceState.getInt("ID");
}
}
#Override
public void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
// put your values, for example:
outState.putInt("ID", mID);
}
This way you don't have to manage the values yourself.
If you have custom Objects, you can make them implement Parcelable.
In contrast, SharedPreferences are meant to save values that should persist even after the application closes, i.e.: preferences.
The better location to do that is onDestroy() without the if statement.
however, you can read from Android documentation about onDestroy() that:
There are situations where the system will simply kill the activity's hosting process without calling this method (or any others) in it, so it should not be used to do things that are intended to remain around after the process goes away.
So, in my opinion, if you don't want data remains after activity ends, you should use a class to hold it.
I think that what you're looking for can be achieved using onSaveInstanceState mechanism.
Nonetheless, I'll try answering your specific question while assuming that by saying that "the method is never implemented" you mean that the if statement value is always false and that your method doesn't get called.
isFinishing() returns true only when you called finish() on the Activity or if someone else has requested that it will be finished.
If you just click on the home button, you will get isFinishing() == false, thus your method doesn't gets called. So make sure you're actually finishing the Activity and not just pausing it.
Anyways, the best way to find out what's the problem is to use the debugger.
I have an activity that allows the user to start a second activity. The second activity has a list of items which I add to an array list. When I return to the previous activity I want to display the size of the array list.
However I am having a problem with onResume(). It is called when my first activity is created and as a result generates an error as the array list does not exist when it is first launched!
onResume():
#Override
protected void onResume() {
// TODO Auto-generated method stub
super.onResume();
getIntentData();
calcSubTotal(orderData);
}
getIntentData():
public void getIntentData(){
b = new Bundle();
b = getIntent().getExtras();
orderData = b.getParcelable("order");
Toast.makeText(this.getApplicationContext(), orderData.size(), Toast.LENGTH_LONG).show();
}
onCreate() of second activity:
#Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_starters);
createTestData();
b = new Bundle();
orderData = new MenuItemList();
adapter = new MenuItemArrayAdapter(this, starters);
this.setListAdapter(adapter);
}
#Override
protected void onListItemClick(ListView l, View v, int position, long id) {
Toast.makeText(this.getApplicationContext(), l.getItemAtPosition(position).toString() + " clicked", Toast.LENGTH_LONG).show();
//add clicked item to orderData....
MenuItem m = (MenuItem)l.getItemAtPosition(position);
//create new item
orderData.add(m);
}
Any idea how I might be able to control this?
ERROR:
java.lang.RuntimeException: Unable to resume activity {com.example.waitronproto3/com.example.waitronproto3.SectionsActivity}: java.lang.NullPointerException
I think you may want to have a look at startActivityForResult instead, when you're starting your second Activity. It'll allow your second activity to return a result back to your first activity. You can read up on it at the Activity documentation, specifically the "Starting Activities and Getting Results" section of the document.
Edit: By the looks of your code - nothing you're doing is either storing a bundle from the second activity and sending it back to the first. So you'll never get the proper Bundle data in your first activity. As suggested, look into startActivityForResult to launch your second activity with. This will allow you to return data back into your first activity with ease.
However I am having a problem with onResume(). It is called when my first activity is created and as a result generates an error as the array list does not exist when it is first launched!
I recommend changing getIntentData() to check if the appropriate data exists first:
public void getIntentData(){
Intent intent = getIntent();
if(intent != null && intent.hasExtra("order")) {
orderData = b.getParcelable("order");
Toast.makeText(this.getApplicationContext(), orderData.size(), Toast.LENGTH_LONG).show();
calculateSubTotal(order);
}
}
And update onResume():
#Override
protected void onResume() {
super.onResume();
getIntentData();
}
(Though you could simply put getIntentData() in onResume() now.)
Your onResume() will be called after onCreate() according to the Android Lifecycle so you will want to check that the data is not null before trying to use it.
`if(intentData != null)
//do something`