Cambia colore disegnabile a livello di codice


139

Sto cercando di cambiare il colore su un'immagine dell'indicatore bianco in base al codice. Ho letto che il codice seguente dovrebbe cambiare il colore, ma il mio marker rimane bianco.

Drawable.setColorFilter( 0xffff0000, Mode.MULTIPLY )

Ho dimenticato qualcosa? C'è un altro modo per cambiare i colori dei miei disegni che si trovano nella mia cartella res?


risposta accettata non ha funzionato per me..used questo Come rispondere [1], [1]: stackoverflow.com/questions/5940825/...
sham.y

Penso che tutte le risposte qui cambino il colore di sfondo, ma non il colore dell'immagine. Ho ragione? qualcuno può dirmi per favore? Ho provato tutte le soluzioni qui e anche sulle stesse domande su StackOverflow, ma in questo caso cambiano solo il colore di sfondo. Quindi penso che possiamo solo cambiare il colore di sfondo, ma non il colore delle immagini. Ho ragione io?
Shirish Herwade,

Risposte:


258

Prova questo:

Drawable unwrappedDrawable = AppCompatResources.getDrawable(context, R.drawable.my_drawable); 
Drawable wrappedDrawable = DrawableCompat.wrap(unwrappedDrawable);
DrawableCompat.setTint(wrappedDrawable, Color.RED);    

L'uso DrawableCompatè importante perché fornisce retrocompatibilità e correzioni di bug su dispositivi API 22 e precedenti.


Hmm, il colore rimane bianco. Potrebbe avere a che fare con la OverlayItemsclasse Hello MapView che potrebbe causare il problema? È un normale disegno dalla mia cartella res, niente di speciale ...
Johan

quindi qual era la soluzione?
speedynomads

@ ρяσѕρєяK sei davvero eccezionale.Molto utile
Android Android

30
Potresti preferire PorterDuff.Mode.SRC_IN se desideri che funzioni con una gamma più ampia di colori di origine.
Lorne Laliberte,

1
Il costruttore PorterDuffColorFilter utilizza il formato colore ARGB
RichX

124

Puoi provare questo per il disegno vettoriale svg

DrawableCompat.setTint(
    DrawableCompat.wrap(myImageView.getDrawable()),
    ContextCompat.getColor(context, R.color.another_nice_color)
);

4
Il modo migliore che ho visto per svg.
apSTRK,

1
preferisco questo rispetto alla risposta accettata, anche se entrambi funzioneranno, ma con questo non devo preoccuparmi di quale disegnabile impostare, ho appena quello già lì ed è anche compatibile con le versioni precedenti, fantastico!
RJFares,

1
La migliore risposta quando non ha funzionato nulla funziona come un fascino! Molte grazie! Nota: funziona anche quando si dispone di un disegno XML in imageView / AppCompatImageView
Sjd

1
Come rimuoverlo programmaticamente?
Hardik Joshi,

1
La documentazione di @HardikJoshi dice: Per cancellare la tinta, passare nullaDrawable#setTintList(ColorStateList)
arekolek,

23

Potrebbe essere necessario chiamare mutate () sul disegno oppure tutte le icone sono interessate.

Drawable icon = ContextCompat.getDrawable(getContext(), R.drawable.ic_my_icon).mutate();
TypedValue typedValue = new TypedValue();
getContext().getTheme().resolveAttribute(R.attr.colorIcon, typedValue, true);
icon.setColorFilter(typedValue.data, PorterDuff.Mode.SRC_ATOP);

21

Un altro modo per farlo su Lollipop, Android 5. + è impostare una tinta su un disegno bitmap come questo:

<?xml version="1.0" encoding="utf-8"?>
<bitmap
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:src="@drawable/ic_back"
    android:tint="@color/red_tint"/>

Questo funzionerà per te se hai un numero limitato di colori che vuoi usare sui tuoi disegni. Controlla il mio post sul blog per ulteriori informazioni .


2
Bello! A proposito, questo sembra funzionare anche su pre-Lollipop. (Ho appena provato questo con un minSdkVersion 16dispositivo Android 4.1.1.)
Jonik

Quando si crea una bitmap in questo modo, non si allunga per adattarsi al layout come quando si utilizza android:background="...". Abbastanza strano!
Prince,

Penso che sia perché non stai creando una patch nove qui.
MinceMan,

