當前位置:首頁 » 安卓系統 » androidbitmap壓縮

androidbitmap壓縮

發布時間: 2022-05-07 09:52:59

① 請問在android 編程,Bitmap 怎麼轉換成 file

static boolean saveBitmap2file(Bitmap bmp,String filename){
CompressFormat format= Bitmap.CompressFormat.JPEG;
int quality = 100;
OutputStream stream = null;
try {
stream = new FileOutputStream("/sdcard/" + filename);
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}

return bmp.compress(format, quality, stream);
}

stream = new FileOutputStream("/sdcard/" + filename);
獲取要保存到的文件的文件流
bmp.compress(format, quality, stream);
把指定的bitmp壓縮到文件中 就是保存在指定文件中 format是文件格式(Bitmap.CompressFormat.JPEG jpeg) quality 是品質(100 就是原質量)
看名字 saveBitmap2file
你要上傳的話 就去指定位置取這個file就行 路徑的問題 可能有寫真機找不到/sdcard/
建議 Environment類取地址 保存和讀取時 都用Environment.getXXXX

② android bitmap 改變圖片大小

Optionsoptions1=newOptions();
options1.inJustDecodeBounds=true;
BitmapFactory.decodeFile(filePath,options1);
options1.inSampleSize=RegisterTool.calculateInSampleSize(options1,110,160);//110,160:轉換後的寬和高,具體值會有些出入
options1.inJustDecodeBounds=false;
Bitmapbitmap=BitmapFactory.decodeFile(filePath,options1);//filePath:文件路徑
(BitmapFactory.Optionsoptions,
intreqWidth,intreqHeight){

finalintheight=options.outHeight;
finalintwidth=options.outWidth;
intinSampleSize=1;

if(height>reqHeight||width>reqWidth){

finalintheightRatio=Math.round((float)height
/(float)reqHeight);
finalintwidthRatio=Math.round((float)width/(float)reqWidth);

inSampleSize=heightRatio<widthRatio?widthRatio:heightRatio;
}

returninSampleSize;
}
//壓縮圖片並將Bitmap保存到本地
FileOutputStreamout=newFileOutputStream(newFile(filePath));
saveBitmap.compress(Bitmap.CompressFormat.JPEG,60,out);//60代表壓縮40%

③ android bitmap怎麼做緩存

Bitmap是Android系統中的圖像處理的最重要類之一。用它可以獲取圖像文件信息,進行圖像剪切、旋轉、縮放等操作,並可以指定格式保存圖像文件。

重要函數

public void recycle() // 回收點陣圖佔用的內存空間,把點陣圖標記為Dead

public final boolean isRecycled() //判斷點陣圖內存是否已釋放

public final int getWidth()//獲取點陣圖的寬度

public final int getHeight()//獲取點陣圖的高度

public final boolean isMutable()//圖片是否可修改

public int getScaledWidth(Canvas canvas)//獲取指定密度轉換後的圖像的寬度

public int getScaledHeight(Canvas canvas)//獲取指定密度轉換後的圖像的高度

public boolean compress(CompressFormat format, int quality, OutputStream stream)//按指定的圖片格式以及畫質,將圖片轉換為輸出流。

format:Bitmap.CompressFormat.PNG或Bitmap.CompressFormat.JPEG

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

public static Bitmap createBitmap(Bitmap src) //以src為原圖生成不可變得新圖像

public static Bitmap createScaledBitmap(Bitmap src, int dstWidth, int dstHeight, boolean filter)//以src為原圖,創建新的圖像,指定新圖像的高寬以及是否可變。

public static Bitmap createBitmap(int width, int height, Config config)——創建指定格式、大小的點陣圖

public static Bitmap createBitmap(Bitmap source, int x, int y, int width, int height)以source為原圖,創建新的圖片,指定起始坐標以及新圖像的高寬。

BitmapFactory工廠類:
Option 參數類:

public boolean inJustDecodeBounds//如果設置為true,不獲取圖片,不分配內存,但會返回圖片的高度寬度信息。

public int inSampleSize//圖片縮放的倍數

public int outWidth//獲取圖片的寬度值

public int outHeight//獲取圖片的高度值

public int inDensity//用於點陣圖的像素壓縮比

public int inTargetDensity//用於目標點陣圖的像素壓縮比(要生成的點陣圖)

public byte[] inTempStorage //創建臨時文件,將圖片存儲

