getColor (int id) en desuso en Android 6.0 Marshmallow (API 23)

719

El Resources.getColor(int id)método ha quedado en desuso.

@ColorInt
@Deprecated
public int getColor(@ColorRes int id) throws NotFoundException {
    return getColor(id, null);
}

¿Qué tengo que hacer?

araks
fuente
26
Utilice ContextCompat.getColor (contexto, R.color.color_name)
Ashokchakravarthi Nagarajan
Con este método mencionado anteriormente: getColor (contexto, R.color.your_color); No está claro cómo obtener el "contexto". No funcionará simplemente poniendo contexto allí en mi caso, android studio 3.2. Me parece que esto funciona para mí. .setTextColor (Color.RED).
Harry

Respuestas:

1347

A partir de la Biblioteca de soporte de Android 23, se ha agregado
un nuevo método getColor ()ContextCompat .

Su descripción del JavaDoc oficial:

Devuelve un color asociado con un ID de recurso particular

Comenzando en M, el color devuelto tendrá un estilo para el tema del Contexto especificado.


Entonces, solo llame :

ContextCompat.getColor(context, R.color.your_color);


Puede consultar el ContextCompat.getColor() código fuente en GitHub .

araks
fuente
1
Esta parece ser la solución, pero ¿qué se supone que debemos hacer cuando recibimos un error "Debería pasar el color resuelto en lugar de la identificación del recurso aquí"? Por lo que puedo decir, probablemente sea porque Lint no reconoce la nueva API de la Biblioteca de soporte, por lo que tal vez solo agregue una anotación @SuppressWarnings ("ResourceAsColor") es el camino a seguir. Aunque no me gusta mucho.
Stan
1
Hola @Stan, ¿puede proporcionar el fragmento de código con la llamada al método que activa la pelusa "ResourceAsColor"?
araks
"int color = ContextCompat.getColor (esto, R.color.orange);" y luego "span = new ForegroundColorSpan (color);". La palabra que se subraya en rojo es "color", donde la paso a "new ForegroundColorSpan ()".
Stan
1
@MonicaLabbao oh ... lo siento, no entendí tu comentario! :)
araks
3
ContextCompatApi23 este error de marca supuso su referencia ContextCompat
Webserveis el
499

tl; dr:

ContextCompat.getColor(context, R.color.my_color)

Explicación:

Deberá usar ContextCompat.getColor () , que forma parte de la Biblioteca de Support V4 (funcionará para todas las API anteriores).

ContextCompat.getColor(context, R.color.my_color)

Si aún no usa la Biblioteca de soporte, deberá agregar la siguiente línea a la dependenciesmatriz dentro de su aplicación build.gradle(nota: es opcional si ya usa la biblioteca appcompat (V7) ):

compile 'com.android.support:support-v4:23.0.0' # or any version above

Si le interesan los temas, la documentación especifica que:

Comenzando en M, el color devuelto tendrá un estilo para el tema del contexto especificado

Melvin
fuente
44
Esta debería ser la respuesta seleccionada como correcta. Debido a que en el enlace dado de Android Docs, dice "Al comenzar M, el color devuelto tendrá el estilo del tema del Contexto especificado "
errores ocurren el
1
compilar 'com.android.support:appcompat-v7:23.0.1'
G O'Rilla
@G O'Rilla Como puede ver en la documentación, la ContextCompatclase proviene de SupportV4. AppcompatV7 también funciona, ya que se basa en SupportV4. Como dicen en la documentación de la biblioteca de apoyo , This library depends on the v4 Support Library. If you are using Ant or Eclipse, make sure you include the v4 Support Library as part of this library's classpath.. Por lo tanto, tiene sentido no poner AppcompatV7la respuesta.
Melvin
1
Gracias @Melvin, aquí está mi ejemplo de uso: int colorTwitterBlue = ContextCompat.getColor (esto, R.color.color_twitter_blue); composeTweetAlertDialog.getButton (AlertDialog.BUTTON_NEGATIVE) .setTextColor (colorTwitterBlue); composeTweetAlertDialog.getButton (AlertDialog.BUTTON_POSITIVE) .setTextColor (colorTwitterBlue);
Lara Ruffle Coles
1
@Melvin. ¿Qué significa exactamente el 'color será diseñado para el tema del contexto especificado'? Parece que uno puede definir diferentes colores para la misma identificación de color según el tema. ¿Cómo se hace esto exactamente?
RobertoCuba
47

No quiero incluir la biblioteca de soporte solo para getColor , así que estoy usando algo como

public static int getColorWrapper(Context context, int id) {
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
        return context.getColor(id);
    } else {
        //noinspection deprecation
        return context.getResources().getColor(id);
    }
}

Supongo que el código debería funcionar bien, y lo obsoleto getColorno puede desaparecer de la API <23.

Y esto es lo que estoy usando en Kotlin:

