Reputation: 604
I need 3 icons: ContextCompat.getDrawable(this, R.drawable.my_vector_drawable)
.
First – without tint, second – with tint, third – without tint too,
Ok.
ImageView img1 = (ImageView) findViewById(R.id.img1);
ImageView img2 = (ImageView) findViewById(R.id.img2);
ImageView img3 = (ImageView) findViewById(R.id.img3);
Drawable drawable1 = ContextCompat.getDrawable(this, R.drawable.my_vector_drawable);
Drawable drawable2 = DrawableCompat.wrap(ContextCompat.getDrawable(this, R.drawable.my_vector_drawable));
DrawableCompat.setTintMode(drawable2, PorterDuff.Mode.MULTIPLY);
DrawableCompat.setTintList(drawable2, ContextCompat.getColorStateList(this, R.color.menu_tint_colors));
Drawable drawable3 = ContextCompat.getDrawable(this, R.drawable.my_vector_drawable);
img1.setImageDrawable(drawable1);
img2.setImageDrawable(drawable2);
img3.setImageDrawable(drawable3);
Where R.drawable.my_vector_drawable
is white figure.
But as result – 3 icons with tint (WHY?!).
For example, I tried to set ContextCompat.getColor(this, R.color.somecolor)
, and result is... Two icons with tint! Icon 2 and 3, and first icon – without tint (Why?!)
How to load NOT cached drawable? Or how to fix this issue? AppCompat 23.4.+
Upvotes: 2
Views: 834
Reputation: 4926
@azizbekian's answer is correct, but doing it for every drawable might be inefficient for some scenarios. Take a look at this answer for more details.
I would sugget using TintedIconCache
instead of mutating your drawables. It will manage a cache for your tinted drawables so that they are only created once when needed, and then cached in a memory efficient way for subsequent usage. It is a single class an you can grab from this gist.
// Get an instance
final TintedIconCache cache = TintedIconCache.getInstance();
// Will be fetched from the resources
Drawable backIcon = cache.fetchTintedIcon(context, R.drawable.icon, R.color.black));
// Will be fetched from the resources as well
Drawable bleuIcon = cache.fetchTintedIcon(context, R.drawable.icon, R.color.bleu));
// Will be fetched from the cache, with no mutation!!!
Drawable backIconTwo = cache.fetchTintedIcon(context, R.drawable.icon, R.color.back));
Upvotes: 0
Reputation: 62189
You have to mutate()
your drawables.
Now you refer to the exact same source. As soon as you mutate your drawable, each one will have its own state.
Drawable d = ContextCompat.getDrawable(this, R.drawable.my_vector_drawable).mutate();
From docs:
Make this drawable mutable. This operation cannot be reversed. A mutable drawable is guaranteed to not share its state with any other drawable. This is especially useful when you need to modify properties of drawables loaded from resources. By default, all drawables instances loaded from the same resource share a common state; if you modify the state of one instance, all the other instances will receive the same modification. Calling this method on a mutable Drawable will have no effect.
Upvotes: 3