国产精品电影_久久视频免费_欧美日韩国产激情_成年人视频免费在线播放_日本久久亚洲电影_久久都是精品_66av99_九色精品美女在线_蜜臀a∨国产成人精品_冲田杏梨av在线_欧美精品在线一区二区三区_麻豆mv在线看

Android著色器Tint研究

移動開發 Android
Tint 這個東西 主要用來減少apk體積的,比如說我現在有一個textview,他的背景圖 有兩種,一種是當獲得焦點時顯示的a圖,另一種是 失去焦點時顯示的b圖。如果要適配分辨率的話 很有可能圖片會更多,而且在切換的時候 因為是重新加載一次bitmap 效率也會下降很多。所以谷歌就給了一套解決方案 這個就是tint了。

Tint 這個東西 主要用來減少apk體積的,比如說我現在有一個textview,他的背景圖 有兩種,一種是當獲得焦點時顯示的a圖,另一種是 失去焦點時顯示的b圖。

相信大家開發的時候 這種需求做過很多次了,我們一般都會發現 這種a圖和b圖 除了顏色不一樣,其他都是一樣的,但是我們做的時候呢,通常是找ui要了兩張圖。

如果要適配分辨率的話 很有可能圖片會更多,而且在切換的時候 因為是重新加載一次bitmap 效率也會下降很多。所以谷歌就給了一套解決方案 這個就是tint了。

他的目的就是當你發現有這種需求的時候,只需要 放一張圖 在apk里即可,當你需要改變背景圖的顏色的時候 就用Tint即可!

下面就來簡單說一下,tint的使用 以及需要注意的地方。

首先 我們定義一個簡單的布局文件: 

 

 

 

我們發現這2個imageview 都是引用的同樣一個drawable資源,并且 在studio這個xml編輯界面里面 我們很明顯的 能看出來 這個圖片的顏色是黑色的 對吧!

那 現在 我們想改一下,想把iv1 這個imageview的 背景色 改成綠色的! 我們想當然的 當然會這么寫:

  1. iv1 = (ImageView) this.findViewById(R.id.iv1); 
  2.   iv2 = (ImageView) this.findViewById(R.id.iv2); 
  3.   final Drawable originBitmapDrawable = getResources().getDrawable(R.drawable.ic_account_circle_black_18dp); 
  4.   iv1.setImageDrawable(tintDrawable(originBitmapDrawable, ColorStateList.valueOf(Color.GREEN))); 

 應該很好理解對吧,代碼就不解釋了。但是我們運行以后發現: 

 

 

 

臥槽 怎么2個都變綠色了!

回顧一下 我們的代碼 我們應該能明白 2個imageview 都是引用的同樣的一個drawable,要知道 既然是一個drawable,那系統肯定為了優化資源 把這2個drawable 在內存里的拷貝弄成了一份!

還記得 我們以前講的bitmap優化那篇么?http://www.cnblogs.com/punkisnotdead/p/4881771.html 和這個里面的inBitmap 屬性有異曲同工之妙,如果還不理解 你看下面的圖就理解了: 

 

 

 

所以才會造成上面的情況。你修改了共同變量,所以2個圖就都被影響了。

解決方法 其實也很簡單:

  1. final Drawable originBitmapDrawable = getResources().getDrawable(R.drawable. 
  2. ic_account_circle_black_18dp).mutate();  

修改以后 我們再看: 

 

 

 

你看這么做就一切正常了。

那有人就要問了,臥槽 你這么做 不是把谷歌給我們做好的圖片內存優化方案給損壞了么,其實這種擔心是多余的,這個http://android-developers.blogspot.hk/2009/05/drawable-mutations.html

這個地址會告訴你 其實我們做 只是把單獨的受到影響的那部分 內存給單獨拿出來了,其他沒受到影響的還是共享的數據!換句話說 我們內存里 會另外存放的就是一些純的標志位 之類的 類似于狀態值這種東西。

大部分的內存還是公用的!

然后接著來,我們看下一個例子 關于editext的。 

 

 

 

你看這個edittext 的顏色是這樣的。那現在我們來修改一下 這個edittext的背景色

  1. et1 = (EditText) this.findViewById(R.id.et); 
  2.   final Drawable originBitmapDrawable = et1.getBackground(); 
  3.   et1.setBackgroundDrawable(tintDrawable(originBitmapDrawable, ColorStateList.valueOf(Color.GREEN))); 

  

 

 

 