public boolean inScaled//設置為true時進行圖片壓縮,從inDensity到inTargetDensity

public boolean inDither //如果為true,解碼器嘗試抖動解碼

public Bitmap.Config inPreferredConfig //設置解碼器

public String outMimeType //設置解碼圖像

public boolean inPurgeable//當存儲Pixel的內存空間在系統內存不足時是否可以被回收

public boolean inInputShareable //inPurgeable為true情況下才生效,是否可以共享一個InputStream

public boolean inPreferQualityOverSpeed //為true則優先保證Bitmap質量其次是解碼速度

public boolean inMutable //配置Bitmap是否可以更改,比如:在Bitmap上隔幾個像素加一條線段

public int inScreenDensity //當前屏幕的像素密度
工廠方法:

public static Bitmap decodeFile(String pathName, Options opts) //從文件讀取圖片

public static Bitmap decodeFile(String pathName)

public static Bitmap decodeStream(InputStream is) //從輸入流讀取圖片

public static Bitmap decodeStream(InputStream is, Rect outPadding, Options opts)

public static Bitmap decodeResource(Resources res, int id) //從資源文件讀取圖片

public static Bitmap decodeResource(Resources res, int id, Options opts)

public static Bitmap decodeByteArray(byte[] data, int offset, int length) //從數組讀取圖片

public static Bitmap decodeByteArray(byte[] data, int offset, int length, Options opts)

public static Bitmap decodeFileDescriptor(FileDescriptor fd)//從文件讀取文件 與decodeFile不同的是這個直接調用JNI函數進行讀取 效率比較高

public static Bitmap decodeFileDescriptor(FileDescriptor fd, Rect outPadding, Options opts)
Bitmap.Config inPreferredConfig :

枚舉變數 (點陣圖位數越高代表其可以存儲的顏色信息越多,圖像越逼真,佔用內存越大)
public static final Bitmap.Config ALPHA_8 //代表8位Alpha點陣圖 每個像素佔用1byte內存
public static final Bitmap.Config ARGB_4444 //代表16位ARGB點陣圖 每個像素佔用2byte內存
public static final Bitmap.Config ARGB_8888 //代表32位ARGB點陣圖 每個像素佔用4byte內存
public static final Bitmap.Config RGB_565 //代表8位RGB點陣圖 每個像素佔用2byte內存
Android中一張圖片(BitMap)佔用的內存主要和以下幾個因數有關:圖片長度,圖片寬度,單位像素佔用的位元組數。一張圖片(BitMap)佔用的內存=圖片長度*圖片寬度*單位像素佔用的位元組數

④ 在android開發中載入的圖片太大,有好幾十兆,應該怎麼辦

如果圖片太大會造成OOM內存溢出的錯誤,需要用Bitmap的壓縮機制。
解決方案:
1.使用BitmapFactory.decodeStream替代createBitmap方法
原因是該方法直讀取圖片位元組,調用JNI>>nativeDecodeAsset()來完成decode,無需再使用java層的createBitmap。

2.使用壓縮讀取技術
BitmapFactory.Options options = new BitmapFactory.Options();
options.inJustDecodeBounds = true;
BitmapFactory.decodeFile(imageSdUri, options);
final int height = options.outHeight;
final int width = options.outWidth;
options.inSampleSize = 1;
int w = 320;
int h = 480;
h = w*height/width;//計算出寬高等比率
int a = options.outWidth/ w;
int b = options.outHeight / h;
options.inSampleSize = Math.max(a, b);
options.inJustDecodeBounds = false;
Bitmap bitmap = BitmapFactory.decodeFile(imageSdUri, options);

3.及時釋放Bitamp
Bitmap對象在不使用時,我們應該先調用recycle()釋放內存,然後才它設置為null.雖然recycle()從源碼上看,調用它應該能立即釋放Bitmap的主要內存,但是測試結果顯示它並沒能立即釋放內存。但是我它應該還是能大大的加速Bitmap的主要內存的釋放。

⑤ android 圖片質量壓縮和尺寸壓縮有什麼區別

這個方法用來將特定格式的壓縮圖片寫入輸出流(OutputStream)中,當然例如輸出流與文件聯系在一起,壓縮後的圖片也就是一個文件。如果壓縮成功則返回true,其中有三個參數:

format是壓縮後的圖片的格式,可取值:Bitmap.CompressFormat .JPEG、~.PNG、~.WEBP。

