Although I easily fixed this issue, the solution should be included in the next update.
I'd give a bit of context on why this happened and how to recreate the problem.
I have a base class BaseActivity which extends ThemeActivity. All my Activity classes extend BaseActivity and so can override syncTheme() and getStartTheme().
Let's say I start from MainActivity which extends BaseActivity and in it's onCreate() it calls ThemeManager.init(activity, getStartTheme()). This happens from the ThemeActivity super class.
However when I navigate to another class say SecondActivity, this is what happens.
onStop() of MainActivity is called.
onCreate() of SecondActivity is called and this is where the ThemeManager instance is initialized again (from the super class ThemeActivity) and changes private activity variable from MainActivity to SecondActivity. This is fine as the current Context would be SecondActivity.
But when I navigate back to MainActivity, this is what happens.
onStop() for SecondActivity is called.
onRestart() for MainActivity is called.
Since the MainActivity is not destroyed and remained on the heap, it just stopped and restarted. It's onCreate() was not called and that means the activity variable in the ThemeManager instance that was reinstantiated when SecondActivity was navigated to still has the private activity variable as the SecondActivity instance (which should have been destroyed when navigated back up). This is a resource leak.
And so whenever I try to change theme in MainActivity, I get a "Cannot run animation on a detached View" error from the ViewAnimator.
I fixed this error by reinstantiating ThemeManager by calling ThemeManager.init(activity, getStartTheme()) in the onRestart() of MainActivity and that fixed my issue.
So I feel onRestart() should be overriden in ThemeActivity and ThemeManager should reinstantiated on that callback.
I did a debug on my code when carrying out the above scenario and found that issue out.
Although I easily fixed this issue, the solution should be included in the next update.
I'd give a bit of context on why this happened and how to recreate the problem.
I have a base class
BaseActivitywhich extendsThemeActivity. All myActivityclasses extendBaseActivityand so can overridesyncTheme()andgetStartTheme().Let's say I start from
MainActivitywhich extendsBaseActivityand in it'sonCreate()it callsThemeManager.init(activity, getStartTheme()). This happens from theThemeActivitysuper class.However when I navigate to another class say
SecondActivity, this is what happens.onStop()ofMainActivityis called.onCreate()ofSecondActivityis called and this is where theThemeManagerinstance is initialized again (from the super classThemeActivity) and changes privateactivityvariable fromMainActivitytoSecondActivity. This is fine as the currentContextwould beSecondActivity.But when I navigate back to
MainActivity, this is what happens.onStop()forSecondActivityis called.onRestart()forMainActivityis called.Since the
MainActivityis not destroyed and remained on the heap, it just stopped and restarted. It'sonCreate()was not called and that means theactivityvariable in theThemeManagerinstance that was reinstantiated whenSecondActivitywas navigated to still has the privateactivityvariable as theSecondActivityinstance (which should have been destroyed when navigated back up). This is a resource leak.And so whenever I try to change theme in
MainActivity, I get a "Cannot run animation on a detached View" error from theViewAnimator.I fixed this error by reinstantiating
ThemeManagerby callingThemeManager.init(activity, getStartTheme())in theonRestart()ofMainActivityand that fixed my issue.So I feel
onRestart()should be overriden inThemeActivityandThemeManagershould reinstantiated on that callback.I did a debug on my code when carrying out the above scenario and found that issue out.