Spiacenti, questa pagina non esiste = (
Phan Van Linh,

@Jonik Le risposte alla domanda fornita sono irrilevanti. Questa domanda chiede come cambiare il colore di Drawable , non ImageView.
Antony.H

19

Puoi provare questo per ImageView. usando setColorFilter().

imageViewIcon.setColorFilter(ContextCompat.getColor(context, R.color.colorWhite));

10

Ho scritto una funzione generica in cui puoi passare il contesto, l'icona è id immagine disegnabile / icona immagine mipmap e nuovo colore che ti serve per quell'icona.

Questa funzione restituisce un disegno.

public static Drawable changeDrawableColor(Context context,int icon, int newColor) {
    Drawable mDrawable = ContextCompat.getDrawable(context, icon).mutate(); 
    mDrawable.setColorFilter(new PorterDuffColorFilter(newColor, PorterDuff.Mode.SRC_IN)); 
    return mDrawable;
} 

changeDrawableColor(getContext(),R.mipmap.ic_action_tune, Color.WHITE);

9

Puoi provare un ColorMatrixColorFilter, poiché il colore della tua chiave è bianco:

// Assuming "color" is your target color
float r = Color.red(color) / 255f;
float g = Color.green(color) / 255f;
float b = Color.blue(color) / 255f;

ColorMatrix cm = new ColorMatrix(new float[] {
        // Change red channel
        r, 0, 0, 0, 0,
        // Change green channel
        0, g, 0, 0, 0,
        // Change blue channel
        0, 0, b, 0, 0,
        // Keep alpha channel
        0, 0, 0, 1, 0,
});
ColorMatrixColorFilter cf = new ColorMatrixColorFilter(cm);
myDrawable.setColorFilter(cf);

7

Questo ha funzionato per me. Assicurati di inserire "ff" tra 0x e il codice colore. Come questo 0xff2196F3

Drawable mDrawable = ContextCompat.getDrawable(MainActivity.this,R.drawable.ic_vector_home);
                    mDrawable.setColorFilter(new
                            PorterDuffColorFilter(0xff2196F3,PorterDuff.Mode.SRC_IN));

Ciao @Bek, benvenuto su StackOverflow. Se questo ha funzionato per te, sarebbe molto utile includere un jsfiddle con una soluzione minima per dimostrarlo. Aiuterà la persona che ha pubblicato la domanda a capire correttamente.
Arjun Chaudhary,

6

Come la risposta accettata ma un metodo di praticità più semplice:

val myDrawable = ContextCompat.getDrawable(context, R.drawable.my_drawable)
myDrawable.setColorFilter(Color.GREEN, PorterDuff.Mode.SRC_IN)
setCompoundDrawablesWithIntrinsicBounds(myDrawable, null, null, null)

Nota, il codice qui è Kotlin.


3

Puoi provare Mode.LIGHTENo Mode.DARKEN. I Javadocs di Android sono orribili a spiegare cosa fanno le modalità PorterDuff. Puoi dare un'occhiata qui: PorterDuff | androide

Suggerisco di dare un'occhiata a Compositing sul sito di Mozilla qui. (Non hanno tutte le modalità di Android ma ce ne sono molte)


3

Usa questo: per java

view.getBackground().setColorFilter(Color.parseColor("#343434"), PorterDuff.Mode.SRC_OVER)

per Kotlin

view.background.setColorFilter(Color.parseColor("#343434"),PorterDuff.Mode.SRC_OVER)

puoi usare PorterDuff.Mode.SRC_ATOP, se lo sfondo ha angoli arrotondati ecc.


1

Sintassi

"your image name".setColorFilter("your context".getResources().getColor("color name"));

Esempio

myImage.setColorFilter(mContext.getResources().getColor(R.color.deep_blue_new));

0

Questo è quello che ho fatto:

public static Drawable changeDrawableColor(int drawableRes, int colorRes, Context context) {
    //Convert drawable res to bitmap
    final Bitmap bitmap = BitmapFactory.decodeResource(context.getResources(), drawableRes);
    final Bitmap resultBitmap = Bitmap.createBitmap(bitmap, 0, 0,
            bitmap.getWidth() - 1, bitmap.getHeight() - 1);
    final Paint p = new Paint();
    final Canvas canvas = new Canvas(resultBitmap);
    canvas.drawBitmap(resultBitmap, 0, 0, p);

    //Create new drawable based on bitmap
    final Drawable drawable = new BitmapDrawable(context.getResources(), resultBitmap);
    drawable.setColorFilter(new
            PorterDuffColorFilter(context.getResources().getColor(colorRes), PorterDuff.Mode.MULTIPLY));
    return drawable;
}

0

Basta usare

    android:drawableTint="@color/primary_color"

nel tuo file XML. Sostituisci primary_color con un colore personalizzato


0

Crea un metodo come questo:

//CHANGE ICON COLOR
private void changeIconColor(Context context ,int drawable){
    Drawable unwrappedDrawable = AppCompatResources.getDrawable(context, drawable);
    assert unwrappedDrawable != null;
    Drawable wrappedDrawable = DrawableCompat.wrap(unwrappedDrawable);
    DrawableCompat.setTint(wrappedDrawable, getResources().getColor(R.color.colorAccent));
}

e usalo così:

    changeIconColor(this,R.drawable.ic_home);

0

Il modo più semplice per farlo:

imageView.setColorFilter(Color.rgb(r, g b));

o

imageView.setColorFilter(Color.argb(a, r, g, b));

a, r, g, b: valori argb di colore.


Funzionerà solo se l'OP avrebbe usato imageViews invece di drawable.
SowingFiber

0

Per coloro che usano Kotlin una semplice funzione di estensione:

fun Drawable.tint(context: Context,  @ColorRes color: Int) {
    DrawableCompat.setTint(this, context.resources.getColor(color, context.theme))
}

e poi semplicemente

background.tint(context, R.color.colorPrimary)
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.