quality的取值范圍為[0,100],值越小,經過壓縮後圖片失真越嚴重,當然圖片文件也會越小。(PNG格式的圖片會忽略這個值的設定)

stream指定壓縮的圖片輸出的地方,比如某文件。

上述方法還有一個值得注意的地方是:當用BitmapFactory decode文件時可能返回一個跟原圖片不同位深的圖片,或者丟失了每個像素的透明值(alpha),比如說,JPEG格式的圖片僅僅支持不透明的像素。文章android圖片壓縮在文末提到的下面這點可能就是這個原因:

當調用bitmap.compress(CompressFormat.JPEG, 100, fos);保存為圖片時發現圖片背景為黑色,如下圖:

下面是質量壓縮的代碼:

(Bitmapbmp,Filefile){

ByteArrayOutputStreambaos=newByteArrayOutputStream();

intoptions=80;//個人喜歡從80開始,

bmp.compress(Bitmap.CompressFormat.JPEG,options,baos);

while(baos.toByteArray().length/1024>100){

baos.reset();

options-=10;

bmp.compress(Bitmap.CompressFormat.JPEG,options,baos);

}

try{

FileOutputStreamfos=newFileOutputStream(file);

fos.write(baos.toByteArray());

fos.flush();

fos.close();

}catch(Exceptione){

e.printStackTrace();

}

}

這段代碼來自Android圖片壓縮總結,我根據自己的需求改了改,但是大同小異,所以就直接貼了。

隨著代碼中的option逐漸變小,我們可以在logcat中列印baos的大小來查看圖片的大小。我們也可以去掉while的循環條件,一直壓縮下去看效果,最終一張照片可能就由原來的3、4M變成了幾百K甚至幾百B了。我在試的過程中將option設置成100,壓縮後偶爾會出現一張3、4M的圖片經過壓縮後竟變成了6、7M,這里還是有點困惑,不知道為什麼。

隨後,我想把這個壓縮後的圖片(1、200KB)填充到ImageView中時卻失敗了,logcat中提示圖片過大!這就是文章開頭提到的問題,雖然我們通過質量壓縮使File形式的圖片文件縮小了,但是並沒有改變圖片的寬高,原先是1080*1920解析度的圖片經壓縮後還是1080*1920,而File格式轉換成Bitmap格式進入到內存中時,內存是根據圖片的像素數量來給圖片分配內存大小的,還是有好幾M,因此填充ImageView失敗。

順便提一下,可以用bitmap.getByteCount()獲取存儲bitmap像素的內存大小,但是KITKAT(Android 4.4版本)以後用getAllocateByteCount()獲取。一般情況下,後者返回值比前者大,比如,當bitmap被重用去decode另外更小的bitmaps時,或者被人為地配置一下屬性值,比如setWidth()、setHeight()、reconfigure()時,如果bitmap不做以上操作,二者的返回值應該是一樣的。(譯文,不太懂)

二、尺寸壓縮

特點: 通過設置采樣率, 減少圖片的像素, 達到對內存中的Bitmap進行壓縮



我們主要通過BitmapFactory中的decodeFile方法對圖片進行尺寸壓縮:

publicstaticBitmapdecodeFile(StringpathName,BitmapFactory.Optionsopts)

public static Bitmap decodeFile (String pathName, BitmapFactory.Options opts)

其中有兩個參數:

pathName是圖片文件的路徑。

opts 就是所謂的采樣率,它里邊有很多屬性可以設置,我們通過設置屬性來達到根據自己的需要,壓縮出指定的圖片。其中比較常用的屬性有:

booleaninJustDecodeBounds—— 如果設置為true,則只讀取bitmap的寬高,而忽略內容。

intinSampleSize—— 如果>1,調用decodeFile方法後,就會得到一個更小的bitmap對象(已壓縮)。比如設置為2,那麼新Bitmap的寬高都會是原Bitmap寬高的1/2,總體大小自然就是原來的1/4了,以此類推。

booleaninPurgeable—— 如果設置為true,壓縮後的圖片像素占的內存將會在系統清理內存的時候被回收掉,當像素的信息再次被用到時將會自動重新decode該像素(比如getPixels()時)。(慎用!重復decode可以會造成UI的卡頓,API level 21 已棄用)

booleaninInputShareable—— 與inPurgeable配合使用,如果inPurgeable設置成false,自動忽略此值,如果inPurgeable為true,此值決定是否該bitmap能分享引用給輸入數據(inputstream,array等),或者必須進行深拷貝。API level 21 已棄用。(這是譯文,不太理解!!!)

