爲了避免drawable 下面出現一大推的xml ,希望用代碼動態創建相應的selector 和 shape ;如果掌握了動態創建drawable,可以在自定義view的時候大有用處,尤其涉及到view的外觀變化方面。接下來,開幹。
可繪製對象 有顏色列表、形狀、狀態;這三種是我們最常用的,也還有其他的,不過不常用;下面爲示範代碼:
形狀可繪製對象 GradientDrawable
object GradientDrawableUtil {
fun gradientDrawableCreate(
context: Context,
cornerRadius : Float ?,
@ColorRes solidColor : Int ?, //R.color.colorPrimary
strokeWidth : Int ?,
@ColorRes strokeColor : Int ?,
dashWith : Float = 0F,
dashGap : Float = 0F
) : GradientDrawable{
val gradientDrawable = GradientDrawable()
gradientDrawable.cornerRadius = cornerRadius ?: 0F
// 設置顏色 即爲設置 填充色 solid;
if (solidColor != null){
gradientDrawable.setColor(context.resources.getColor(solidColor))
}
if (strokeWidth != null && strokeColor != null){
gradientDrawable.setStroke(strokeWidth, context.resources.getColor(strokeColor), dashWith , dashGap)
}
return gradientDrawable
}
fun gradientDrawableCreate(
context: Context,
cornerRadius : FloatArray, //這個數組長度爲8 ,每個角需要兩個數值;分別表示左上、右上,右下,左下
@ColorRes solidColor : Int,
strokeWidth : Int,
@ColorRes strokeColor : Int
) : GradientDrawable{
val gradientDrawable = GradientDrawable()
gradientDrawable.cornerRadii = cornerRadius
// 設置顏色 即爲設置 填充色 solid;
gradientDrawable.setColor(context.resources.getColor(solidColor))
gradientDrawable.setStroke(strokeWidth, context.resources.getColor(strokeColor))
return gradientDrawable
}
/**
* 虛線的顯示問題
* 1。 view高度大於虛線的width
* 2 在xml中添加 android:layerType=“software” 或者 代碼中設置 view.setLayerType(View.LAYER_TYPE_SOFTWARE,null);
*/
fun lineDrawableCreate(
context: Context,
strokeWidth : Int = 1,
@ColorRes strokeColor : Int ,
dashWith : Float = 4F,
dashGap : Float = 4F
) : GradientDrawable{
val gradientDrawable = GradientDrawable()
gradientDrawable.shape = GradientDrawable.LINE
gradientDrawable.setStroke(strokeWidth, context.resources.getColor(strokeColor), dashWith , dashGap)
return gradientDrawable
}
}
顏色和狀態
public class StateDrawableUtil {
/**
* 示範代碼
*
* 這裏 state[2] = new int[]{-android.R.attr.state_checked}; 添加負號 表示 false 的意思
* @param context
* @return
*/
public static StateListDrawable getStateListDrawable(Context context){
StateListDrawable stateListDrawable = new StateListDrawable();
int [][] state = new int[4][];
state[0] = new int[]{android.R.attr.state_checked};
state[1] = new int[]{android.R.attr.state_selected};
state[2] = new int[]{-android.R.attr.state_checked};
state[3] = new int[]{-android.R.attr.state_selected};
//
//stateListDrawable.addState(state[0], context.getResources().getDrawable(R.color.colorPrimary));
//stateListDrawable.addState(state[0], context.getResources().getDrawable( 其他的 drawable 文件, R.drawable.selector));
stateListDrawable.addState(state[0], context.getResources().getDrawable(R.drawable.deduct_checked));
stateListDrawable.addState(state[1], context.getResources().getDrawable(R.drawable.deduct_checked));
stateListDrawable.addState(state[2], context.getResources().getDrawable(R.drawable.deduct_uncheck));
stateListDrawable.addState(state[3], context.getResources().getDrawable(R.drawable.deduct_uncheck));
return stateListDrawable;
}
/**
* 獲取stateList 工具類
* @param state
* @param drawables
* @return
*/
public static StateListDrawable getStateListDrawable(int [][] state, Drawable[] drawables){
if (drawables == null || drawables.length == 0){
return null;
}
if (state == null || state.length == 0){
return null;
}
if (drawables.length != state.length){
return null;
}
StateListDrawable stateListDrawable = new StateListDrawable();
for (int i = 0; i < drawables.length; i++) {
stateListDrawable.addState(state[i], drawables[i]);
}
return stateListDrawable;
}
/**
* 示範代碼 獲取顏色
* 注意 顏色 要是這樣使用 context.getResources().getColor(R.color.colorAccent), 不能傳遞一個 R.color.colorAccent
* 這個方法可以加給 textView ,不過要添加點擊事件,否則沒有辦法觸發press 事件;或者用其他的按鈕控制focus 狀態
* 這樣沒有作用
* @param context
* @return
*/
public static ColorStateList getColorStates(Context context){
int [][] states = new int[4][];
states[0] = new int[]{android.R.attr.state_pressed};
states[1] = new int[]{android.R.attr.state_focused};
states[2] = new int[]{-android.R.attr.state_pressed};
states[3] = new int[]{-android.R.attr.state_focused};
int [] colors = new int[]{
context.getResources().getColor(R.color.colorAccent),
context.getResources().getColor(R.color.colorAccent),
context.getResources().getColor(R.color.colorPrimary),
context.getResources().getColor(R.color.colorPrimary)
};
ColorStateList colorStateList = new ColorStateList( states, colors);
//colorStateList.valueOf(R.color.colorAccent);
return colorStateList;
}
/**
* 抽象顏色工具類 但是沒有什麼用
* @param state
* @param colors
* @return
*/
public static ColorStateList getColorStates(int [][] state, int [] colors){
if (colors == null || colors.length == 0){
return null;
}
if (state == null || state.length == 0){
return null;
}
if (colors.length != state.length){
return null;
}
return new ColorStateList( state, colors);
}
}
註釋和用法都在裏面寫的比較詳細了,歡迎使用。
對於selector的狀態的使用,可以 參考 https://blog.csdn.net/sjh_389510506/article/details/105270753 ;如果想看 xml 中shape的 屬性,可以看 https://blog.csdn.net/sjh_389510506/article/details/85134904