在程式碼中實現android:tint效果

丿灬安之若死發表於2017-11-17
Android著色效果tint

Android有個tint的著色效果,這樣有些純色圖片,如果需要顯示別的顏色效果,直接加上就行,特別方便。這個網上一搜就有,效果如圖:

android:tint="@color/x"

我這個原本是個黑色的圖示,加上這句,就可以顯示各種顏色。 使用很簡單,直接在XML加上android:tint="@color/colorPrimary"就行;如果是背景,加上android:backgroundTint="@color/colorPrimary"就行,比單純設定方便多了。 比如Button如果設定android:background="@color/colorPrimary"為純顏色,那樣會沒有點選效果,需要點選效果還需要寫個selector效果的drawable。如果要在Android5.0之上顯示漣漪效果,還需要在drawable-v21中建立一個同名字的ripple效果的drawable XML寫法簡單,在程式碼中卻有點麻煩。 網上搜尋出來的方法有兩種: 第一種不去區分版本,使用V4包的android.support.v4.graphics.drawable.DrawableCompat

ImageView image = new ImageView(context);
Drawable up = ContextCompat.getDrawable(context,R.drawable.ic_sort_up);
Drawable drawableUp= DrawableCompat.wrap(up);
DrawableCompat.setTint(drawableUp, ContextCompat.getColor(context,R.color.theme));
image.setImageDrawable(drawableUp);

第二種只能在API21以上使用

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {    
    ImageView image = new ImageView(context);
    image.setImageResource(R.drawable.ic_sort_down);
    image.setImageTintList(ColorStateList.valueOf(ContextCompat.getColor(context,R.color.theme)));
}

第一種雖然好用,且向下相容,但有個問題,就是如果我在A介面使用,先開啟A介面,再去開啟有使用同一個圖片的B介面,會發現即使B介面的該ImageView沒使用Tint,也會有對應的著色效果。除非先進入的B介面,或者退出應用。

看有個DrawableCompat.unwrap(...)方法,試了一下,不管用,stackoverflow找到答案
http://stackoverflow.com/questions/30945490/drawablecompat-unwrap-is-not-working-pre-lollipop
試了一下,可以了,完整如下:

ImageView image = new ImageView(context);

Drawable up = ContextCompat.getDrawable(context,R.drawable.ic_sort_up);
Drawable drawableUp= DrawableCompat.wrap(up);
DrawableCompat.setTint(drawableUp, ContextCompat.getColor(context,R.color.theme));

image.setImageDrawable(drawableUp);

layoutParams.addRule(RelativeLayout.RIGHT_OF, text.getId());
addView(image, layoutParams);

Drawable up1 = ContextCompat.getDrawable(context,R.drawable.ic_sort_up);
Drawable drawableUp1= DrawableCompat.unwrap(up1);
DrawableCompat.setTintList(drawableUp1, null);

倒數第三行寫的那樣,需要重新弄個Drawable 出來,用的同一個會導致之前設定的著色無效;倒數第二行測試使用wrap();也沒出問題;最後一行一定用後面的那個Drawable ,用原來那個也會導致之前設定的著色無效。即使他們放在addView()之後。
當然,最後三行完整放在image.setImageDrawable(drawable);前面也是沒有問題的,這邊只是為了方便說明。
這些只是個人隨便寫的,又剛好有效,寫法不一定對。



相關文章