/**
 * Returns a color associated with a particular resource ID.
 *
 * Wrapper around the deprecated [Resources.getColor][android.content.res.Resources.getColor].
 */
@Suppress("DEPRECATION")
@ColorInt
fun getColorHelper(context: Context, @ColorRes id: Int) =
    if (Build.VERSION.SDK_INT >= 23) context.getColor(id) else context.resources.getColor(id);
Alex Vang
fuente
44
Mirando el código fuente, así es exactamente como lo hace la biblioteca de soporte. Apunto API> = 21, así que no quiero incluir un jar completo para estas pocas líneas. Tenga en cuenta que puede suprimir la advertencia en Android Studio agregando "// desaprobación sin inspección" sobre la llamada desaprobada. Y use un contexto de Actividad, no un contexto de Aplicación, o podría perder la información del tema.
personne3000
2
Esta debería ser la respuesta correcta, aunque la biblioteca de soporte puede ser una opción más a prueba de futuro, estoy de acuerdo en que si esta es la única razón por la que incluye la biblioteca de soporte, es mejor que incluya estas dos líneas.
anthonymonori
30

En Android Marshmallow, muchos métodos están en desuso.

Por ejemplo, para usar el color

ContextCompat.getColor(context, R.color.color_name);

También para obtener un uso dibujable

ContextCompat.getDrawable(context, R.drawable.drawble_name);
Ashokchakravarthi Nagarajan
fuente
3
¿De dónde viene el contexto variable? ¿tengo que inicializarlo? No puedo conseguir que funcione. A mí me parece que Androind tiene un largo camino por recorrer; ¡me sorprende lo mucho que estoy luchando para obtener un color de un recurso xml! Wow
ColdTuna
29

Para todos los usuarios de Kotlin:

context?.let {
    val color = ContextCompat.getColor(it, R.color.colorPrimary)
    // ...
}
Paul Spiesberger
fuente
En realidad debería ser val color = ContextCompat.getColor(context, R.color.colorPrimary). La variable "it" podría ser cualquier cosa, pero debe ser un Contexto .
Scott Biggs
ites en este caso el context, ya que uso context?.let {para verificar si el contextno es nulo. La función getColor()solo acepta un contexto no nulo. Lea más aquí sobre lety cómo usarlo: kotlinlang.org/docs/reference/scope-functions.html#let
Paul Spiesberger
4

En su recicladorVer en Kotlin

inner class ViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {
    fun bind(t: YourObject, listener: OnItemClickListener.YourObjectListener) = with(itemView) {
        textViewcolor.setTextColor(ContextCompat.getColor(itemView.context, R.color.colorPrimary))
        textViewcolor.text = t.name
    }
}
Irvin Joao
fuente
1

Utilice el getColor(Resources, int, Theme)método de la ResourcesCompatBiblioteca de soporte de Android.

int white = new ResourcesCompat().getColor(getResources(), R.color.white, null);

Creo que refleja mejor tu pregunta que la getColor(Context, int)de la ContextCompatque preguntas Resources. Antes del nivel 23 de API, el tema no se aplicará y el método llamará getColor(int)pero no tendrá la advertencia en desuso. El tema también puede ser null.

Pedro
fuente
1
Si pasa nulo como argumento de tema, el color devuelto NO tendrá el estilo del tema actual. Entonces podría ser incorrecto.
Araks
1

Si su actual min. El nivel de API es 23, simplemente puede usarlogetColor() como lo estamos usando para obtener recursos de cadena al getString():

//example
textView.setTextColor(getColor(R.color.green));
// if `Context` is not available, use with context.getColor()

Puede restringir los niveles de API por debajo de 23:

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
    textView.setTextColor(getColor(R.color.green));
} else {
    textView.setTextColor(getResources().getColor(R.color.green));
}

pero para que sea simple, puede hacer lo siguiente como respuesta aceptada:

textView.setTextColor(ContextCompat.getColor(context, R.color.green))

De los recursos .

Desde ContextCompat AndroidX .

De ContextCompat Support

Blasanka
fuente
0

Yo también me frustré. Mi necesidad era muy directa. Todo lo que quería era el color ARGB de los recursos, así que escribí un método estático simple.

protected static int getARGBColor(Context c, int resId)
        throws Resources.NotFoundException {

    TypedValue color = new TypedValue();
    try {
        c.getResources().getValue(resId, color, true);
    }
    catch (Resources.NotFoundException e) {
        throw(new Resources.NotFoundException(
                  String.format("Failed to find color for resourse id 0x%08x",
                                resId)));
    }
    if (color.type != TYPE_INT_COLOR_ARGB8) {
        throw(new Resources.NotFoundException(
                  String.format(
                      "Resourse id 0x%08x is of type 0x%02d. Expected TYPE_INT_COLOR_ARGB8",
                      resId, color.type))
        );
    }
    return color.data;
}
Steven Smith
fuente