[NO-CI] improved theme

This commit is contained in:
Mariotaku Lee 2016-12-20 08:10:45 +08:00
parent 983bd4cb70
commit b715088437
16 changed files with 561 additions and 113 deletions

View File

@ -3,7 +3,8 @@ package org.mariotaku.chameleon;
import android.app.Activity;
import android.content.Context;
import android.content.res.TypedArray;
import android.os.Build;
import android.graphics.Color;
import android.support.annotation.IntDef;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.support.v4.util.ArrayMap;
@ -13,8 +14,10 @@ import android.support.v7.app.AppCompatDelegate;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.view.Window;
import org.mariotaku.chameleon.internal.ChameleonInflationFactory;
import org.mariotaku.chameleon.internal.WindowSupport;
/**
* Created by mariotaku on 2016/12/18.
@ -61,8 +64,11 @@ public class Chameleon {
statusBarColorHandled = true;
}
}
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP && !statusBarColorHandled) {
activity.getWindow().setStatusBarColor(theme.getStatusBarColor());
if (!statusBarColorHandled) {
final Window window = activity.getWindow();
final int statusBarColor = theme.getStatusBarColor();
WindowSupport.setStatusBarColor(window, statusBarColor);
ChameleonUtils.applyLightStatusBar(window, statusBarColor, theme.getLightStatusBarMode());
}
}
@ -98,27 +104,34 @@ public class Chameleon {
*/
public static class Theme {
private int colorPrimary;
private int colorAccent;
private int colorToolbar;
private int colorBackground;
private int colorForeground;
private boolean toolbarColored;
private int textColorPrimary;
private int textColorSecondary;
private int textColorLink;
private int colorPrimary;
private int colorPrimaryDark;
private int colorAccent;
private int colorEdgeEffect;
private int colorControlNormal;
private int colorControlActivated;
private int statusBarColor;
private int navigationBarColor;
private int colorToolbar;
private boolean toolbarColored;
@LightStatusBarMode
private int lightStatusBarMode = LightStatusBarMode.NONE;
Theme() {
}
public int getColorAccent() {
return colorAccent;
}
public void setColorAccent(int colorAccent) {
this.colorAccent = colorAccent;
}
public int getColorPrimary() {
return colorPrimary;
}
@ -127,13 +140,44 @@ public class Chameleon {
this.colorPrimary = colorPrimary;
}
public int getColorPrimaryDark() {
if (colorPrimaryDark == 0) {
return ChameleonUtils.darkenColor(getColorPrimary());
}
return colorPrimaryDark;
}
public void setColorPrimaryDark(int colorPrimaryDark) {
this.colorPrimaryDark = colorPrimaryDark;
}
public int getColorAccent() {
return colorAccent;
}
public void setColorAccent(int color) {
this.colorAccent = color;
}
public int getColorEdgeEffect() {
if (colorEdgeEffect == 0) {
return getColorPrimary();
}
return colorEdgeEffect;
}
public void setColorEdgeEffect(int color) {
if (color == colorPrimary) return;
this.colorEdgeEffect = color;
}
public int getColorToolbar() {
if (colorToolbar == 0) return colorPrimary;
return colorToolbar;
}
public void setColorToolbar(int colorToolbar) {
this.colorToolbar = colorToolbar;
public void setColorToolbar(int color) {
this.colorToolbar = color;
}
public boolean isToolbarColored() {
@ -144,14 +188,6 @@ public class Chameleon {
this.toolbarColored = toolbarColored;
}
public int getTextColorPrimary() {
return textColorPrimary;
}
public void setTextColorPrimary(int textColorPrimary) {
this.textColorPrimary = textColorPrimary;
}
public int getColorBackground() {
return colorBackground;
}
@ -168,23 +204,36 @@ public class Chameleon {
this.colorForeground = colorForeground;
}
@NonNull
public static Theme from(Context context) {
Theme theme = new Theme();
TypedArray a = context.obtainStyledAttributes(R.styleable.ChameleonTheme);
theme.setColorPrimary(a.getColor(R.styleable.ChameleonTheme_colorPrimary, 0));
theme.setColorAccent(a.getColor(R.styleable.ChameleonTheme_colorAccent, 0));
theme.setColorToolbar(a.getColor(R.styleable.ChameleonTheme_colorToolbar, theme.getColorPrimary()));
theme.setColorBackground(a.getColor(R.styleable.ChameleonTheme_android_colorBackground, 0));
theme.setColorForeground(a.getColor(R.styleable.ChameleonTheme_android_colorForeground, 0));
theme.setToolbarColored(a.getBoolean(R.styleable.ChameleonTheme_isToolbarColored, true));
a.recycle();
return theme;
public int getTextColorPrimary() {
return textColorPrimary;
}
public void setTextColorPrimary(int textColorPrimary) {
this.textColorPrimary = textColorPrimary;
}
public int getTextColorSecondary() {
return textColorSecondary;
}
public void setTextColorSecondary(int textColorSecondary) {
this.textColorSecondary = textColorSecondary;
}
public int getTextColorLink() {
if (textColorLink == 0) {
return getColorAccent();
}
return textColorLink;
}
public void setTextColorLink(int textColorLink) {
this.textColorLink = textColorLink;
}
public int getStatusBarColor() {
if (statusBarColor == 0) {
return ChameleonUtils.darkenColor(getColorToolbar());
return getColorPrimaryDark();
}
return statusBarColor;
}
@ -192,6 +241,86 @@ public class Chameleon {
public void setStatusBarColor(int statusBarColor) {
this.statusBarColor = statusBarColor;
}
public int getNavigationBarColor() {
return navigationBarColor;
}
public void setNavigationBarColor(int navigationBarColor) {
this.navigationBarColor = navigationBarColor;
}
public void setColorControlNormal(int color) {
if (color == textColorSecondary) return;
this.colorControlNormal = color;
}
public int getColorControlNormal() {
if (colorControlNormal == 0) {
return getTextColorSecondary();
}
return colorControlNormal;
}
public int getColorControlActivated() {
if (colorControlActivated == 0) {
return getColorAccent();
}
return colorControlActivated;
}
public void setColorControlActivated(int color) {
if (color == colorAccent) return;
this.colorControlActivated = color;
}
public void setLightStatusBarMode(@LightStatusBarMode int mode) {
this.lightStatusBarMode = mode;
}
@LightStatusBarMode
public int getLightStatusBarMode() {
return lightStatusBarMode;
}
@NonNull
public static Theme from(Context context) {
Theme theme = new Theme();
TypedArray a = context.obtainStyledAttributes(R.styleable.ChameleonTheme);
theme.setColorBackground(a.getColor(R.styleable.ChameleonTheme_android_colorBackground, 0));
theme.setColorForeground(a.getColor(R.styleable.ChameleonTheme_android_colorForeground, 0));
theme.setColorPrimary(a.getColor(R.styleable.ChameleonTheme_colorPrimary, 0));
theme.setColorPrimaryDark(a.getColor(R.styleable.ChameleonTheme_colorPrimaryDark, 0));
theme.setColorAccent(a.getColor(R.styleable.ChameleonTheme_colorAccent, 0));
theme.setTextColorPrimary(a.getColor(R.styleable.ChameleonTheme_android_textColorPrimary, 0));
theme.setTextColorSecondary(a.getColor(R.styleable.ChameleonTheme_android_textColorSecondary, 0));
theme.setTextColorLink(a.getColor(R.styleable.ChameleonTheme_android_textColorLink, 0));
theme.setColorEdgeEffect(a.getColor(R.styleable.ChameleonTheme_colorEdgeEffect, 0));
theme.setColorControlNormal(a.getColor(R.styleable.ChameleonTheme_colorControlNormal, 0));
theme.setColorControlActivated(a.getColor(R.styleable.ChameleonTheme_colorControlNormal, 0));
theme.setStatusBarColor(a.getColor(R.styleable.ChameleonTheme_android_statusBarColor, 0));
theme.setNavigationBarColor(a.getColor(R.styleable.ChameleonTheme_android_navigationBarColor, Color.BLACK));
theme.setColorToolbar(a.getColor(R.styleable.ChameleonTheme_colorToolbar, theme.getColorPrimary()));
theme.setToolbarColored(a.getBoolean(R.styleable.ChameleonTheme_isToolbarColored, true));
a.recycle();
return theme;
}
@IntDef({LightStatusBarMode.NONE, LightStatusBarMode.AUTO, LightStatusBarMode.ON,
LightStatusBarMode.OFF})
public @interface LightStatusBarMode {
int NONE = 0;
int AUTO = 1;
int ON = 2;
int OFF = 3;
}
}
/**

View File

@ -3,10 +3,22 @@ package org.mariotaku.chameleon;
import android.app.Activity;
import android.content.Context;
import android.content.ContextWrapper;
import android.content.res.ColorStateList;
import android.graphics.Color;
import android.graphics.PorterDuff;
import android.graphics.drawable.Drawable;
import android.os.Build;
import android.support.annotation.CheckResult;
import android.support.annotation.ColorInt;
import android.support.annotation.FloatRange;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.support.v4.graphics.drawable.DrawableCompat;
import android.util.AttributeSet;
import android.view.View;
import android.view.Window;
import org.mariotaku.chameleon.Chameleon.Theme.LightStatusBarMode;
/**
* Created by mariotaku on 2016/12/18.
@ -41,6 +53,29 @@ public class ChameleonUtils {
return shiftColor(color, 0.9f);
}
// This returns a NEW Drawable because of the mutate() call. The mutate() call is necessary because Drawables with the same resource have shared states otherwise.
@CheckResult
@Nullable
public static Drawable createTintedDrawable(@Nullable Drawable drawable, @ColorInt int color) {
if (drawable == null) return null;
drawable = DrawableCompat.wrap(drawable.mutate());
DrawableCompat.setTintMode(drawable, PorterDuff.Mode.SRC_IN);
DrawableCompat.setTint(drawable, color);
return drawable;
}
// This returns a NEW Drawable because of the mutate() call. The mutate() call is necessary because Drawables with the same resource have shared states otherwise.
@CheckResult
@Nullable
public static Drawable createTintedDrawable(@Nullable Drawable drawable, @NonNull ColorStateList sl) {
if (drawable == null) return null;
drawable = DrawableCompat.wrap(drawable.mutate());
DrawableCompat.setTintList(drawable, sl);
return drawable;
}
@CheckResult
@Nullable
public static Activity getActivity(Context context) {
if (context instanceof Activity) return (Activity) context;
if (context instanceof ContextWrapper) {
@ -48,4 +83,30 @@ public class ChameleonUtils {
}
return null;
}
public static int getColorDependent(int color) {
final boolean isLight = isColorLight(color);
return isLight ? Color.BLACK : Color.WHITE;
}
public static void applyLightStatusBar(Window window, int statusBarColor,
@LightStatusBarMode int lightStatusBarMode) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
final View decorView = window.getDecorView();
final int systemUiVisibility = decorView.getSystemUiVisibility();
boolean isLightStatusBar;
if (lightStatusBarMode == LightStatusBarMode.ON) {
isLightStatusBar = true;
} else if (lightStatusBarMode == LightStatusBarMode.AUTO) {
isLightStatusBar = isColorLight(statusBarColor);
} else {
isLightStatusBar = false;
}
if (isLightStatusBar) {
decorView.setSystemUiVisibility(systemUiVisibility | View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR);
} else {
decorView.setSystemUiVisibility(systemUiVisibility & ~View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR);
}
}
}
}

View File

@ -17,6 +17,7 @@ import org.mariotaku.chameleon.view.ChameleonAutoCompleteTextView;
import org.mariotaku.chameleon.view.ChameleonEditText;
import org.mariotaku.chameleon.view.ChameleonFloatingActionButton;
import org.mariotaku.chameleon.view.ChameleonMultiAutoCompleteTextView;
import org.mariotaku.chameleon.view.ChameleonProgressBar;
import org.mariotaku.chameleon.view.ChameleonSwipeRefreshLayout;
import org.mariotaku.chameleon.view.ChameleonTextView;
import org.mariotaku.chameleon.view.ChameleonToolbar;
@ -76,6 +77,10 @@ public class ChameleonInflationFactory implements LayoutInflaterFactory {
view = new ChameleonMultiAutoCompleteTextView(context, attrs);
break;
}
case "ProgressBar": {
view = new ChameleonProgressBar(context, attrs);
break;
}
case "android.support.design.widget.FloatingActionButton": {
view = new ChameleonFloatingActionButton(context, attrs);
break;

View File

@ -1,4 +1,4 @@
package org.mariotaku.chameleon;
package org.mariotaku.chameleon.internal;
import android.annotation.SuppressLint;
import android.content.Context;
@ -7,6 +7,10 @@ import android.graphics.drawable.ColorDrawable;
import android.graphics.drawable.Drawable;
import android.util.AttributeSet;
import org.mariotaku.chameleon.Chameleon;
import org.mariotaku.chameleon.ChameleonUtils;
import org.mariotaku.chameleon.R;
/**
* Created by mariotaku on 2016/12/18.
*/

View File

@ -0,0 +1,26 @@
package org.mariotaku.chameleon.internal;
import android.annotation.TargetApi;
import android.os.Build;
import android.view.Window;
/**
* Created by mariotaku on 14/10/23.
*/
public class WindowSupport {
private WindowSupport() {
}
public static void setStatusBarColor(Window window, int color) {
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) return;
WindowAccessorLollipop.setStatusBarColor(window, color);
}
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
private static class WindowAccessorLollipop {
public static void setStatusBarColor(Window window, int color) {
window.setStatusBarColor(color);
}
}
}

View File

@ -0,0 +1,90 @@
package org.mariotaku.chameleon.view;
import android.app.Activity;
import android.content.Context;
import android.graphics.Color;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.support.v4.widget.DrawerLayout;
import android.util.AttributeSet;
import android.view.Window;
import org.mariotaku.chameleon.Chameleon;
import org.mariotaku.chameleon.Chameleon.Theme.LightStatusBarMode;
import org.mariotaku.chameleon.ChameleonUtils;
import org.mariotaku.chameleon.ChameleonView;
import org.mariotaku.chameleon.internal.WindowSupport;
/**
* Created by mariotaku on 2016/12/19.
*/
public class ChameleonDrawerLayout extends DrawerLayout implements ChameleonView, ChameleonView.StatusBarThemeable {
public ChameleonDrawerLayout(Context context) {
super(context);
}
public ChameleonDrawerLayout(Context context, AttributeSet attrs) {
super(context, attrs);
}
public ChameleonDrawerLayout(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
}
@Override
public boolean isPostApplyTheme() {
return false;
}
@Nullable
@Override
public Appearance createAppearance(Context context, AttributeSet attributeSet, Chameleon.Theme theme) {
Appearance appearance = new Appearance();
appearance.setStatusBarColor(theme.getStatusBarColor());
appearance.setLightStatusBarMode(theme.getLightStatusBarMode());
return appearance;
}
@Override
public void applyAppearance(@NonNull ChameleonView.Appearance appearance) {
Appearance a = (Appearance) appearance;
final int statusBarColor = a.getStatusBarColor();
final Activity activity = ChameleonUtils.getActivity(getContext());
if (activity != null) {
final Window window = activity.getWindow();
WindowSupport.setStatusBarColor(window, Color.TRANSPARENT);
ChameleonUtils.applyLightStatusBar(window, statusBarColor, a.getLightStatusBarMode());
}
setStatusBarBackgroundColor(statusBarColor);
}
@Override
public boolean isStatusBarColorHandled() {
return true;
}
public static class Appearance implements ChameleonView.Appearance {
int statusBarColor;
@LightStatusBarMode
int lightStatusBarMode;
public int getStatusBarColor() {
return statusBarColor;
}
public void setStatusBarColor(int statusBarBackgroundColor) {
this.statusBarColor = statusBarBackgroundColor;
}
@LightStatusBarMode
public int getLightStatusBarMode() {
return lightStatusBarMode;
}
public void setLightStatusBarMode(@LightStatusBarMode int lightStatusBarMode) {
this.lightStatusBarMode = lightStatusBarMode;
}
}
}

View File

@ -2,17 +2,23 @@ package org.mariotaku.chameleon.view;
import android.content.Context;
import android.content.res.ColorStateList;
import android.graphics.drawable.Drawable;
import android.support.annotation.ColorInt;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.support.v4.content.ContextCompat;
import android.support.v4.view.ViewCompat;
import android.support.v7.widget.AppCompatEditText;
import android.util.AttributeSet;
import android.widget.TextView;
import org.mariotaku.chameleon.Chameleon;
import org.mariotaku.chameleon.ChameleonTypedArray;
import org.mariotaku.chameleon.ChameleonUtils;
import org.mariotaku.chameleon.ChameleonView;
import org.mariotaku.chameleon.R;
import org.mariotaku.chameleon.internal.ChameleonTypedArray;
import java.lang.reflect.Field;
/**
* Created by mariotaku on 2016/12/18.
@ -63,16 +69,40 @@ public class ChameleonEditText extends AppCompatEditText implements ChameleonVie
public static void apply(TextView view, Appearance appearance) {
view.setLinkTextColor(appearance.getLinkTextColor());
ViewCompat.setBackgroundTintList(view, ColorStateList.valueOf(appearance.getBackgroundColor()));
setCursorTint(view, appearance.getBackgroundColor());
}
public static Appearance create(Context context, AttributeSet attributeSet, Chameleon.Theme theme) {
Appearance appearance = new Appearance();
ChameleonTypedArray a = ChameleonTypedArray.obtain(context, attributeSet,
R.styleable.ChameleonEditText, theme);
appearance.setLinkTextColor(a.getColor(R.styleable.ChameleonEditText_android_textColorLink, theme.getColorAccent()));
appearance.setLinkTextColor(a.getColor(R.styleable.ChameleonEditText_android_textColorLink, theme.getTextColorLink()));
appearance.setBackgroundColor(a.getColor(R.styleable.ChameleonEditText_backgroundTint, theme.getColorAccent()));
a.recycle();
return appearance;
}
public static void setCursorTint(@NonNull TextView textView, @ColorInt int color) {
try {
Field fCursorDrawableRes = TextView.class.getDeclaredField("mCursorDrawableRes");
fCursorDrawableRes.setAccessible(true);
int mCursorDrawableRes = fCursorDrawableRes.getInt(textView);
Field fEditor = TextView.class.getDeclaredField("mEditor");
fEditor.setAccessible(true);
Object editor = fEditor.get(textView);
Class<?> clazz = editor.getClass();
Field fCursorDrawable = clazz.getDeclaredField("mCursorDrawable");
fCursorDrawable.setAccessible(true);
Drawable[] drawables = new Drawable[2];
drawables[0] = ContextCompat.getDrawable(textView.getContext(), mCursorDrawableRes);
drawables[0] = ChameleonUtils.createTintedDrawable(drawables[0], color);
drawables[1] = ContextCompat.getDrawable(textView.getContext(), mCursorDrawableRes);
drawables[1] = ChameleonUtils.createTintedDrawable(drawables[1], color);
fCursorDrawable.set(editor, drawables);
} catch (Exception e) {
e.printStackTrace();
}
}
}
}

View File

@ -8,9 +8,10 @@ import android.support.design.widget.FloatingActionButton;
import android.util.AttributeSet;
import org.mariotaku.chameleon.Chameleon;
import org.mariotaku.chameleon.ChameleonTypedArray;
import org.mariotaku.chameleon.ChameleonUtils;
import org.mariotaku.chameleon.ChameleonView;
import org.mariotaku.chameleon.R;
import org.mariotaku.chameleon.internal.ChameleonTypedArray;
/**
* Created by mariotaku on 2016/12/18.
@ -40,7 +41,9 @@ public class ChameleonFloatingActionButton extends FloatingActionButton implemen
Appearance appearance = new Appearance();
ChameleonTypedArray a = ChameleonTypedArray.obtain(context, attributeSet,
R.styleable.ChameleonFloatingActionButton, theme);
appearance.backgroundTint = a.getColor(R.styleable.ChameleonFloatingActionButton_backgroundTint, theme.getColorAccent());
final int backgroundTint = a.getColor(R.styleable.ChameleonFloatingActionButton_backgroundTint, theme.getColorAccent());
appearance.setBackgroundTint(backgroundTint);
appearance.setIconTint(ChameleonUtils.getColorDependent(backgroundTint));
a.recycle();
return appearance;
}
@ -48,11 +51,34 @@ public class ChameleonFloatingActionButton extends FloatingActionButton implemen
@Override
public void applyAppearance(@NonNull ChameleonView.Appearance appearance) {
Appearance a = (Appearance) appearance;
setBackgroundTintList(ColorStateList.valueOf(a.backgroundTint));
setBackgroundTintList(ColorStateList.valueOf(a.getBackgroundTint()));
final int iconTint = a.getIconTint();
if (iconTint == 0) {
clearColorFilter();
} else {
setColorFilter(iconTint);
}
}
public static class Appearance implements ChameleonView.Appearance {
int backgroundTint;
private int backgroundTint;
private int iconTint;
public int getBackgroundTint() {
return backgroundTint;
}
public void setBackgroundTint(int backgroundTint) {
this.backgroundTint = backgroundTint;
}
public int getIconTint() {
return iconTint;
}
public void setIconTint(int iconTint) {
this.iconTint = iconTint;
}
}
}

View File

@ -0,0 +1,69 @@
package org.mariotaku.chameleon.view;
import android.content.Context;
import android.graphics.drawable.Drawable;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.support.v4.graphics.drawable.DrawableCompat;
import android.util.AttributeSet;
import android.widget.ProgressBar;
import org.mariotaku.chameleon.Chameleon;
import org.mariotaku.chameleon.ChameleonView;
/**
* Created by mariotaku on 2016/12/18.
*/
public class ChameleonProgressBar extends ProgressBar implements ChameleonView {
public ChameleonProgressBar(Context context) {
super(context);
}
public ChameleonProgressBar(Context context, AttributeSet attrs) {
super(context, attrs);
}
public ChameleonProgressBar(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
@Override
public boolean isPostApplyTheme() {
return false;
}
@Nullable
@Override
public Appearance createAppearance(Context context, AttributeSet attributeSet, Chameleon.Theme theme) {
Appearance appearance = new Appearance();
appearance.setProgressColor(theme.getColorAccent());
return appearance;
}
@Override
public void applyAppearance(@NonNull ChameleonView.Appearance appearance) {
final Appearance a = (Appearance) appearance;
final Drawable indeterminateDrawable = getIndeterminateDrawable();
if (indeterminateDrawable != null) {
DrawableCompat.setTint(indeterminateDrawable, a.getProgressColor());
}
final Drawable progressDrawable = getProgressDrawable();
if (progressDrawable != null) {
DrawableCompat.setTint(progressDrawable, a.getProgressColor());
}
}
public static class Appearance implements ChameleonView.Appearance {
private int progressColor;
public int getProgressColor() {
return progressColor;
}
public void setProgressColor(int progressColor) {
this.progressColor = progressColor;
}
}
}

View File

@ -7,9 +7,9 @@ import android.support.v7.widget.AppCompatTextView;
import android.util.AttributeSet;
import org.mariotaku.chameleon.Chameleon;
import org.mariotaku.chameleon.ChameleonTypedArray;
import org.mariotaku.chameleon.ChameleonView;
import org.mariotaku.chameleon.R;
import org.mariotaku.chameleon.internal.ChameleonTypedArray;
/**
* Created by mariotaku on 2016/12/18.
@ -39,7 +39,7 @@ public class ChameleonTextView extends AppCompatTextView implements ChameleonVie
Appearance appearance = new Appearance();
ChameleonTypedArray a = ChameleonTypedArray.obtain(context, attributeSet,
R.styleable.ChameleonTextView, theme);
appearance.setLinkTextColor(a.getColor(R.styleable.ChameleonTextView_android_textColorLink, theme.getColorAccent()));
appearance.setLinkTextColor(a.getColor(R.styleable.ChameleonTextView_android_textColorLink, theme.getTextColorLink()));
a.recycle();
return appearance;
}

View File

@ -9,7 +9,7 @@ import android.support.v7.widget.Toolbar;
import android.util.AttributeSet;
import org.mariotaku.chameleon.Chameleon;
import org.mariotaku.chameleon.ChameleonTypedArray;
import org.mariotaku.chameleon.internal.ChameleonTypedArray;
import org.mariotaku.chameleon.ChameleonView;
import org.mariotaku.chameleon.R;

View File

@ -1,11 +1,33 @@
<?xml version="1.0" encoding="utf-8"?>
<resources>
<declare-styleable name="ChameleonTheme">
<attr name="colorPrimary"/>
<attr name="colorAccent"/>
<attr name="colorToolbar" format="color"/>
<!-- Basic colors -->
<attr name="android:colorForeground"/>
<attr name="android:colorBackground"/>
<attr name="colorPrimary"/>
<attr name="colorPrimaryDark"/>
<attr name="colorAccent"/>
<!-- Text colors -->
<attr name="android:textColorPrimary"/>
<attr name="android:textColorSecondary"/>
<attr name="android:textColorLink"/>
<!-- Colors based on base colors -->
<attr name="colorEdgeEffect" format="color"/>
<attr name="colorControlNormal"/>
<attr name="colorControlActivated"/>
<attr name="colorControlHighlight"/>
<attr name="colorButtonNormal"/>
<attr name="colorSwitchThumbNormal"/>
<attr name="android:statusBarColor"/>
<attr name="android:navigationBarColor"/>
<attr name="colorToolbar" format="color"/>
<attr name="isToolbarColored" format="boolean"/>
</declare-styleable>
<declare-styleable name="ChameleonTextView">

View File

@ -1,20 +1,13 @@
package org.mariotaku.twidere.view;
import android.content.Context;
import android.graphics.Color;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.support.v4.view.GravityCompat;
import android.support.v4.widget.DrawerLayout;
import android.util.AttributeSet;
import android.view.MotionEvent;
import org.mariotaku.chameleon.Chameleon;
import org.mariotaku.chameleon.ChameleonUtils;
import org.mariotaku.chameleon.ChameleonView;
import org.mariotaku.twidere.util.support.WindowSupport;
import org.mariotaku.chameleon.view.ChameleonDrawerLayout;
public class HomeDrawerLayout extends DrawerLayout implements ChameleonView, ChameleonView.StatusBarThemeable {
public class HomeDrawerLayout extends ChameleonDrawerLayout {
private ShouldDisableDecider mShouldDisableDecider;
private int mStartLockMode, mEndLockMode;
@ -56,42 +49,6 @@ public class HomeDrawerLayout extends DrawerLayout implements ChameleonView, Cha
return super.dispatchTouchEvent(ev);
}
@Override
public boolean isPostApplyTheme() {
return false;
}
@Nullable
@Override
public Appearance createAppearance(Context context, AttributeSet attributeSet, Chameleon.Theme theme) {
Appearance appearance = new Appearance();
WindowSupport.setStatusBarColor(ChameleonUtils.getActivity(context).getWindow(), Color.TRANSPARENT);
appearance.setStatusBarBackgroundColor(ChameleonUtils.darkenColor(theme.getColorToolbar()));
return appearance;
}
@Override
public void applyAppearance(@NonNull ChameleonView.Appearance appearance) {
Appearance a = (Appearance) appearance;
setStatusBarBackgroundColor(a.getStatusBarBackgroundColor());
}
@Override
public boolean isStatusBarColorHandled() {
return true;
}
public static class Appearance implements ChameleonView.Appearance {
int statusBarBackgroundColor;
public int getStatusBarBackgroundColor() {
return statusBarBackgroundColor;
}
public void setStatusBarBackgroundColor(int statusBarBackgroundColor) {
this.statusBarBackgroundColor = statusBarBackgroundColor;
}
}
public interface ShouldDisableDecider {
boolean shouldDisableTouch(MotionEvent e);

View File

@ -4,7 +4,6 @@ import android.content.Context;
import android.content.res.Resources;
import android.content.res.TypedArray;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.PorterDuff;
import android.graphics.drawable.Drawable;
@ -232,8 +231,7 @@ public class TabPagerIndicator extends RecyclerView implements PagerIndicator, C
public Appearance createAppearance(Context context, AttributeSet attributeSet, Chameleon.Theme theme) {
final Appearance appearance = new Appearance();
final int toolbarColor = theme.getColorToolbar();
final boolean isLight = ChameleonUtils.isColorLight(toolbarColor);
final int itemColor = isLight ? Color.BLACK : Color.WHITE;
final int itemColor = ChameleonUtils.getColorDependent(toolbarColor);
appearance.setLabelColor(itemColor);
appearance.setIconColor(itemColor);
if (theme.isToolbarColored()) {

View File

@ -19,6 +19,7 @@
package org.mariotaku.twidere.view;
import android.app.Activity;
import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.Canvas;
@ -32,10 +33,13 @@ import android.support.v4.view.ViewCompat;
import android.support.v4.view.WindowInsetsCompat;
import android.util.AttributeSet;
import android.view.View;
import android.view.Window;
import org.mariotaku.chameleon.Chameleon;
import org.mariotaku.chameleon.Chameleon.Theme.LightStatusBarMode;
import org.mariotaku.chameleon.ChameleonUtils;
import org.mariotaku.chameleon.ChameleonView;
import org.mariotaku.chameleon.internal.WindowSupport;
import org.mariotaku.twidere.R;
import org.mariotaku.twidere.view.iface.TintedStatusLayout;
@ -133,14 +137,22 @@ public class TintedStatusFrameLayout extends ExtendedFrameLayout implements Tint
@Override
public Appearance createAppearance(Context context, AttributeSet attributeSet, Chameleon.Theme theme) {
Appearance appearance = new Appearance();
appearance.setColor(ChameleonUtils.darkenColor(theme.getColorToolbar()));
appearance.setStatusBarColor(theme.getStatusBarColor());
appearance.setLightStatusBarMode(theme.getLightStatusBarMode());
return appearance;
}
@Override
public void applyAppearance(@NonNull ChameleonView.Appearance appearance) {
Appearance a = (Appearance) appearance;
setStatusBarColor(a.getColor());
final int statusBarColor = a.getStatusBarColor();
setStatusBarColor(statusBarColor);
final Activity activity = ChameleonUtils.getActivity(getContext());
if (activity != null) {
final Window window = activity.getWindow();
WindowSupport.setStatusBarColor(window, Color.TRANSPARENT);
ChameleonUtils.applyLightStatusBar(window, statusBarColor, a.getLightStatusBarMode());
}
}
@Override
@ -149,14 +161,25 @@ public class TintedStatusFrameLayout extends ExtendedFrameLayout implements Tint
}
public static class Appearance implements ChameleonView.Appearance {
int color;
private int statusBarColor;
@LightStatusBarMode
private int lightStatusBarMode;
public int getColor() {
return color;
public int getStatusBarColor() {
return statusBarColor;
}
public void setColor(int color) {
this.color = color;
public void setStatusBarColor(int statusBarColor) {
this.statusBarColor = statusBarColor;
}
@LightStatusBarMode
public int getLightStatusBarMode() {
return lightStatusBarMode;
}
public void setLightStatusBarMode(@LightStatusBarMode int lightStatusBarMode) {
this.lightStatusBarMode = lightStatusBarMode;
}
}

View File

@ -40,6 +40,7 @@ import android.view.View
import com.squareup.otto.Bus
import org.mariotaku.chameleon.Chameleon
import org.mariotaku.chameleon.ChameleonActivity
import org.mariotaku.chameleon.ChameleonUtils
import org.mariotaku.kpreferences.KPreferences
import org.mariotaku.twidere.BuildConfig
import org.mariotaku.twidere.TwidereConstants.SHARED_PREFERENCES_NAME
@ -86,6 +87,19 @@ open class BaseActivity : ChameleonActivity(), IExtendedActivity, IThemedActivit
// Registered listeners
private val controlBarOffsetListeners = ArrayList<IControlBarActivity.ControlBarOffsetListener>()
private val userTheme: Chameleon.Theme by lazy {
val theme = Chameleon.Theme.from(this)
theme.colorAccent = ThemeUtils.getUserAccentColor(this)
theme.colorPrimary = ThemeUtils.getUserAccentColor(this)
if (theme.isToolbarColored) {
theme.colorToolbar = theme.colorPrimary
}
theme.statusBarColor = ChameleonUtils.darkenColor(theme.colorToolbar)
theme.textColorLink = ThemeUtils.getOptimalAccentColor(theme.colorAccent, theme.colorForeground)
return@lazy theme
}
// Data fields
private var systemWindowsInsets: Rect? = null
var keyMetaState: Int = 0
@ -340,13 +354,7 @@ open class BaseActivity : ChameleonActivity(), IExtendedActivity, IThemedActivit
}
override fun getOverrideTheme(): Chameleon.Theme {
val theme = Chameleon.Theme.from(this)
theme.colorAccent = ThemeUtils.getUserAccentColor(this)
theme.colorPrimary = ThemeUtils.getUserAccentColor(this)
if (theme.isToolbarColored) {
theme.colorToolbar = theme.colorPrimary
}
return theme
return userTheme
}
companion object {