¿Cómo creo ColorStateList programmatically?

Estoy intentando crear un ColorStateList programáticamente usando esto:

 ColorStateList stateList = new ColorStateList(states, colors); 

Pero no estoy seguro de cuáles son los dos parámetros.

Según la documentación:

 public ColorStateList (int[][] states, int[] colors) 

Agregado en el nivel de API 1

Crea una ColorStateList que devuelve la asignación especificada de estados a colores.

¿Alguien puede explicarme cómo crear esto?

¿Cuál es el significado de matriz bidimensional para los estados?

Consulte http://developer.android.com/reference/android/R.attr.html#state_above_anchor para obtener una lista de los estados disponibles.

Si desea establecer colores para estados deshabilitados, desenfocados, no verificados, etc., simplemente niegue los estados:

 int[][] states = new int[][] { new int[] { android.R.attr.state_enabled}, // enabled new int[] {-android.R.attr.state_enabled}, // disabled new int[] {-android.R.attr.state_checked}, // unchecked new int[] { android.R.attr.state_pressed} // pressed }; int[] colors = new int[] { Color.BLACK, Color.RED, Color.GREEN, Color.BLUE }; ColorStateList myList = new ColorStateList(states, colors); 

La primera dimensión es una matriz de conjuntos de estados, la segunda es el conjunto de estados. La matriz de colores enumera los colores para cada conjunto de estados coincidentes, por lo tanto, la longitud de la matriz de colores debe coincidir con la primera dimensión de la matriz de estados (o se bloqueará cuando se use el estado). Aquí y un ejemplo:

 ColorStateList myColorStateList = new ColorStateList( new int[][]{ new int[]{android.R.attr.state_pressed}, //1 new int[]{android.R.attr.state_focused}, //2 new int[]{android.R.attr.state_focused, android.R.attr.state_pressed} //3 }, new int[] { Color.RED, //1 Color.GREEN, //2 Color.BLUE //3 } ); 

espero que esto ayude.

Ejemplo EDIT: una lista de estados de color xml como:

      

se vería así

 ColorStateList myColorStateList = new ColorStateList( new int[][]{ new int[]{android.R.attr.state_pressed}, new int[]{} }, new int[] { context.getResources().getColor(R.color.white), context.getResources().getColor(R.color.black) } ); 

A veces esto será suficiente:

 int colorInt = getResources().getColor(R.color.ColorVerificaLunes); ColorStateList csl = ColorStateList.valueOf(colorInt); 

Lamentablemente, ninguna de las soluciones funciona para mí.

  1. Si no establece el estado presionado al principio, no lo detectará.
  2. Si lo configura, entonces necesita definir el estado vacío para agregar el color predeterminado
 ColorStateList themeColorStateList = new ColorStateList( new int[][]{ new int[]{android.R.attr.state_pressed}, new int[]{android.R.attr.state_enabled}, new int[]{android.R.attr.state_focused, android.R.attr.state_pressed}, new int[]{-android.R.attr.state_enabled}, new int[]{} // this should be empty to make default color as we want }, new int[]{ pressedFontColor, defaultFontColor, pressedFontColor, disabledFontColor, defaultFontColor } ); 

Este es el constructor del código fuente:

 /** * Creates a ColorStateList that returns the specified mapping from * states to colors. */ public ColorStateList(int[][] states, int[] colors) { mStateSpecs = states; mColors = colors; if (states.length > 0) { mDefaultColor = colors[0]; for (int i = 0; i < states.length; i++) { if (states[i].length == 0) { mDefaultColor = colors[i]; } } } } 

Mi clase de generador para crear ColorStateList

 private class ColorStateListBuilder { List colors = new ArrayList<>(); List states = new ArrayList<>(); public ColorStateListBuilder addState(int[] state, int color) { states.add(state); colors.add(color); return this; } public ColorStateList build() { return new ColorStateList(convertToTwoDimensionalIntArray(states), convertToIntArray(colors)); } private int[][] convertToTwoDimensionalIntArray(List integers) { int[][] result = new int[integers.size()][1]; Iterator iterator = integers.iterator(); for (int i = 0; iterator.hasNext(); i++) { result[i] = iterator.next(); } return result; } private int[] convertToIntArray(List integers) { int[] result = new int[integers.size()]; Iterator iterator = integers.iterator(); for (int i = 0; iterator.hasNext(); i++) { result[i] = iterator.next(); } return result; } } 

Ejemplo de uso

 ColorStateListBuilder builder = new ColorStateListBuilder(); builder.addState(new int[] { android.R.attr.state_pressed }, ContextCompat.getColor(this, colorRes)) .addState(new int[] { android.R.attr.state_selected }, Color.GREEN) .addState(..., some color); if(// some condition){ builder.addState(..., some color); } builder.addState(new int[] {}, colorNormal); // must add default state at last of all state ColorStateList stateList = builder.build(); // ColorStateList created here // textView.setTextColor(stateList); 

si usa el recurso, Colors.xml

 int[] colors = new int[] { getResources().getColor(R.color.ColorVerificaLunes), getResources().getColor(R.color.ColorVerificaMartes), getResources().getColor(R.color.ColorVerificaMiercoles), getResources().getColor(R.color.ColorVerificaJueves), getResources().getColor(R.color.ColorVerificaViernes) }; ColorStateList csl = new ColorStateList(new int[][]{new int[0]}, new int[]{colors[0]}); example.setBackgroundTintList(csl);