Wie stelle ich den Farbton für eine Bildansicht programmgesteuert in Android ein?

396

Sie müssen den Farbton für eine Bildansicht festlegen ... Ich verwende ihn folgendermaßen:

imageView.setColorFilter(R.color.blue,android.graphics.PorterDuff.Mode.MULTIPLY);

Aber es ändert sich nicht ...

Alexander Farber
quelle
15
Möglicherweise haben Sie die Ganzzahl-Ressourcen-ID anstelle des Ganzzahl-Farbwerts verwendet. Versuchen Sie, R.color.blue in getResources () zu konvertieren. GetColor (R.color.blue)
milosmns
Drawable drawable = ...; drawable.setColorFilter (ContextCompat.getColor (Kontext, R.color.white), PorterDuff.Mode.DST); imageView.setImageDrawable (zeichnbar); // Hier kann jede Farbe verwendet werden
Flamme3

Antworten:

916

Sie können den Farbton ganz einfach im Code ändern über:

imageView.setColorFilter(Color.argb(255, 255, 255, 255)); // Weißer Farbton

Wenn Sie dann Farbtönung wünschen

imageView.setColorFilter(ContextCompat.getColor(context, R.color.COLOR_YOUR_COLOR), android.graphics.PorterDuff.Mode.MULTIPLY);

Für Vektor zeichnbar

imageView.setColorFilter(ContextCompat.getColor(context, R.color.COLOR_YOUR_COLOR), android.graphics.PorterDuff.Mode.SRC_IN);

UPDATE :
@ADev hat eine neuere Lösung in seiner Antwort hier , aber seine Lösung erfordert eine neuere Support-Bibliothek - 25.4.0 oder höher.

Hardik
quelle
12
In XML, Android: Tint = "@ Farbe / Blau"
Luis
1
Plus Android: Farbton ist 21+
androidguy
8
android:tintfunktioniert auf allen Android-Versionen. Vielleicht redest du drawableTint?
Finstas
11
PorterDuff.Mode.MULTIPLY funktioniert nicht in meiner Situation Ich habe PorterDuff.Mode.SRC_IN verwendet und es funktioniert
Mohamed Nageh
234

Die meisten Antworten beziehen sich auf die Verwendung, setColorFilterdie ursprünglich nicht gestellt wurde.

Der Benutzer @Tad hat seine Antwort in die richtige Richtung, aber es funktioniert nur mit API 21+.

Verwenden Sie Folgendes, um den Farbton für alle Android-Versionen festzulegen ImageViewCompat:

ImageViewCompat.setImageTintList(imageView, ColorStateList.valueOf(yourTint));

Beachten Sie, dass yourTintin diesem Fall eine "Farbe int" sein muss. Wenn Sie eine Farbressource wie haben R.color.blue, müssen Sie zuerst die Farbe int laden:

ContextCompat.getColor(context, R.color.blue);
ADev
quelle
6
Sollte die akzeptierte Antwort sein. Beachten Sie, dass es nur auf XML- ImageViewInstanzen mit AppCompat-Design oder auf AppCompatImageViewUnterklassen funktioniert .
Louis CAD
1
@ ADev schätzen Ihre Lösung, aber die Frage wurde 2013 gestellt und ImageViewCompat und AppCompatImageView Release mit v4-Unterstützung lib 25.4.0 im Juni 2017 bzw. 25.1.0 Dezember 2016 :)
Hardik
1
@ADev natürlich, aber Sie haben in Ihrer Antwort nicht richtig erwähnt, dass Ihre Lösung neu ist und eine neuere Support-Bibliothek 25.4.0 und höher erfordert, da diese Klasse mit einer niedrigeren Version der Support-Bibliothek nicht verfügbar ist, sodass niemand sie finden kann !! !!
Übrigens habe
Dies funktioniert nicht mit API 16.
Tayyab Mazhar
49

Das hat bei mir funktioniert

mImageView.setColorFilter(ContextCompat.getColor(getContext(), R.color.green_500));
toobsco42
quelle
Ja, hat auch für mich gearbeitet, ohne den zweiten Parameter. Es kann auch gehenmImageView.setColorFilter(getContext().getResources().getColor(R.color.green_500));
Biskrem Muhammad
upvoted und ohne den zweiten Parameter funktioniert es wie Charme. Thx @ toobsco42
Ravi Vaniya
35

