O getColor (int id) foi descontinuado no Android 6.0 Marshmallow (API 23)

719

O Resources.getColor(int id)método foi preterido.

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

O que devo fazer?

araks
fonte
26
Use ContextCompat.getColor (context, R.color.color_name)
Ashokchakravarthi Nagarajan
Com este método mencionado acima: getColor (context, R.color.your_color); Não está claro como obter o "contexto". Não funcionará apenas colocando o contexto no meu caso, o android studio 3.2. Acho que isso funciona para mim. .setTextColor (Color.RED).
Harry

Respostas:

1347

A partir da Biblioteca de suporte Android 23,
um novo método getColor () foi adicionado a ContextCompat.

Sua descrição do JavaDoc oficial:

Retorna uma cor associada a um ID de recurso específico

Começando em M, a cor retornada será estilizada para o tema do contexto especificado.


Então, basta ligar para :

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


Você pode verificar o ContextCompat.getColor() código fonte no GitHub .

araks
fonte
1
Parece a solução, mas o que devemos fazer quando recebermos um erro "Deve passar a cor resolvida em vez da identificação do recurso aqui"? Pelo que sei, é provável que o Lint não reconheça a nova API da Biblioteca de Suporte, portanto, talvez apenas adicionar uma anotação @SuppressWarnings ("ResourceAsColor") seja o caminho a seguir. Eu não gosto muito disso.
Stan
1
Oi @ Stan, você pode fornecer o trecho de código com a chamada de método que aciona o fiapo "ResourceAsColor"?
Araks
"int color = ContextCompat.getColor (isso, R.color.orange);" e depois "span = new ForegroundColorSpan (color);". A palavra sublinhada em vermelho é "cor", onde a passo como "new ForegroundColorSpan ()".
Stan
1
@MonicaLabbao oh ... desculpe, eu não entendi o seu comentário! :)
Araks
3
ContextCompatApi23 esse erro de marca supunha que você referencia ContextCompat
Webserveis
499

tl; dr:

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

Explicação:

Você precisará usar ContextCompat.getColor () , que faz parte da Biblioteca Support V4 (funcionará para todas as APIs anteriores).

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

Se você ainda não usa a Biblioteca de Suporte, precisará adicionar a seguinte linha à dependenciesmatriz dentro do seu aplicativo build.gradle(nota: é opcional se você já usa a biblioteca appcompat (V7) ):

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

Se você se preocupa com temas, a documentação especifica que:

Começando em M, a cor retornada será estilizada para o tema do contexto especificado

Melvin
fonte
4
Essa deve ser a resposta correta selecionada. Como no link fornecido do Android Docs, ele diz " Iniciando M, a cor retornada será estilizada para o tema do contexto especificado " .
Erros acontecem
1
compile 'com.android.support:appcompat-v7:23.0.1'
G O'Rilla 26/09/15
@G O'Rilla Como você pode ver na documentação, a ContextCompatclasse vem do SupportV4. O AppcompatV7 também funciona, pois depende do SupportV4. Como se costuma dizer na documentação da Biblioteca de Apoio , 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.. Portanto, faz sentido não AppcompatV7responder.
Melvin
1
Obrigado @Melvin, aqui está o meu exemplo, se for de uso: int colorTwitterBlue = ContextCompat.getColor (this, R.color.color_twitter_blue); composeTweetAlertDialog.getButton (AlertDialog.BUTTON_NEGATIVE) .setTextColor (colorTwitterBlue); composeTweetAlertDialog.getButton (AlertDialog.BUTTON_POSITIVE) .setTextColor (colorTwitterBlue);
Lara Ruffle Coles
1
@Melvin. O que exatamente significa que a 'cor será estilizada para o tema do contexto especificado'. Parece que se pode definir cores diferentes para a mesma identificação de cor, dependendo do tema. Como isso é feito exatamente?
RobertoCuba
47

Não quero incluir a biblioteca de suporte apenas para getColor , então estou 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);
    }
}

Eu acho que o código deve funcionar muito bem, e o obsoleto getColornão pode desaparecer da API <23.

E é isso que estou usando no 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
fonte
4
Observando o código fonte, é exatamente assim que a biblioteca de suporte faz isso. Como eu segmento a API> = 21, não quero incluir um jar completo para essas poucas linhas. Observe que você pode suprimir o aviso no Android Studio adicionando "// reprovação noinspection" acima da chamada preterida. E use um contexto de Atividade, não um contexto de Aplicativo, ou você poderá perder informações sobre o tema.
que você
2
Essa deve ser a resposta correta, embora a biblioteca de suporte possa ser uma opção mais preparada para o futuro, eu concordo que, se esse for o único motivo pelo qual você inclui a biblioteca de suporte, é melhor incluir essas duas linhas.
Anthonymonori
30

No Android Marshmallow, muitos métodos estão obsoletos.

Por exemplo, para obter cores, use

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

Também para obter uso extraível

ContextCompat.getDrawable(context, R.drawable.drawble_name);
Ashokchakravarthi Nagarajan
fonte
3
de onde vem o contexto variável? eu tenho que inicializar isso? Eu não posso fazê-lo funcionar. Para mim, parece que Androind tem um longo caminho a percorrer; me impressiona o quanto estou lutando para obter uma cor de um recurso xml !! Wow
ColdTuna
29

Para todos os usuários do Kotlin por aí:

context?.let {
    val color = ContextCompat.getColor(it, R.color.colorPrimary)
    // ...
}
Paul Spiesberger
fonte
Na verdade deveria ser val color = ContextCompat.getColor(context, R.color.colorPrimary). A variável "it" pode ser qualquer coisa, mas precisa ser um Contexto .
Scott Biggs
ité neste caso o context, desde que eu uso context?.let {para verificar se o contextnão é nulo. A função getColor()aceita apenas um contexto não nulo. Leia mais aqui sobre lete como usá-lo: kotlinlang.org/docs/reference/scope-functions.html#let
Paul Spiesberger
4

In Your RecyclerView em 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
fonte
1

Use o getColor(Resources, int, Theme)método da na ResourcesCompatBiblioteca de suporte do Android.

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

Eu acho que isso reflete melhor a sua pergunta do que a getColor(Context, int)da ContextCompatdesde que você pergunta Resources. Antes do nível 23 da API, o tema não seria aplicado e o método passaria para, getColor(int)mas você não receberá o aviso preterido. O tema também pode ser null.

Pedro
fonte
1
Se você passar nulo como argumento Tema, a cor retornada NÃO será estilizada para o tema atual. Portanto, pode estar incorreto.
Araks
1

Se você não precisa necessariamente dos recursos, use parseColor(String):
Color.parseColor("#cc0066")

N. Osil
fonte
1

Se o seu min atual. O nível da API é 23, você pode simplesmente usargetColor() como estamos usando para obter recursos de string getString():

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

Você pode restringir os níveis de API abaixo 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));
}

mas, para simplificar, faça o seguinte abaixo como resposta aceita:

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

De Recursos .

De ContextCompat AndroidX .

De Suporte ContextCompat

Blasanka
fonte
0

Também fiquei frustrado. Minha necessidade era muito direta. Tudo o que eu queria era a cor ARGB dos recursos, então escrevi um método estático simples.

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
fonte