onSharedPreferenceChanged not fired if change occurs in separate activity?

Viewed 56186

I've implemented onSharedPreferenceChanged in my main activity.

If I change the preferences in the main activity, my event fires.

If I change the preferences through my preferences screen (PreferenceActivity) my event does NOT fire when preferences are changed (because it's a separate activity and separate reference to sharedPreferences?)

Does anybody have a recommendation of how I should go about overcoming this situation?

Thanks!

EDIT1: I tried adding the event handler right in my preference activity but it never fires. The following method gets called during onCreate of my preference activity. When I change values, it never prints the message (msg() is a wrapper for Log.d).

private void registerChangeListener () {
SharedPreferences sp = PreferenceManager.getDefaultSharedPreferences(this);

    sp.registerOnSharedPreferenceChangeListener(new OnSharedPreferenceChangeListener () {
        public void onSharedPreferenceChanged(SharedPreferences sharedPreferences, String key) {
            msg (" ***** Shared Preference Update ***** ");
            Intent i = new Intent();
            i.putExtra("KEY", key);
            i.setAction("com.gtosoft.dash.settingschanged");

            sendBroadcast(i);

            // TODO: fire off the event
        }
    });
}
9 Answers

Consider keeping PreferencesChangeListener inside Android App class instance. Although it's NOT a clean solution storing reference inside App should stop GC from garbage collecting your listener and you should still be able to receive DB change updates. Remember that preference manager does not store a strong reference to the listener! (WeakHashMap)

/**
 * Main application class
 */
class MyApp : Application(), KoinComponent {

    var preferenceManager: SharedPreferences? = null
    var prefChangeListener: MySharedPrefChangeListener? = null

    override fun onCreate() {
        super.onCreate()

        preferenceManager = PreferenceManager.getDefaultSharedPreferences(this)
        prefChangeListener = MySharedPrefChangeListener()
        preferenceManager?.registerOnSharedPreferenceChangeListener(prefChangeListener)
    }
}

and

class MySharedPrefChangeListener : SharedPreferences.OnSharedPreferenceChangeListener {

    /**
     * Called when a shared preference is changed, added, or removed.
     */
    override fun onSharedPreferenceChanged(sharedPreferences: SharedPreferences?, key: String?) {
        if (sharedPreferences == null)
            return

        if (sharedPreferences.contains(key)) {
            // action to perform
        }
    }
}
Related