标签:
ColorStateList value = new ColorStateList(states, colors);看到ColorStateList的构造方法,我们知道要想获得一个ColorStateList,需要有一个
int[][]
和一个存放ColorRes的
int[]
先看看一个很常用selector结构的color.xml
<?xml version="1.0" encoding="utf-8"?>
<selector
xmlns:android="http://schemas.android.com/apk/res/android">
<item android:color="#ffffff" android:state_enabled="true" android:state_pressed="true"/>
<item android:color="#000000"/>
</selector>要想解析这么一个xml文档,要用到xml解析库,我用的是jsoup,在AndroidStudio中的gradle添加compile 'org.jsoup:jsoup:1.8.2'就可以使用这个库了。
final File colorDir = new File(skinDirectory, "color");//指定SD卡目录下的color文件夹,这个目录由外部传入
if (colorDir.exists()) {
final File[] files = colorDir.listFiles(mXmlFilter);
for (File file : files) {
final Document parse = Jsoup.parse(file, "UTF-8");//将xml文件解析成Document对象
final Elements selectors = parse.getElementsByTag("selector");//拿到selector节点列表,实际上列表中只有一个selector
if (selectors.isEmpty()) {
continue;
}
final Element selector = selectors.get(0);
final Elements children = selector.children();
int[][] states = new int[children.size()][];
int[] colors = new int[children.size()];
for (int i = 0; i < children.size(); i++) {
Element child = children.get(i);
if ("item".equals(child.tagName())) {//拿到item节点
final Attributes attributes = child.attributes();//item节点的属性集
String value = attributes.get("android:color");
final int parseColor = Color.parseColor(value);
states[i] = getStatesArr(attributes);
colors[i] = parseColor;
}
}
ColorStateList value = new ColorStateList(states, colors);
这段代码里主要是将每个item的属性取出来,比如android:color 就是item的一个属性,取到color的值,通过Color.parseColor转换成ColorInt。
private int[] getStatesArr(Attributes attributes) {
List<Integer> stateList = new ArrayList<>();
String attributePress = attributes.get("android:state_pressed");
if (!TextUtils.isEmpty(attributePress)) {
boolean isPressed = Boolean.parseBoolean(attributePress);
stateList.add((isPressed ? 1 : -1) * android.R.attr.state_pressed);
}
String attributeFocus = attributes.get("android:state_focused");
if (!TextUtils.isEmpty(attributeFocus)) {
boolean isPressed = Boolean.parseBoolean(attributeFocus);
stateList.add((isPressed ? 1 : -1) * android.R.attr.state_focused);
}
String attributeSelect = attributes.get("android:state_selected");
if (!TextUtils.isEmpty(attributeSelect)) {
boolean isPressed = Boolean.parseBoolean(attributeSelect);
stateList.add((isPressed ? 1 : -1) * android.R.attr.state_selected);
}
String attributeActive = attributes.get("android:state_active");
if (!TextUtils.isEmpty(attributeActive)) {
boolean isPressed = Boolean.parseBoolean(attributeActive);
stateList.add((isPressed ? 1 : -1) * android.R.attr.state_active);
}
String attributeCheckable = attributes.get("android:state_checkable");
if (!TextUtils.isEmpty(attributeCheckable)) {
boolean isPressed = Boolean.parseBoolean(attributeCheckable);
stateList.add((isPressed ? 1 : -1) * android.R.attr.state_checkable);
}
String attributeChecked = attributes.get("android:state_checked");
if (!TextUtils.isEmpty(attributeChecked)) {
boolean isPressed = Boolean.parseBoolean(attributeChecked);
stateList.add((isPressed ? 1 : -1) * android.R.attr.state_checked);
}
String attributeEnable = attributes.get("android:state_enabled");
if (!TextUtils.isEmpty(attributeEnable)) {
boolean isPressed = Boolean.parseBoolean(attributeEnable);
stateList.add((isPressed ? 1 : -1) * android.R.attr.state_enabled);
}
String attributeWindowFocus = attributes.get("android:state_window_focused");
if (!TextUtils.isEmpty(attributeWindowFocus)) {
boolean isPressed = Boolean.parseBoolean(attributeWindowFocus);
stateList.add((isPressed ? 1 : -1) * android.R.attr.state_window_focused);
}
if(stateList.isEmpty()){
return new int[]{};
}else{
int[] stateArr =new int[stateList.size()];
for (int i=0;i<stateList.size();i++){
stateArr[i] =stateList.get(i);
}
return stateArr;
}
}这是取每个状态对应的int值,比如android:state_pressed为true,添加android.R.attr.state_pressed到数组中,如果为false添加 -android.R.attr.state_pressed,负的。
动态换肤之从SD卡中的xml中获取ColorStateList
标签:
原文地址:http://blog.csdn.net/u012902707/article/details/51363621