@ Hardik hat es richtig. Der andere Fehler in Ihrem Code ist, wenn Sie auf Ihre XML-definierte Farbe verweisen. Sie haben nur die ID an die setColorFilterMethode übergeben, wenn Sie die ID zum Auffinden der Farbressource verwenden und die Ressource an die setColorFilterMethode übergeben sollten. Schreiben Sie Ihren Originalcode unten um.

Wenn diese Zeile in Ihrer Aktivität enthalten ist:

imageView.setColorFilter(getResources().getColor(R.color.blue), android.graphics.PorterDuff.Mode.MULTIPLY);

Andernfalls müssen Sie auf Ihre Hauptaktivität verweisen:

Activity main = ...
imageView.setColorFilter(main.getResources().getColor(R.color.blue), android.graphics.PorterDuff.Mode.MULTIPLY);

Beachten Sie, dass dies auch für andere Arten von Ressourcen gilt, z. B. Ganzzahlen, Bools, Dimensionen usw. Mit Ausnahme von Zeichenfolgen, die Sie direkt getString()in Ihrer Aktivität verwenden können, ohne dass Sie zuerst aufrufen müssen getResources()(fragen Sie mich nicht warum). .

Ansonsten sieht Ihr Code gut aus. (Obwohl ich die setColorFilterMethode nicht zu sehr untersucht habe ...)

CrepeGoat
quelle
22

Nachdem ich alle Methoden ausprobiert hatte und sie bei mir nicht funktionierten.

Ich erhalte die Lösung mit einem anderen PortDuff.MODE.

imgEstadoBillete.setColorFilter(context.getResources().getColor(R.color.green),PorterDuff.Mode.SRC_IN);
Catluc
quelle
14

Beginnend mit Lollipop gibt es auch eine Tint- Methode für BitmapDrawables, die mit der neuen Palette-Klasse funktioniert:

public void setTintList (ColorStateList-Farbton)

und

public void setTintMode (PorterDuff.Mode tintMode)

In älteren Android-Versionen können Sie jetzt die DrawableCompat- Bibliothek verwenden

Bisschen
quelle
2
Tatsächlich unterstützt die Support-Bibliothek dies. siehe meine Antwort: stackoverflow.com/a/34479043/878126
Android-Entwickler
12

Versuche dies. Es sollte auf allen Android-Versionen funktionieren, die von der Support-Bibliothek unterstützt werden:

public static Drawable getTintedDrawableOfColorResId(@NonNull Context context, @NonNull Bitmap inputBitmap, @ColorRes int colorResId) {
    return getTintedDrawable(context, new BitmapDrawable(context.getResources(), inputBitmap), ContextCompat.getColor(context, colorResId));
}

public static Drawable getTintedDrawable(@NonNull Context context, @NonNull Bitmap inputBitmap, @ColorInt int color) {
    return getTintedDrawable(context, new BitmapDrawable(context.getResources(), inputBitmap), color);
}

public static Drawable getTintedDrawable(@NonNull Context context, @NonNull Drawable inputDrawable, @ColorInt int color) {
    Drawable wrapDrawable = DrawableCompat.wrap(inputDrawable);
    DrawableCompat.setTint(wrapDrawable, color);
    DrawableCompat.setTintMode(wrapDrawable, PorterDuff.Mode.SRC_IN);
    return wrapDrawable;
}

Sie können eine der oben genannten Methoden verwenden, damit es funktioniert.

Weitere interessante Funktionen von DrawableCompat finden Sie in den Dokumenten hier .

Android-Entwickler
quelle
1
Ich musste auch tun imageView.getBackground(), um das Drawable zu bekommen, weil imageView.getDrawable()es null zurückgab.
Rock Lee
@ RockLee stellen Sie sicher, dass Sie src in der Bildansicht xml oder setImageResource im Code verwendet haben
orelzion
Dies ist der perfekte Weg, um Farbton für Bildansicht Hintergrund
einzustellen
12

Bessere vereinfachte Erweiterungsfunktion dank ADev

fun ImageView.setTint(@ColorRes colorRes: Int) {
    ImageViewCompat.setImageTintList(this, ColorStateList.valueOf(ContextCompat.getColor(context, colorRes)))
}

Verwendungszweck:-

imageView.setTint(R.color.tintColor)
Manohar Reddy
quelle
Gibt es eine ähnliche für die Textfarbe von Button / TextView?
Android-Entwickler
Meinst du Textansicht Textfarbe oder Farbton für Textansicht zeichnbar?
Manohar Reddy
Ich meine "Textfarbe". Die Farbe des Textes. Aber ich denke, es ist ziemlich problematisch, da Text für jeden Zustand eine Farbe hat ... Wie kommt es, dass es gut funktioniert, wenn ich die Akzentfarbe einstelle ... Seltsam ... Ist es vielleicht möglich, die Akzentfarbe auf einzustellen? eine bestimmte Schaltfläche (oder TextView) programmgesteuert?
Android-Entwickler
11