下面是一段實現的代碼

privateBitmapsizeCompres(Stringpath,intrqsW,intrqsH){

//用option設置返回的bitmap對象的一些屬性參數

finalBitmapFactory.Optionsoptions=newBitmapFactory.Options();

options.inJustDecodeBounds=true;//設置僅讀取Bitmap的寬高而不讀取內容

BitmapFactory.decodeFile(path,options);//獲取到圖片的寬高,放在option里邊

finalintheight=options.outHeight;//圖片的高度放在option里的outHeight屬性中

finalintwidth=options.outWidth;

intinSampleSize=1;

if(rqsW==0||rqsH==0){

options.inSampleSize=1;

}elseif(height>rqsH||width>rqsW){

finalintheightRatio=Math.round((float)height/(float)rqsH);

finalintwidthRatio=Math.round((float)width/(float)rqsW);

inSampleSize=heightRatio<widthRatio?heightRatio:widthRatio;

options.inSampleSize=inSampleSize;

}

returnBitmapFactory.decodeFile(path,options);//主要通過option里的inSampleSize對原圖片進行按比例壓縮

}

private Bitmap sizeCompres(String path, int rqsW, int rqsH) {

// 用option設置返回的bitmap對象的一些屬性參數

final BitmapFactory.Options options = new BitmapFactory.Options();

options.inJustDecodeBounds = true;// 設置僅讀取Bitmap的寬高而不讀取內容

BitmapFactory.decodeFile(path, options);// 獲取到圖片的寬高,放在option里邊

final int height = options.outHeight;//圖片的高度放在option里的outHeight屬性中

final int width = options.outWidth;

int inSampleSize = 1;

if (rqsW == 0 || rqsH == 0) {

options.inSampleSize = 1;

} else if (height > rqsH || width > rqsW) {

final int heightRatio = Math.round((float) height / (float) rqsH);

final int widthRatio = Math.round((float) width / (float) rqsW);

inSampleSize = heightRatio < widthRatio ? heightRatio : widthRatio;

options.inSampleSize = inSampleSize;

}

return BitmapFactory.decodeFile(path, options);// 主要通過option里的inSampleSize對原圖片進行按比例壓縮

}

上面就是簡單的質量壓縮與尺寸壓縮。

⑥ android 圖片壓縮50*1024是多少

總結來看,圖片有三種存在形式:硬碟上時是file,網路傳輸時是stream,內存中是stream或bitmap。
所謂的質量壓縮,它其實只能實現對file的影響,你可以把一個file轉成bitmap再轉成file,或者直接將一個bitmap轉成file時,這個最終的file是被壓縮過的,但是中間的bitmap並沒有被壓縮(或者說幾乎沒有被壓縮,我不確定),因為bigmap在內存中的大小是按像素計算的,也就是width * height,對於質量壓縮,並不會改變圖片的像素,所以就算質量被壓縮了,但是bitmap在內存的佔有率還是沒變小,但你做成file時,它確實變小了;

而尺寸壓縮由於是減小了圖片的像素,所以它直接對bitmap產生了影響,當然最終的file也是相對的變小了;

最後把自己總結的工具類貼出來:
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import <strong style="color:black;background-color:#ffff66">android</strong>.graphics.Bitmap;
import <strong style="color:black;background-color:#ffff66">android</strong>.graphics.Bitmap.Config;
import <strong style="color:black;background-color:#ffff66">android</strong>.graphics.BitmapFactory;

⑦ android 怎麼將bitmap進行尺寸壓縮

總結來看,圖片有三種存在形式:硬碟上時是file,網路傳輸時是stream,內存中是stream或bitmap,所謂的質量壓縮,它其實只能實現對file的影響,你可以把一個file轉成bitmap再轉成file,或者直接將一個bitmap轉成file時,這個最終的file是被壓縮過的,但是中間的bitmap並沒有被壓縮(或者說幾乎沒有被壓縮,我不確定),因為bigmap在內存中的大小是按像素計算的,也就是width * height,對於質量壓縮,並不會改變圖片的像素,所以就算質量被壓縮了,但是bitmap在內存的佔有率還是沒變小,但你做成file時,它確實變小了;

而尺寸壓縮由於是減小了圖片的像素,所以它直接對bitmap產生了影響,當然最終的file也是相對的變小了;

