Bitmap使用分享

2021-07-02 17:43:13 字數 4058 閱讀 7744

這篇文章裡面只是想總結一下工作中使用bitmap遇到的一些使用情況。

bitmap翻譯過來就是"位圖",對於bitmap更多的優化問題吧!

bitmap類有乙個方法recycle(),從方法名可以看出是**的意思。雖然有gc,但是有時候**還是不盡如人意,這時候我們就需要用到recycle()我們手動來釋放bitmap的記憶體。

public void recycle() 

mrecycled = true;

}}

boolean mrecycled:是否被**

使用了jni方法**bitmap,nativerecycle(mnativebitmap)的返回值表示原生畫素物件是否實際**。false表示它在native仍然在使用和這些物件現在不應該收集。當位圖本身被收集它們將被收集後。

一般來說,如果能夠獲得bitmap物件的引用,就需要及時的呼叫bitmap的recycle()方法來釋放bitmap占用的記憶體空間,而不要等android系統來進行釋放。

下面是釋放bitmap的示例**片段。

// 先判斷是否已經**

if(bitmap != null && !bitmap.isrecycled())

在bitmap不再需要的時候就可以進行**了

bitmap類的構造方法都是私有的,所以開發者不能直接new出乙個bitmap物件

一種是方式是使用bitmapfactory

先說用io流建立吧

inputstream is = res.openrawresource(r.drawable.welcome);  // 讀取資源檔案獲取輸入流 

//當然上面的io流也可以是網路獲取的,而bitmapfactory.options options的使用

bitmap bitmap = bitmapfactory.decodestream(is);//建立bitmap

但是當我們遇到一些大圖的時候就是出現oom了,所以bitmapfactory提供了另乙個方法

decodestream(inputstream is, rect outpadding, options opts)
這個options是bitmapfactory的乙個內部類,修改options的一些屬性可以幫助我們優化載入bitmap是的記憶體,示例**如下:

//例項化bitmapfactory.options

bitmapfactory.options options = new bitmapfactory.options();

options .inpreferredconfig = bitmap.config.rgb_565;

options .inpurgeable = true;

options .ininputshareable = true;

//建立bitmap

bitmap bitmap = bitmapfactory.decodestream(is, null, options);

其中inpreferredconfig是這是bitmap的每乙個畫素所佔的位的配置,而bitmap.config的配置有四種:

另外兩個屬性需要共同設定,inpurgeable和ininputshareable屬性我檢視過api但是沒有看的太明白,如果有明白的大神還請告訴一下。

還有一種是使用bitmap的createbitmap(),這個方法有一系列的方法都能夠建立bitmap,可能有人會很奇怪的問到為什麼會用到這個一系列的方法,那是在開發的時候遇到問題了,我需要根據scrollview的滑動去改變乙個圓角背景圖的顏色。可能大家都會去寫乙個drawable檔案來搞定圓角,但是顏色沒辦法動態改變啊!於是就想到自己去建立乙個bitmap,然後自己把它在切圓。找了一會找到這個方法bitmap.createbitmap

(int width, int height, 

bitmap.config

config),可以生成乙個指定寬高的bitmap,後面的bitmap.config就是之前提到的位影象素位配置。

但是這樣得到的bitmap是乙個有寬高,沒有仍和顯示,因為還沒有個bitmap上的每乙個畫素設定顏色,那挨個畫素去設定這個想法應該不會有人去實現吧!於是就用用到的canvas(畫布)。

bitmap bitmap = bitmap.createbitmap(width,height,config.argb_4444);

canvas canvas =  new canvas(bitmap);//構造乙個畫布來繪製bitmap

canvas.drawargb(255, 255, 255, 255);//設定繪製的顏色

canvas.drawbitmap(newb, 0, 0, null); //顯示在bitmap上

這樣bitmap就有顏色了,只差切圓角了;其實圓角可以在上面建立的那個過程就一併完成的,但是由於沒有自習學習沒有去合併**,這裡只是提供一中參考。

在上傳的時候使用過這個方法

bitmap的compress(compressformat format, int quality, outputstream stream)可以按指定的格式以及畫質,將轉換為輸出流。 

format:bitmap.compressformat.png或bitmap.compressformat.jpeg 

quality:畫質,0-100.0表示最低畫質壓縮,100以最高清壓縮。對於png等無損格式的,會忽略此項設定。 

如果畫素過大,比如瀏覽**。可能我們就需要生成縮圖來優化,以減少載入過程中的記憶體的使用,避免發生outofmemory異常。

使用bitmapfactory.options中insamplesize就可以縮小。該屬性表示縮圖大小為原始大小的幾分之一。例如設定insamplesize=2,則取出的縮圖的寬和高都是原的1/2,的大小就為原圖大小的1/4。

我們可以預設對所有都進行這中處理,但是有些圖沒有必要進行壓縮形成縮圖的意義不大,還影響使用者體驗了。

於是我們可以通過設定bitmapfactory.options的injustdecodebounds=true之後,再使用上文中提到過的bitmapfactory.decodestream(is, null, options)等方法之後,我們就能在options中獲取到的原始寬高了,即options.outwidth和options.outheight。對這兩個值進行判斷就可以知道是否過大了。值得注意的是injustdecodebounds=true的時候執行decodestream方法並不會真正的分配空間,這時候獲取到的bitmap為null,所以這裡不用擔心會oom。

示例**:

bitmapfactory.options options= new bitmapfactory.options();

options.injustdecodebounds = true;// 設定injustdecodebounds為true

bitmapfactory.decodestream(is, null, options);// 使用decodefile方法得到的寬和高

int width = options.outwidth;

int height = options.outheight;

在實際專案中可以利用上面的**,先獲取真實的寬度和高度,然後判斷是否需要縮小。

如果不需要縮小,設定insamplesize的值為1。

如果需要縮小,則動態計算並設定insamplesize的值,對進行縮小。

這裡有一點需要注意,在下次使用bitmapfactory的decodestream()等方法例項化bitmap物件前,必須要將options.injustdecodebound設定為false,否則建立的bitmap為null。

為什麼這裡我舉例的是類似與相簿的使用呢?因為通過聯網獲取的我們可以在程式中進行壓縮和優化,同時服務端也可以根據不同的手機解析度返回不同的大小的來優化。

這是我在開發過程中遇到的一些問題肯定不是很全面,在這裡分享一下,有錯誤還請大家指正!!

還有一點值得說的是,即使已經優化的很好的,但是我們還是一定要捕獲exception或error,避免程式crash。

bitmap與2 bitmap使用總結

bitmap是一種簡單的資料結構,但在儲存空間壓縮方面卻使用廣泛。bitmap就是用乙個bit位來標記某個元素是否存在 1表示存在,0表示不存在 而2 bitmap就是用兩個bit為來標記某個元素出現的次數 00出現0次,01出現1次,10出現2次及其以上,11無意義。2 bitmap在記憶體中的表...

如何有效使用bitmap

使用bitmap容易遭遇out of memory exception,主要由以下三個原因 bitmap比較耗費記憶體,例如1300w畫素,每個畫素可能佔4個位元組 有些view group例如list view,grid view中可能包含很多bitmap。綜上,使用bitmap時主要考慮節省記憶...

使用Bitmap實現排序

使用bitmap實現排序,是通過在bitmap將待排序列表中的數值位標記為1,然後順序輸出bitmap的標記位實現排序的方法。具體來說,分為兩步 1 迴圈待排序列表,i 表示待排序列錶值。bitmap i 1 二 實踐篇 參考一篇python實現的bitmap encoding utf 8 auth...