web-dev-qa-db-fra.com

La teinture DrawableCompat ne fonctionne pas sur la pré-sucette

J'utilise le nouveau TextInputLayout pour encapsuler un EditText. Lorsque je détermine qu'un champ contient une erreur, je fais ce qui suit:

Drawable drawable = DrawableCompat.wrap(getEditText().getBackground());

DrawableCompat.setTintList(drawable, ColorStateList.valueOf(Color.RED));

Cela fonctionne sur 5.0 et vire le soulignement en rouge, mais ne fait rien sur les appareils de test 4.4 ou 4.1. Qu'est-ce que j'oublie ici? Semble si simple et selon google "ça marche" ... je suis sûr que j'en ai aussi la dernière version:

compilez 'com.Android.support:design:22.2.0'

FWIW, si je fais setColorFilter au lieu de setTint, cela fonctionne sur toutes les plates-formes, mais j'ai des problèmes avec le fait qu'il disparaisse et ne revienne pas dès que le focus est défini/laissé/etc ... Je préférerais le faire avec teinte (et préfère vraiment que la teinte s'applique aux états focalisés et non focalisés si quelqu'un recherche un crédit supplémentaire lol)

Merci!

37
Jason T.

Lorsque vous appelez wrap(), le Drawable d'origine est enveloppé en interne dans un nouveau DrawableWrapper qui est utilisé pour implémenter la teinture sur les appareils plus anciens. Donc, pour que cela fonctionne, vous devez remettre le Drawable retourné au EditText:

final Drawable originalDrawable = editText.getBackground();
final Drawable wrappedDrawable = DrawableCompat.wrap(originalDrawable);
DrawableCompat.setTintList(wrappedDrawable, ColorStateList.valueOf(Color.RED));
editText.setBackground(wrappedDrawable);

Depuis la version 23.2.0 de la bibliothèque de support, vous pouvez également utiliser setTint() au lieu de setTintList() pour définir une seule couleur de teinte sans avoir à créer un ColorStateList.

DrawableCompat.setTint(wrappedDrawable, Color.RED);

Si vous souhaitez assurer une compatibilité descendante au-delà du niveau API 16, vous rencontrez un petit problème. setBackground() a été ajouté au niveau API 16 et vous devez appeler setBackgroundDrawable() sur les appareils avant cela. Il est préférable d'implémenter une méthode d'assistance qui le fait pour vous:

public static void setBackground(View view, Drawable background) {
    if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
        view.setBackground(background);
    } else {
        view.setBackgroundDrawable(background);
    }
}
66
Xaver Kapeller