Android 實現一鍵切換應用主題顏色 [復制鏈接]

2018-11-26 10:26
hellokenken 閱讀:674 評論:0 贊:0
Tag:  
最近項目中要實現切換應用主題的功能,下面就來說一說我在項目中是怎么實現這個功能的,一般我們需要改變整個應用的背景顏色可以直接這樣設置getWindow().getDecorView().setBackgroundColor(int color)。但是這種方式顯然不是我們想要的,而且還有許多不好的地方。為什么呢?第一、它會把整個頁面的背景顏色都改變了。第二、布局的背景還必須是透明的才會有效果。所以這種方式有的時候是滿足不了我們的需求的。下面我將為大家介紹我的解決方案,下面是一個實現的效果圖。



 

    上面效果圖中點擊設置應用主題顏色按鈕,然后跳轉至主題顏色選擇界面,在界面中選擇相應的主題顏色,可以發現界面的title布局會立即跟隨所選擇的主題顏色進行切換。下面我將貼出相應的代碼片段。



1、定義一個監聽顏色改變的接口

public interface OnColorChangedListener {
void onColorChanged(int color);
}


2、創建一個主題顏色管理類
import java.util.ArrayList;
import java.util.List;
import android.content.Context;
import com.qiulong.changedmotivecolortest.R;
import com.qiulong.changedmotivecolortest.activity.MyApplication;
 
public class ColorManager {
 
public static final int DEFAULT_COLOR = 0xFF0C89D8;
private final List<OnColorChangedListener> listeners = new ArrayList<OnColorChangedListener>();
private int mCurrentColor = DEFAULT_COLOR;
private static ColorManager instance;
 
public static ColorManager getInstance() {
if (instance == null) {
return instance = new ColorManager();
}
return instance;
}
 
public void addListener(OnColorChangedListener listener) {
if (!this.listeners.contains(listener)) {
if (listener != null) {
listener.onColorChanged(mCurrentColor);
this.listeners.add(listener);
}
}
}
 
public void removeListener(OnColorChangedListener listener) {
this.listeners.remove(listener);
}
 
public void notifyColorChanged(int color) {
if (mCurrentColor == color) {
return;
}
mCurrentColor = color;
for (OnColorChangedListener listener : this.listeners) {
if (listener != null) {
listener.onColorChanged(color);
}
}
}
 
public int[] getSkinColor(Context context) {
return context.getResources().getIntArray(R.array.default_color_array);
}
 
public void setSkinColor(Context context, int position) {
int[] colorArr = context.getResources().getIntArray(
R.array.default_color_array);
MyApplication.mPreference.setSkinColorValue(colorArr[position]);
notifyColorChanged(colorArr[position]);
}
 
}


3、自定義一個LinearLayout重寫onAttachedToWindow以及onDetachedFromWindow方法,以及實現OnColorChangedListener監聽接口的OnColorChanged(int color)方法,當然你也可以繼承其它的View。
import com.qiulong.changedmotivecolortest.mode.ColorManager;
import com.qiulong.changedmotivecolortest.mode.OnColorChangedListener;
import android.content.Context;
import android.graphics.LightingColorFilter;
import android.graphics.drawable.ColorDrawable;
import android.util.AttributeSet;
import android.widget.LinearLayout;
 
public class ColorLinearLayout extends LinearLayout implements
OnColorChangedListener {
 
public ColorLinearLayout(Context context, AttributeSet attrs,
int defStyleAttr) {
super(context, attrs, defStyleAttr);
// TODO Auto-generated constructor stub
}
 
public ColorLinearLayout(Context context, AttributeSet attrs) {
super(context, attrs);
// TODO Auto-generated constructor stub
}
 
public ColorLinearLayout(Context context) {
super(context);
// TODO Auto-generated constructor stub
}
 
@Override
public void onColorChanged(int color) {
if (getBackground() != null
&& !(getBackground() instanceof ColorDrawable)) {
getBackground().setColorFilter(new LightingColorFilter(color, 1));
} else {
setBackgroundColor(color);
}
}
 
@Override
protected void onAttachedToWindow() {
ColorManager.getInstance().addListener(this);
super.onAttachedToWindow();
}
 
@Override
protected void onDetachedFromWindow() {
ColorManager.getInstance().removeListener(this);
super.onDetachedFromWindow();
}
 
}

4、主題顏色選擇Activity
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;
import com.qiulong.changedmotivecolortest.R;
import com.qiulong.changedmotivecolortest.mode.ColorManager;
 
public class MotiveActivity extends Activity {
 
private final int[] layouts = { R.id.skin_01, R.id.skin_02, R.id.skin_03,
R.id.skin_04, R.id.skin_05 };
 
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_motive);
initView();
}
 
private void initView() {
findViewById(R.id.motive_back).setOnClickListener(
new OnClickListener() {
@Override
public void onClick(View v) {
finish();
}
});
int colorArr[] = ColorManager.getInstance().getSkinColor(this);
for (int i = 0; i < layouts.length; i++) {
View view = findViewById(layouts[i]);
View color = view.findViewById(R.id.motive_item_color);
View selected = view.findViewById(R.id.motive_item_selected);
color.setBackgroundColor(colorArr[i]);
if (colorArr[i] == MyApplication.mPreference.getSkinColorValue()) {
selected.setVisibility(View.VISIBLE);
}
color.setOnClickListener(new OnSkinColorClickListener(i));
}
}
 
class OnSkinColorClickListener implements OnClickListener {
 
private int position;
 
public OnSkinColorClickListener(int position) {
this.position = position;
}
 
@Override
public void onClick(View v) {
for (int i = 0; i < layouts.length; i++) {
View view = findViewById(layouts[i]);
View selected = view.findViewById(R.id.motive_item_selected);
selected.setVisibility(i == position ? View.VISIBLE : View.GONE);
ColorManager.getInstance().setSkinColor(MotiveActivity.this,
position);
}
}
}
 
}

5、最后貼上主題顏色arrays.xml
<!-- 應用主題顏色 -->
    <integer-array name="default_color_array">
        <item>0xFF0C89D8</item>
        <item>0xFFB32CD1</item>
        <item>0xFFF676C1</item>
        <item>0xFF04BA19</item>
        <item>0xFF18D9BF</item>
    </integer-array>


以上內容僅供參考和學習,如有不妥之處歡迎指正,謝謝。


我來說兩句
您需要登錄后才可以評論 登錄 | 立即注冊
facelist
所有評論(0)
領先的中文移動開發者社區
18620764416
7*24全天服務
意見反饋:[email protected]

掃一掃關注我們

Powered by Discuz! X3.2© 2001-2019 Comsenz Inc.( 粵ICP備15117877號 )

两码中特期期