Wenn Ihre Farbe hexadezimale Transparenz aufweist, verwenden Sie den folgenden Code.

ImageViewCompat.setImageTintMode(imageView, PorterDuff.Mode.SRC_ATOP);
ImageViewCompat.setImageTintList(imageView, ColorStateList.valueOf(Color.parseColor("#80000000")));

Um den Farbton zu löschen

ImageViewCompat.setImageTintList(imageView, null);
Sai
quelle
Was ist der Typ von "img"
Beyaz
1
@Beyaz imgist vom Typ ImageView.
Sai
10

Einfach und einzeilig

imageView.setColorFilter(activity.getResources().getColor(R.color.your_color));
Gautam Surani
quelle
9

Da die erste Antwort bei mir nicht funktioniert hat:

//get ImageView
ImageView myImageView = (ImageView) findViewById(R.id.iv);

//colorid is the id of a color defined in values/colors.xml
myImageView.setImageTintList(ColorStateList.valueOf(ContextCompat.getColor(getApplicationContext(), R.color.colorid)));

Dies scheint nur in API 21+ zu funktionieren, aber für mich war das kein Problem. Sie können ein ImageViewCompat verwenden, um dieses Problem zu beheben.

Ich hoffe ich habe jemandem geholfen :-)

Felix
quelle
7

Ab Lollipop gibt es eine Methode ImageView#setImageTintList(), die Sie verwenden können. Der Vorteil besteht darin, dass nicht ColorStateListnur eine einzige Farbe, sondern der Farbton des Bildes berücksichtigt wird .

Auf Pre-Lollipop-Geräten können Sie dasselbe Verhalten erzielen, indem Sie das Zeichenelement tönen und dann als ImageViewBildzeichnungsobjekt festlegen:

ColorStateList csl = AppCompatResources.getColorStateList(context, R.color.my_clr_selector);
Drawable drawable = DrawableCompat.wrap(imageView.getDrawable());
DrawableCompat.setTintList(drawable, csl);
imageView.setImageDrawable(drawable);
Alex Lockwood
quelle
6
Random random=new Random;
ImageView imageView = (ImageView) view.findViewById(R.id.imageView);
ColorFilter cf = new PorterDuffColorFilter(Color.rgb(random.nextInt(255), random.nextInt(255), random.nextInt(255)),Mode.OVERLAY);

imageView.setImageResource(R.drawable.ic_bg_box);
imageView.setColorFilter(cf);
Pawan Asati
quelle
6

Zum Festlegen des Farbtons für eine Bildansicht programmgesteuert in Android

Ich habe zwei Methoden für Android:

1)

imgView.setColorFilter(context.getResources().getColor(R.color.blue));

2)

 DrawableCompat.setTint(imgView.getDrawable(),
                     ContextCompat.getColor(context, R.color.blue));

Ich hoffe ich habe jemandem geholfen :-)

Abhign01
quelle
4

Zusätzlich zu ADEV ‚s Antwort (was meiner Meinung nach ist die korrekteste), da die weit verbreiteten Annahme von Kotlin und seinen nützlichen Erweiterungsfunktionen:

fun ImageView.setTint(context: Context, @ColorRes colorId: Int) {
    val color = ContextCompat.getColor(context, colorId)
    val colorStateList = ColorStateList.valueOf(color)
    ImageViewCompat.setImageTintList(this, colorStateList)
}

Ich denke, dies ist eine Funktion, die in jedem Android-Projekt nützlich sein könnte!

Cillian Myles
quelle
4

Ich habe festgestellt, dass wir den Farbwähler für den Farbton verwenden können:

mImageView.setEnabled(true);

activity_main.xml:

<ImageView
    android:id="@+id/image_view"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:src="@drawable/ic_arrowup"
    android:tint="@color/section_arrowup_color" />

section_arrowup_color.xml:

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:color="@android:color/white" android:state_enabled="true"/>
    <item android:color="@android:color/black" android:state_enabled="false"/>
    <item android:color="@android:color/white"/>