背景色是修改成功了 但是這個光標的顏色 還沒變 非常不協調, 有人又要說了 我們可以用: 

 

 

 

這個xml 屬性來修改呀,當然了這個方法確實是可以的 但是你想 你這么做的話 又要增加資源文件了,不是與我們的tint 背道而馳了么?

所以 這個地方 我們就要想辦法 突破一下。其實很多人都能想到方法了,對于android 沒有 提供給我們的api 比如那些private 函數,

我們通常都是通過反射的方法 去調用的。 這里也是一樣,稍微想一下 我們就能明白, 這個地方 我們就先通過反射來獲取到這個cursorDrawable

然后給他著色,然后在反射調用方法 給他set進去不就行了么?

首先我們都知道 editext 實際上就是textview,所以我們看一下textview 的源碼 找找看 這個屬性到底叫啥名字。經過一番努力發現 在這:

  1. // Although these fields are specific to editable text, they are not added to Editor because 
  2.   // they are defined by the TextView's style and are theme-dependent. 
  3.   int mCursorDrawableRes;  

并且我們要看下editor的源碼 這是和edittext息息相關的:

  1. /** 
  2.      * EditText specific data, created on demand when one of the Editor fields is used. 
  3.      * See {<a href="http://www.jobbole.com/members/57845349">@link</a> #createEditorIfNeeded()}. 
  4.      */ 
  5.     private Editor mEditor; 
  6.  
  7.  
  8. //注意這段代碼屬于editor   
  9. final Drawable[] mCursorDrawable = new Drawable[2];  

有了這段代碼 我們就知道 剩下反射的代碼怎么寫了。 

  1. //參數就是要反射修改光標的edittext對象 
  2.     private void invokeEditTextCallCursorDrawable(EditText et) { 
  3.         try { 
  4.             Field fCursorDrawableRes = TextView.class.getDeclaredField("mCursorDrawableRes"); 
  5.             // 看源碼知道 這個變量不是public的 所以要設置下這個可訪問屬性 
  6.             fCursorDrawableRes.setAccessible(true); 
  7.             //取得 editext對象里的mCursorDrawableRes 屬性的值 看源碼知道這是一個int值 
  8.             int mCursorDrawableRes = fCursorDrawableRes.getInt(et); 
  9.             //下面的代碼 是通過獲取mEditor對象 然后再通過拿到的mEditor對象來獲取最終我們的mCursorDrawable這個光標的drawable 
  10.             Field fEditor = TextView.class.getDeclaredField("mEditor"); 
  11.             fEditor.setAccessible(true); 
  12.             Object editor = fEditor.get(et); 
  13.             Class<?> clazz = editor.getClass(); 
  14.             Field fCursorDrawable = clazz.getDeclaredField("mCursorDrawable"); 
  15.             fCursorDrawable.setAccessible(true); 
  16.             if (mCursorDrawableRes <= 0) { 
  17.                 return
  18.             } 
  19.             //到這里 我們終于拿到了默認主題下 edittext的光標的那個小圖標的drawable 
  20.             Drawable cursorDrawable = et.getContext().getResources().getDrawable(mCursorDrawableRes); 
  21.             if (cursorDrawable == null) { 
  22.                 return
  23.             } 
  24.             //既然都拿到了這個drawble 那就修改他。 
  25.             Drawable tintDrawable = tintDrawable(cursorDrawable, ColorStateList.valueOf(Color.GREEN)); 
  26.             //前面貼出的mCursorDrawable源碼 可以知道 這是一個二維數組。所以我們要構造出一個全新的二維數組 
  27.             Drawable[] drawables = new Drawable[]{tintDrawable, tintDrawable}; 
  28.             //然后再通過反射 把這個二維數組的值 放到editor里面 即可! 
  29.             fCursorDrawable.set(editor, drawables); 
  30.         } catch (NoSuchFieldException e) { 
  31.             e.printStackTrace(); 
  32.         } catch (IllegalAccessException e) { 
  33.             e.printStackTrace(); 
  34.         } 
  35.   
  36.     }  

***調用這個方法以后看一下效果:

 

很*** 對吧~~

***tintDrawable這個方法是用來向下兼容用的。你如果不考慮向下兼容的問題 用系統自帶的方法 就可以了,這里就不做過多介紹了。

  1. public static Drawable tintDrawable(Drawable drawable, ColorStateList colors) { 
  2.         final Drawable wrappedDrawable = DrawableCompat.wrap(drawable); 
  3.         DrawableCompat.setTintList(wrappedDrawable, colors); 
  4.         return wrappedDrawable; 
  5.     }  