最後把自己總結的工具類貼出來:

[java] view plain
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;

⑧ 調用安卓系統自帶的照相機,發現拍完照返回的bitmap是被壓縮過的,想問下是不是每個安卓系統都是這樣

拍完照後,檢索資料庫的時候讀取其地址,不要轉換成bitmap。用文件方式讀取。

⑨ android bitmapfactory.options怎麼把突變壓縮成固定的像素

設置縮放大小對圖片作處理

[java] view plain
public Bitmap getBitmapFromFile(File dst, int width, int height) {
if (null != dst && dst.exists()) {
BitmapFactory.Options opts = null;
if (width > 0 && height > 0) {
opts = new BitmapFactory.Options();
opts.inJustDecodeBounds = true;
BitmapFactory.decodeFile(dst.getPath(), opts);
// 計算圖片縮放比例
final int minSideLength = Math.min(width, height);
opts.inSampleSize = computeSampleSize(opts, minSideLength,
width * height);
opts.inJustDecodeBounds = false;
opts.inInputShareable = true;
opts.inPurgeable = true;
}
try {
return BitmapFactory.decodeFile(dst.getPath(), opts);
} catch (OutOfMemoryError e) {
e.printStackTrace();
}
}
return null;
}

public static int computeSampleSize(BitmapFactory.Options options,
int minSideLength, int maxNumOfPixels) {
int initialSize = computeInitialSampleSize(options, minSideLength,
maxNumOfPixels);

int roundedSize;
if (initialSize <= 8) {
roundedSize = 1;
while (roundedSize < initialSize) {
roundedSize <<= 1;
}
} else {
roundedSize = (initialSize + 7) / 8 * 8;
}

return roundedSize;
}

private static int computeInitialSampleSize(BitmapFactory.Options options,
int minSideLength, int maxNumOfPixels) {
double w = options.outWidth;
double h = options.outHeight;

int lowerBound = (maxNumOfPixels == -1) ? 1 : (int) Math.ceil(Math
.sqrt(w * h / maxNumOfPixels));
int upperBound = (minSideLength == -1) ? 128 : (int) Math.min(Math
.floor(w / minSideLength), Math.floor(h / minSideLength));

if (upperBound < lowerBound) {
// return the larger one when there is no overlapping zone.
return lowerBound;
}

if ((maxNumOfPixels == -1) && (minSideLength == -1)) {
return 1;
} else if (minSideLength == -1) {
return lowerBound;
} else {
return upperBound;
}
}

[java] view plain
/**
* 獲取經過處理的資源圖,包括普通圖和.9圖
* @param context 應用環境
* @param id 資源id
* @return Drawable格式的資源
* <p>
* 以1080p為基準,小於此尺寸的縮寫,大於此尺寸的放大
*/
public static Drawable getCompatibleDrawable(Context context, int id) {
BitmapFactory.Options options = new BitmapFactory.Options();
options.inDensity = 240;
options.inScreenDensity = (int) (240*ratio);
options.inTargetDensity = (int) (240*ratio);

Bitmap bitmap = BitmapFactory.decodeResource(context.getResources(),
id, options);
byte[] ninePathChunk = bitmap.getNinePatchChunk();

if (NinePatch.isNinePatchChunk(ninePathChunk)) {
NinePatch ninePath = new NinePatch(bitmap, ninePathChunk, null);

return new NinePatchDrawable(ninePath);
} else {
return new BitmapDrawable(bitmap);
}
}

熱點內容
分布式緩存部署步驟 發布:2025-05-14 13:24:51 瀏覽:610
php獲取上一月 發布:2025-05-14 13:22:52 瀏覽:89
購買雲伺服器並搭建自己網站 發布:2025-05-14 13:20:31 瀏覽:688
sqlserver建立視圖 發布:2025-05-14 13:11:56 瀏覽:484
搭建httpsgit伺服器搭建 發布:2025-05-14 13:09:47 瀏覽:255
新電腦拿回來我該怎麼配置 發布:2025-05-14 13:09:45 瀏覽:240
視頻伺服器新建ftp用戶 發布:2025-05-14 13:03:09 瀏覽:225
php花生 發布:2025-05-14 12:54:30 瀏覽:550
java人才 發布:2025-05-14 12:29:10 瀏覽:649
如何打開軟密碼 發布:2025-05-14 12:28:55 瀏覽:427