</selector>
NickUnuchek
quelle
Hallo, es funktioniert nicht für Vektor-Drawables. Gibt es eine Problemumgehung für dasselbe?
Manukumar
@Manukumar Verwenden Sie app:srcCompatanstelle von android:srcund fügen Sie vectorDrawables.useSupportLibrary = trueden defaultConfigTeil Ihrer build.gradle-Datei hinzu. Getestet, um auf Kitkat Emulator gut zu funktionieren.
Android-Entwickler
3

Nicht verwenden PoterDuff.Mode, Verwenden Sie setColorFilter()es funktioniert für alle.

ImageView imageView = (ImageView) listItem.findViewById(R.id.imageView);
imageView.setColorFilter(getContext().getResources().getColor(R.color.msg_read));
Vikash Sharma
quelle
2

Wie @milosmns sagte, sollten Sie verwenden imageView.setColorFilter(getResouces().getColor(R.color.blue),android.graphics.PorterDuff.Mode.MULTIPLY);

Diese API benötigt einen Farbwert anstelle einer Farbressourcen-ID. Dies ist die Hauptursache dafür, dass Ihre Anweisung nicht funktioniert hat.

HunkD
quelle
2

Ich bin spät in der Party, aber ich habe meine Lösung oben nicht gesehen. Wir können auch die Tönungsfarbe über setImageResource()einstellen (meine minSdkVersion ist 24).

Zuerst müssen Sie einen Selektor erstellen und im /drawableAsset-Ordner speichern (ich nenne ihn ic_color_white_green_search.xml).

<!-- Focused and not pressed -->
<item android:state_focused="true"
      android:state_pressed="false">

    <bitmap android:src="@drawable/ic_search"
            android:tint="@color/branding_green"/>
</item>

<!-- Focused and pressed -->
<item android:state_focused="true"
      android:state_pressed="true">

    <bitmap android:src="@drawable/ic_search"
            android:tint="@color/branding_green"/>
</item>

<!-- Default -->
<item android:drawable="@drawable/ic_search"/>

Dann setzen Sie es in Code wie folgt:

val icon = itemView.findViewById(R.id.icon) as ImageButton
icon.setImageResource(R.drawable.ic_color_white_green_search)
Hesam
quelle
2

Falls Sie den Selektor auf Ihren Farbton einstellen möchten:

ImageViewCompat.setImageTintList(iv, getResources().getColorStateList(R.color.app_icon_click_color));
Yusril Maulidan Raji
quelle
0

Kotlin-Lösung mit Erweiterungsfunktion zum Ein- und Ausschalten der Tönung:

fun ImageView.setTint(@ColorInt color: Int?) {
    if (color == null) {
        ImageViewCompat.setImageTintList(this, null)
        return
    }
    ImageViewCompat.setImageTintMode(this, PorterDuff.Mode.SRC_ATOP)
    ImageViewCompat.setImageTintList(this, ColorStateList.valueOf(color))
}
Android-Entwickler
quelle
-4

Keine genaue Antwort, aber eine einfachere Alternative:

  • Platzieren Sie eine weitere Ansicht über dem Bild
  • Ändern Sie den Alpha- Wert der Ansicht nach Ihren Wünschen (programmgesteuert), um den gewünschten Effekt zu erzielen.

Hier ist ein Ausschnitt dafür:

<FrameLayout
    android:layout_width="match_parent"
    android:layout_height="wrap_content">

    <ImageView
        android:layout_width="match_parent"
        android:layout_height="@dimen/height120"
        android:contentDescription="@string/my_description"
        android:scaleType="fitXY"
        android:src="@drawable/my_awesome_image"/>

    <View
        android:layout_width="match_parent"
        android:layout_height="@dimen/height120"
        android:alpha="0.5"
        android:background="@color/my_blue_color"/>
</FrameLayout>
Shubham Chaudhary
quelle
Hier geht es um Farbton! nicht Alpha, das für Transparenz ist.
David
Aber das wirkt letztendlich als Farbton. Sie sollten es selbst versuchen. Dies ist nur eine Möglichkeit, Dinge zu betrachten.
Shubham Chaudhary
@ShubhamChaudhary Ich weiß, das ist spät, aber was ist, wenn das Bild ist png. Wird sich dann der Hintergrund nicht ändern? Auch Alpha und Farbton sind sehr unterschiedlich. Farbton Ist wie Farbersatz, wenn ich mich nicht irre. Keine Straftat beabsichtigt.
Ich
Gutes Argument. Diese Antwort hat in meinem Fall geholfen. Hoffnung passt auch zu den Schuhen eines anderen.
Shubham Chaudhary