當然你也可以用http://andraskindler.com/blog/2015/tinting_drawables/ 這個文章里的方法來做向下兼容:public final class TintedBitmapDrawable extends BitmapDrawable { 

  1.   private int tint; 
  2.   private int alpha; 
  3.   
  4.   public TintedBitmapDrawable(final Resources res, final Bitmap bitmap, final int tint) { 
  5.     super(res, bitmap); 
  6.     this.tint = tint; 
  7.     this.alpha = Color.alpha(tint); 
  8.   } 
  9.   
  10.   public TintedBitmapDrawable(final Resources res, final int resId, final int tint) { 
  11.     super(res, BitmapFactory.decodeResource(res, resId)); 
  12.     this.tint = tint; 
  13.     this.alpha = Color.alpha(tint); 
  14.   } 
  15.   
  16.   public void setTint(final int tint) { 
  17.     this.tint = tint; 
  18.     this.alpha = Color.alpha(tint); 
  19.   } 
  20.   
  21.   @Override public void draw(final Canvas canvas) { 
  22.     final Paint paint = getPaint(); 
  23.     if (paint.getColorFilter() == null) { 
  24.       paint.setColorFilter(new LightingColorFilter(tint, 0)); 
  25.       paint.setAlpha(alpha); 
  26.     } 
  27.     super.draw(canvas); 
  28.   } 
  29.  
責任編輯:龐桂玉 來源: 安卓開發精選
相關推薦

2021-12-23 09:34:05

著色器編程語言軟件開發

2013-01-30 15:37:19

CSS著色器HTML5

2021-03-18 08:03:58

SteamMesa緩存

2023-04-12 07:46:24

JavaScriptWebGL

2023-10-16 15:58:54

開源Blender

2017-05-08 11:41:37

WebGLThree.js

2015-08-07 10:24:17

AndroidMaterialDes

2013-04-15 14:23:21

2022-09-26 12:28:16

OpenGLAPI使用移動應用

2023-11-15 14:15:03

開源Blender

2015-07-08 16:38:19

Tint Color

2023-05-06 07:23:57

2025-01-08 10:17:11

2023-03-16 14:33:23

WebGL初始化繪制

2009-12-29 16:21:46

silverlight

2025-06-03 14:14:59

智能技術AI

2019-07-10 16:45:49

LinuxLinux游戲游戲性能

2024-02-26 00:00:00

前端工具Space.js

2023-09-04 06:52:28

AMD銳龍GPU

2012-05-22 01:20:14

SyntaxHighlJavaScriptJava
點贊
收藏

51CTO技術棧公眾號

