Users of my App have the possibility to change the Theme of the Application. You can check this in Play Store: https://play.google.com/store/apps/details?id=at.guger.musixs
Until now, every Activities onApplyThemeResource
-Method is overridden.
This is very costly, but it cannot be done in one way, because every activity has its own peculiarities, e.g. this one has no ActionBar.
There is also one other problem. These styles are not applied to AlertDialogs, as you can see if you check my app!
So is there a better way to apply styles? I saw a module called AppThemeEngine
, which is able to get around with themes, but this one requires superuser-permissions, so it's useless for normal costumers.
@Override
protected void onApplyThemeResource(Resources.Theme theme, int resid, boolean first) {
super.onApplyThemeResource(theme, resid, first);
mPreferences = PreferenceManager.getDefaultSharedPreferences(getApplicationContext());
int iThemeID = R.style.NoActionBarThemeBlue;
String sPrefBlue = getResources().getString(R.string.pref_color_blue);
String sPrefGray = getResources().getString(R.string.pref_color_gray);
String sPrefGreen = getResources().getString(R.string.pref_color_green);
String sPrefOrange = getResources().getString(R.string.pref_color_orange);
String sPrefRed = getResources().getString(R.string.pref_color_red);
String sPrefColor = mPreferences.getString(getResources().getString(R.string.keyThemeColor), sPrefBlue);
if (sPrefColor.equals(sPrefBlue)) {
iThemeID = R.style.NoActionBarThemeBlue;
}
else if (sPrefColor.equals(sPrefGray)) {
iThemeID = R.style.NoActionBarThemeGray;
}
else if (sPrefColor.equals(sPrefGreen)) {
iThemeID = R.style.NoActionBarThemeGreen;
}
else if (sPrefColor.equals(sPrefOrange)) {
iThemeID = R.style.NoActionBarThemeOrange;
}
else if (sPrefColor.equals(sPrefRed)) {
iThemeID = R.style.NoActionBarThemeRed;
}
RuntimeInfo.setThemeID(iThemeID);
theme.applyStyle(iThemeID, true);
}
My styles.xml:
<resources>
<style name="ActionBarThemeBlue" parent="Theme.AppCompat.Light.DarkActionBar">
<item name="android:windowBackground">@android:color/white</item>
<item name="colorPrimary">@color/bluePrimary</item>
<item name="colorPrimaryDark">@color/bluePrimaryDark</item>
<item name="colorAccent">@color/blueAccent</item>
</style>
<style name="NoActionBarThemeBlue" parent="Theme.AppCompat.Light.NoActionBar">
<item name="android:windowBackground">@android:color/white</item>
<item name="colorPrimary">@color/bluePrimary</item>
<item name="colorPrimaryDark">@color/bluePrimaryDark</item>
<item name="colorAccent">@color/blueAccent</item>
</style>
<style name="ActionBarThemeGray" parent="Theme.AppCompat.Light.DarkActionBar">
<item name="android:windowBackground">@android:color/white</item>
<item name="colorPrimary">@color/grayPrimary</item>
<item name="colorPrimaryDark">@color/grayPrimaryDark</item>
<item name="colorAccent">@color/grayAccent</item>
</style>
<style name="NoActionBarThemeGray" parent="Theme.AppCompat.Light.NoActionBar">
<item name="android:windowBackground">@android:color/white</item>
<item name="colorPrimary">@color/grayPrimary</item>
<item name="colorPrimaryDark">@color/grayPrimaryDark</item>
<item name="colorAccent">@color/grayAccent</item>
</style>
<style name="ActionBarThemeGreen" parent="Theme.AppCompat.Light.DarkActionBar">
<item name="android:windowBackground">@android:color/white</item>
<item name="colorPrimary">@color/greenPrimary</item>
<item name="colorPrimaryDark">@color/greenPrimaryDark</item>
<item name="colorAccent">@color/greenAccent</item>
</style>
<style name="NoActionBarThemeGreen" parent="Theme.AppCompat.Light.NoActionBar">
<item name="android:windowBackground">@android:color/white</item>
<item name="colorPrimary">@color/greenPrimary</item>
<item name="colorPrimaryDark">@color/greenPrimaryDark</item>
<item name="colorAccent">@color/greenAccent</item>
</style>
...
</resources>
I hope somebody knows a better way of changing themes! Thanks!
This works very well using the following app theme engine:
https://github.com/garretyoder/app-theme-engine
If you want to support Android O, you'll have to download the library and add the following code to the ATE
class, applyTaskDescription
method:
if (icon == null) {
Drawable mIconDrawable = activity.getApplicationInfo().loadIcon(activity.getPackageManager());
if (mIconDrawable instanceof BitmapDrawable) {
icon = ((BitmapDrawable)mIconDrawable).getBitmap();
} else if (mIconDrawable instanceof AdaptiveIconDrawable) {
icon = getBitmapFromDrawable(mIconDrawable);
}
}