Android动态换肤(一、应用内置多套皮肤)
动态换肤在很多android应用中都有使用,用户根据自己的喜好设置皮肤主题,可以增强用户使用应用的舒适度。
Android换肤可以分为很多种,它们从使用方式,用户体验以及项目框架设计上体现了明显的差异。
接下来几篇文章分别讲解其中比较主流的换肤方式。
应用内置皮肤实现动态切换在技术上是最容易实现的,但有很多局限性,比如不能在使用过程中增减皮肤,除非升级应用,扩展性很弱;如果需要设置皮肤的位置很多,编码起来比较麻烦。主要是使用 SharedPreferences记录当前设置的皮肤序号,然后加载这套皮肤的所有资源,在每个activity中有一个setSkin()的方法设置皮肤。
博主的个人项目好记单词 中的换肤功能就是使用这个方案,感兴趣可以下载看一看,效果还不错。
实现:
确定需要换肤的地方
首先要确定应用中那些界面需要换肤,他们有什么共性?比如天天动听,一套以蓝色为基调的皮肤,所有的界面title应该是蓝色的,所有的按钮也是蓝色系列的…,这样就可以确定一套皮肤需要哪些颜色以及资源文件。
确定一套皮肤需要的资源(其余皮肤按照第一套皮肤模板做)
比如首页,四个模块,其中本地音乐和最近播放的颜色是一样的,这里需要两个颜色值(正常和按下状态),歌曲下载和MV下载的颜色是一样的,这里也需要两个颜色值,每个界面的标题背景色相同,然后一些按钮也需要两个颜色值;综合起来就需要7个色值,在color.xml文件中定义好它们,然后再drawable目录定义好选择器。
(以下是Demo中的代码片段,真实项目开发中只需要按照这个步骤模板做就行)
<?xml version="1.0" encoding="utf-8"?>
<resources>
<!-- 皮肤1 主色调 天蓝#4AC2E3-->
<!-- 界面背景 -->
<color name="pf1_activity_bg_color1">#46BAE3</color>
<color name="pf1_activity_bg_color2">#63f3e3</color>
<!-- item选择器 -->
<color name="pf1_main_item_bg1">#50CEE3</color>
<color name="pf1_main_item_bg2">#4AC2E3</color>
<!-- 字体颜色黑色 -->
<color name="pf1_text_color">#000000</color>
<!-- 皮肤2 主色调 草绿#53CAC3-->
<!-- 界面背景 -->
<color name="pf2_activity_bg_color1">#53CAC3</color>
<color name="pf2_activity_bg_color2">#73FFB9</color>
<!-- item选择器 -->
<color name="pf2_main_item_bg1">#62E3BE</color>
<color name="pf2_main_item_bg2">#5BD7C0</color>
<!-- 字体颜色白色 -->
<color name="pf2_text_color">#ffffff</color>
</resources>
- 编写SkinUtil资源加载类
public class SkinUtil {
private SharedPreferences sp;
//KEY
private final String KEY_PF = "skin"; //记录当前皮肤
//VALUE
public static final int VALUE_SKIN_1 = 1; //天蓝
public static final int VALUE_SKIN_2 = 2; //草绿
//当前皮肤资源ID
public int activity_bg;
public int item_bg;
public int textColor;
public SkinUtil(Context context){
sp = context.getSharedPreferences("mySkin", Context.MODE_PRIVATE);
loadPf();
}
/**
* 设置使用那一套皮肤
* @param witch
*/
public void setSkin(int witch){
sp.edit().putInt(KEY_PF, witch).commit();
loadPf();
}
/**
* 加载皮肤资源
*/
public void loadPf(){
//默认第一套皮肤(如果没有设置过)
int pf_num = sp.getInt(KEY_PF, VALUE_SKIN_1);
switch (pf_num) {
case VALUE_SKIN_1:
setSkin1();
break;
case VALUE_SKIN_2:
setSkin2();
break;
}
}
//加载第一套皮肤资源ID
private void setSkin1() {
activity_bg = R.drawable.skin1_activity_bg;
item_bg = R.drawable.skin1_main_item_bg;
textColor = R.color.pf1_text_color;
}
//加载第二套皮肤资源ID
private void setSkin2() {
activity_bg = R.drawable.skin2_activity_bg;
item_bg = R.drawable.skin2_main_item_bg;
textColor = R.color.pf2_text_color;
}
}
- 使用皮肤
在Application中初始化皮肤工具类
public class MyApplication extends Application {
public static SkinUtil skin;
@Override
public void onCreate() {
super.onCreate();
skin = new SkinUtil(getApplicationContext());
}
}
定义BaseActivity
public abstract class BaseActivity extends Activity implements OnClickListener {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
initView();
setSkin();
}
protected abstract void initView();
protected abstract void setSkin();
}
实现setSkin()方法设置皮肤
public class MainActivity extends BaseActivity{
private LinearLayout ll_bg;
private TextView tv_skin1, tv_skin2;
@Override
protected void initView() {
setContentView(R.layout.activity_main);
ll_bg = (LinearLayout) findViewById(R.id.ll_bg);
...
}
protected void setSkin() {
ll_bg.setBackgroundResource(MyApplication.skin.activity_bg);
...
}
@Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.tv_skin1:
//使用第一套皮肤
MyApplication.skin.setSkin(SkinUtil.VALUE_SKIN_1);
setSkin();
break;
case R.id.tv_skin2:
//使用第二套皮肤
MyApplication.skin.setSkin(SkinUtil.VALUE_SKIN_2);
setSkin();
break;
...
}
}
}
源码下载
Android动态换肤(一、应用内置多套皮肤)的更多相关文章
- Android动态换肤(二、apk免安装插件方式)
在上一篇文章Android动态换肤(一.应用内置多套皮肤)中,我们了解到,动态换肤无非就是调用view的setBackgroundResource(R.drawable.id)等方法设置控件的背景或者 ...
- Android动态换肤(三、安装主题apk方式)
相比之前免安装的方式,这种方法需要用户下载并安装皮肤apk,程序写起来比免安装的要简单很多,像很多系统主题就是通过这种方式实现的. 这种方式的思路是,从所有已安装的应用程序中遍历出皮肤程序(根据特定包 ...
- Android应用换肤总结
换肤,我们都很熟悉,像XP的主题,塞班的主题.看过国外的一些技术博客,就会发现国内和国外对软件的,或者说移动开发的软件的需求的不同.国外用户注重社交.邮件等功能,国内用户则重视音乐.小说.皮肤等功能, ...
- duilib入门之贴图描述、类html文本描述、动态换肤、Dll插件、资源打包
转载自duilib入门文档 贴图描述: Duilib的表现力丰富很大程度上得益于贴图描述的简单强大.Duilib的贴图描述分为简单模式和复杂模式两种. 简单模式使用文件名做为贴图描述内容,在这种方式下 ...
- Android主题换肤实现
本系列文章主要是对一个Material Design的APP的深度解析,主要包括以下内容 基于Material Design Support Library作为项目整体框架.对应博文:Android ...
- Android主题换肤 无缝切换
2016年7月6日 更新:主题换肤库子项目地址:ThemeSkinning,让app集成换肤更加容易.欢迎star以及使用,提供改进意见. 更新日志: v1.3.0:增加一键切换切换字体(初版)v1. ...
- hybird之web动态换肤实现
前言 最近在重构个hybird(原生的壳包着Web页面)的UI框架,进行到了做换肤功能的阶段,所以这里是我思考的解决的方法. 预想 目前实现换肤的功能无非就两种做法. 1.写几个皮肤文件,然后切换使用 ...
- CocoStudio基础教程(4)骨骼动画的动态换肤
1.概述 游戏中人物的状态会发生改变,而这种改变通常要通过局部的变化来表现出来.比如获得一件装备后人物形象的改变,或者战斗中武器.防具的损坏等.这些变化的实现就要通过动态换肤来实现. 2.运行到程序 ...
- Cocos2d-x 3.0 cocostudio骨骼动画的动态换肤
概述 游戏中人物的状态会发生改变,而这种改变通常要通过局部的变化来表现出来.比如获得一件装备后人物形象的改变,或者战斗中武器.防具的损坏等.这些变化的实现就要通过动态换肤来实现.在接下来的这个Demo ...
随机推荐
- bzoj4896 补退选
Description X是T大的一名老师,每年他都要教授许多学生基础的C++知识.在T大,每个学生在每学期的开学前都需要选课,每 次选课一共分为三个阶段:预选,正选,补退选:其中"补退选& ...
- [AHOI2016初中组]迷宫
题目描述 小雪和小可可被困在了一个无限大的迷宫中. 已经知道这个迷宫有 N 堵环状的墙,如果把整个迷宫看作是一个二维平面,那么每一堵墙都是平面上一个圆.任意两个圆不相交,不重合,也不会相切, 但有可能 ...
- 51 nod 1681 公共祖先 (主席树+dfs序)
1681 公共祖先 基准时间限制:1 秒 空间限制:131072 KB 分值: 80 难度:5级算法题 有一个庞大的家族,共n人.已知这n个人的祖辈关系正好形成树形结构(即父亲向儿子连边). 在另 ...
- hdu5587 BestCoder Round #64 (div.2)
问题描述 Vicky是个热爱数学的魔法师,拥有复制创造的能力. 一开始他拥有一个数列{1}.每过一天,他将他当天的数列复制一遍,放在数列尾,并在两个数列间用0隔开.Vicky想做些改变,于是他将当天新 ...
- 如何理解主函数main中变量(int argc,char *argv[])的含义
每一个C语言的初学者,都会注意到主函数main()里的两个参数,但是初学者一般不会去关注这两个参数的具体作用,下面我们就来介绍这两个参数的具体作用. main()函数是控制台程序的入口,int mai ...
- [ Java学习基础 ] Java的抽象类与接口
一.抽象类 1. 抽象类 Java语言提供了两种类:一种是具体类:另一种是抽象子类. 2. 抽象类概念: 在面向对象的概念中,所有的对象都是通过类来描绘的,但是反过来,并不是所有的类都是用来描绘对象的 ...
- URLconnection
URLconnection 开发中最常用的两种网络请求: 1.标准Java接口(java.NET) --HttpURLConnection,可以实现简单的基于URL请求.响应功能: 2.Apache ...
- jmeter录制APP时不能登录的问题
问题描述: 录制APP时,其他一切挺顺利的,但在登录的时候提示"服务器发生未知错误,请稍后重试".一开始以为是接口问题,用python脚本调用了下,是可以登录的,排除接口问题.百度 ...
- C++/C# 开发高级案例资料一次送!关注加群领取哦!
目前C/C++.C#.JAVA等语言开发的在线教育比较火爆,但小编所见的讲解高级案例的非常少,切合市场需求的较少.而且针对铁路.公路.建筑.市政.制造业等所有工业计算机辅助设计的开发技术和案例几乎没有 ...
- Spring消息之AMQP.
一.AMQP 概述 AMQP(Advanced Message Queuing Protocol),高级消息队列协议. 简单回忆一下JMS的消息模型,可能会有助于理解AMQP的消息模型.在JMS中,有 ...