欧美性视频网站| 欧美日韩在线精品| 日本网站在线免费观看视频| 成人午夜伦理影院| 日本一区免费看| 久久91精品| 91精品91久久久久久| 欧美日韩国产网站| 亚洲免费av片| 污网站在线免费看| 在线不卡中文字幕播放| 阿v免费在线观看| 天天影视色香欲综合网老头| 九色中文视频| 一区二区三区毛片| 国产69精品久久久久孕妇| 亚洲另类在线制服丝袜| avtt天堂资源网站| 亚洲精品免费视频| 一个人看的免费视频色| 亚洲曰韩产成在线| 在线观看导航| 在线观看欧美黄色| 制服丝袜在线播放| 亚洲欧美国产制服动漫| 色天使综合视频| 久久国产精品久久精品| 久久综合社区| 国产欧美日韩精品专区| 影音先锋久久精品| 相泽南亚洲一区二区在线播放 | 日韩欧美黄色影院| 日本动漫理论片在线观看网站| 欧美岛国在线观看| 亚洲天堂av在线| 日韩在线不卡视频| 日本欧美韩国国产| 亚洲在线免费视频| 国产欧美欧美| 91免费国产精品| 久久久久国产精品麻豆ai换脸 | 午夜精品久久久久久久男人的天堂| 亚洲国产一区二区三区网站| 人人做人人澡人人爽欧美| 我不卡伦不卡影院| 日韩和欧美的一区二区| 成人av免费网站| 国产字幕中文| 欧美日韩不卡在线| 久九九久频精品短视频| 欧美激情免费观看| 久久精品影视| 亚洲视频在线观看日本a| 99久久精品一区二区| 中文字幕毛片| 欧美成人性战久久| 日韩精品成人| 91超碰在线电影| 国产一区二区在线免费观看| 男裸体无遮挡网站| 欧美挠脚心视频网站| 在线不卡一区| 91日韩久久| 91香蕉视频在线| av中文在线| 欧美黄色片视频| 日韩 欧美 视频| 亚洲成a天堂v人片| 黑人巨大精品| 成人免费激情视频| 国产精品888| 日韩精品系列| www国产91| 一区免费在线| 农村妇女精品一二区| 欧美视频中文一区二区三区在线观看| 成人激情综合| 91免费看蜜桃| 欧美激情一区二区三区四区| 黄视频在线观看网站| 91精品国产一区| 久久黄色级2电影| 亚洲一区二区三区精品中文字幕 | 91国内在线视频| 1024日韩| 五月婷婷激情久久| 亚洲第一黄色网| 亚洲激情五月| 久久婷婷国产91天堂综合精品| 欧美三级韩国三级日本一级| 在线视频亚洲欧美中文| 天堂一区二区三区 | gogo高清免费视频| 亚洲夜晚福利在线观看| 在线观看国产精品入口| 天美星空大象mv在线观看视频| 日韩欧美久久一区| 亚洲成人三区| 国语对白在线视频| 色婷婷综合成人av| 免费久久99精品国产| 国产理论电影在线观看| 2025国产精品视频| 粉嫩av一区二区三区粉嫩| 成人午夜在线影视| 国产欧美一区二区三区四区| 国产精品三级av| a一区二区三区亚洲| 一区二区三区欧美在线| 7777精品伊人久久久大香线蕉完整版| 国产伦精品一区二区三区千人斩| 动漫av免费观看| 久久精品国产亚洲精品| 国产一区二区三区不卡在线观看 | 欧洲亚洲两性| 欧美极品色图| 一本久道久久综合中文字幕| 免费看成人人体视频| 国产精品-区区久久久狼| 伊人一区二区三区久久精品| 日本vs亚洲vs韩国一区三区二区| 高清av电影在线观看| 国产在线观看一区二区三区| 一区二区三区四区国产精品| 先锋影音国产精品| 国产免费专区| 国产精品视频成人| 精品久久久中文| 香港欧美日韩三级黄色一级电影网站| 成年人视频网站| 日本不卡高字幕在线2019| 国产色爱av资源综合区| 日本一区精品视频| 15—17女人毛片| 欧美亚洲第一页| 亚洲一区免费视频| 国产一区二区三区探花| 自拍偷拍电影| 91免费看网站| 欧美一级搡bbbb搡bbbb| 日韩av二区在线播放| av第一福利在线导航| 欧美日韩在线免费观看视频| 伊人青青综合网站| 久久精品视频免费| 国产a久久精品一区二区三区 | 国产精品久久久久婷婷二区次| 国产精品15p| 免费黄色网页| 99在线看视频| 欧美mv日韩mv国产网站| 国产福利一区二区三区视频| 亚洲男人在线| 2018av男人天堂| 91传媒在线免费观看| 欧美久久久一区| 激情av综合网| 日韩免费高清视频网站| 国产女主播在线观看| 91在线观看免费高清| 91精品婷婷国产综合久久 | 欧美极品日韩| 国产亚洲欧美视频| 国产精品视频观看| 亚洲综合五月| 日本一级理论片在线大全| 女人被男人躁得好爽免费视频| 久久久久久久久91| 日韩欧美在线视频日韩欧美在线视频| 久久午夜影视| 天堂精品久久久久| 玖玖综合伊人| 久久久久久久久久久综合| 欧美在线观看一区二区三区| 在线播放一区二区三区| 成人午夜av电影| 日韩电影在线视频| av影院在线免费观看| 99热在线免费| 奇米888一区二区三区| 欧美激情视频播放| 制服丝袜av成人在线看| 久久精品视频在线看| 中文精品久久| 欧美综合社区国产| 国产一级网站视频在线| jizzjizz国产精品喷水| 国产91视觉| 日韩中文第一页| 在线观看免费成人| 欧美国产日韩亚洲一区| 日日夜夜精品视频免费| 欧美日韩夜夜| 免费观看亚洲| 国产一级免费在线观看| 无码内射中文字幕岛国片| 欧美久久在线| 国产精品久久久久影院日本| 在线观看日韩专区| 欧美日韩一级黄|