I have a PreferenceActivity with settings for my app and I want to refresh activity if some preferences was changed.
For example I have a checkbox which responsible for addtional tab in my layout, when checkbox is checked tab must be shown. To catch this event I used OnSharedPreferenceChangeListener. But this listener listen every click on this checkbox and do something (your logic) every time, every click even though setting really was not changed. I want to refresh my activity only if setting was really changed. If earlier was "OFF" and now become "ON" in this case I want to refresh, but if I changed OFF - ON - OFF I don't want to refresh.
How to catch really changes and how to handle this in activity?
Thanks!
How to catch really changes and how to handle this in activity?
Step #1: Implement the OnSharedPreferenceChangeListener on your main activity.
Step #2: Maintain a boolean data member, initially false, which you toggle whenever your checkbox of interest is changed.
Step #3: In onStart() or onResume(), if the boolean data member is true, refresh the activity and set the data member to false.
Related
As i understand it, would it not be better to create a fragments event listeners in the fragments onCreate? If it is done in onCreateView it would have to be redone everytime the fragment comes back into view (onResume())? Would it make a difference where it is set?
1) yes it can be better
2) yes you are correct, as event listener is initialised there than the process will be repeated here
3) please have a close look at life-cycle method
4)it always makes difference where you are using and when you are initializing.
An event is set on a view and hence is restored when the view is restored. For example, lets say we set a listener on a button in a fragment that is created in onCreateView. If at some point of time, if the fragment is restored (without a call to onCreateView), the button is restored along with the listener that is set. The same goes for setting a text/background for a button - you don't have to reset the text/background each time the fragment is resumed.
I have 2 Fragments. 1st is for calculation while the 2nd is for settings.
I save the settings using SharedPreference.Editor.commit() on onPause() method. No problem so far with the saving. The problem I am facing is retrieving the SharedPreference value on my 1st Fragment. I retrieved the value every time I pressed the count button. For the 1st time, the values I am getting are the ones before change (which is the problem I am facing), I will only get my saved value when retrieving/pressing the count button for the 2nd time or more.
And I try to change the settings and then press home button to terminate the app from outside (which triggers onPause method) and when I reopened the settings, the values did change to my defined settings. So, I am sure the settings did saved when onPause is triggered.
I wonder what is going wrong here. Any helps is much appreciated.
As requested, this is my saving code on my SettingFragment :
#Override
public void onPause() {
super.onPause();
saveToPref();
}
public void saveToPref() {
SharedPreferences settings = getActivity().getSharedPreferences("mysettings", 0);
Editor edit = settings.edit();
edit.putString("begin", String.valueOf(ibegin)).putString("end", String.valueOf(iend)).commit();
}
Initialize your SharedPreferences object somewhere else, and do it once - maybe in onCreate. The reason why you're not seeing the change is because a different instance of SharedPreferences is opened somewhere, with the same constructor, and multiple instances of these do not automatically resolve/merge. While you're at it, initialize the Editor edit instance along with settings.
Ok, I have found my problem. The problem is that onPause() is triggered only when I start another activity (I started an activity onClick of Button count). I changed my code to trigger the saveToPref() by overriding onPageSelected of my ViewPager and on backPressed of my MainActivity.
I realized that there are lots of question on this topic already asked on SO.
But I don't even know the basic when it comes to saving the state of an activity.
(Refer Screenshot Below) When app launches,
1) ScrollView item 1,2,3,4 are visible
2) table containd data which is populated due to Gainer button.
As showed in below screenshots, While app is running in PORTRAIT mode, I
1)scrolled down to ScrollView item 4,5,6
2)pressed the Loser button so accordingly data in the table below the button changes.
3)I'll even change content of graph dynamically(which I had not done yet).
Now I switch to LANDSCAPE Mode so
1)ScrollView is showing ScrollView item 1,2,3,4
2)table is showing data which is populated due to pressing Gainer button.
3)graph is as it is as I've not changed it yet(which I will change later).
So what happens is when I change the orientation, my activity is getting re-launched. So if user is performing some task in one orientation and he changes the orientation, then whole progress will be lost.
I know I need to save the state of the activity and Restore it when orientation changes.
But I don't know from where to start and what to save.
ANY HELP WILL BE LIFE-SAVER !
Option #1: Override onSaveInstanceState() of your Activity and put whatever information you want in the supplied Bundle. Your new activity instance will receive that Bundle in onRestoreInstanceState() (or onCreate()). Here is a sample project demonstrating this.
Option #2: Override onRetainNonConfigurationInstance() of your Activity and return some object that represents your state. Your new activity instance can call getLastNonConfigurationInstance() to retrieve that object, so the new activity can apply that information. Be careful, though, not to have the old activity return something in the object that holds a reference back to the old activity (e.g., a widget, an instance of a regular inner class). Here is a sample project demonstrating this.
Option #3: Convert this activity to a fragment. Have the fragment call setRetainInstance(true); on itself during its initial setup. Add the fragment dynamically to some activity via a FragmentTransaction. Now, when the configuration changes, the fragment is retained, so all your widgets and state are retained. Here is an overly-complex sample application demonstrating this.
Those are the three recommended approaches nowadays.
I have a ListView that is inside a TabWidget. When I select an item on the ListView and go to the child ListView, the TabWidget disappears. This is fine, except that it invokes the onPause method, and thus causes onRestart to be called when I return to the parent ListView.
I have onRestart setup to retrieve updated data from the server, but I do not want this to occur everytime the user returns to the parent ListView. I only want onRestart to be called when the app comes alive from running in the background. I have tried implementing a Boolean variable to determine if I should execute the code that is inside onRestart, but there doesn't seem to be a way to get around the effects of this.
Ideas?
You could fire off your child activity with startActivityForResult and set a flag in onActivityResult to not reload (which should be called when the user backs into the listview from the detail page). You'd have a member variable (let's say mReload) that you'd set to true in onCreate and onRestart, and to false in onActivityResult, then process the reload onResume if mReload is true (and set it back to false so a normal resume won't trigger the reload).
Alternative: just set a flag (mLeftPage) in your activity on the row's click listener. On restart, if mLeftPage is true, don't reload the list and set mLeftPage back to false. Otherwise, reload.
I will try to explain a simple app scenario: My app goes right to a 'main view'. In this main view I have inserted a TextView which displays current settings created by way of the PreferenceManager. For simplicity sake, let's say I have a checkbox in my settings. When I first start my app - the TextView on my main view shows my checkbox setting correctly (true). Now I go to the settings menu, it pops-up, and then I change it to false. I go back to the main view and see no change. It still say's true even after I changed it to false. If I end the app and then re-start it - all is well and it shows my change.
Apparently the main view just stays in the background while I'm changing settings? How can I redraw or update the main view after I change settings?
You could implement OnSharedPreferenceChangeListener in your main Activity:
#Override
public void onSharedPreferenceChanged(SharedPreferences prefs, String key) {
if (PREFKEY_OF_INTEREST.equals(key))
updateSomethingInMainView();
}
and in onCreate() call:
SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(this);
prefs.registerOnSharedPreferenceChangeListener(this);
When you go into your preferences your current activity should be paused and the resumed when you go back (see the lifecycle diagram on lifecycle diagram on the android site). You should be able to trigger some kind of redraw from within onResume() I would think. That will allow the data on the page to repopulate. Some sort of invalidate() call would do it I guess.