android 应用开发中经常遇到图片下载,下面是我在开发中常用的方法列举下:
1、解决 图片下载 导致outmemory问题
2、保存本地
3、有从本地获取,本地获取不到则从网络获取
代码如下:
package com.changhong.mscreensynergy.common;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.FilterInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL;
import com.changhong.mscreensynergy.mainui.MainActivity;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Matrix;
public class DownloadPicture {
//构造函数
public DownloadPicture(){
}
/**
* 功能:优先从本地读取图片
* @param channelName
* @param pictureURL
* @param width
* @param height
* @return
*/
public Bitmap getChannelLog(String channelName, String pictureURL, int width, int height ) {
String saveChannelName = channelName + ".jpg";
Bitmap myBitmap = null;
myBitmap = this.getPictureFromLocal(saveChannelName, width, height);
if(myBitmap == null) { //本地获取失败
//System.out.println("getChannelLog-----本地没有保存,从网络获取!");
myBitmap = this.getPictureFromNetwork(pictureURL, width, height);
if(myBitmap != null) {
saveBitmapToLocal(myBitmap, saveChannelName);
}
}else{
//System.out.println("getChannelLog-----从本地获取!");
}
return myBitmap;
}
/**
* 执行下载图片并保存图片
* @param imageURL
* @param saveFileName
* @param width
* @param height
* @return
*/
public boolean downloadPictureAndSaveTolocal(String imageURL, String saveFileName, int width, int height) {
boolean res = false;
Bitmap pictureBitmap = getPictureFromNetwork(imageURL, width, height);
if(pictureBitmap != null) {
res = saveBitmapToLocal(pictureBitmap, saveFileName);
}else{
System.out.println("图片下载失败!");
}
return res;
}
/**
* 保存bitmap到本地
* @param saveBitmap
* @param saveFileName
* @return
*/
public boolean saveBitmapToLocal(Bitmap saveBitmap, String fileName) {
boolean res = false;
String saveFileName = MainActivity.OUT_STORAGE_PATH + fileName;
//把图片保存成本地文件saveFileName
File file = new File(saveFileName);
if (!file.exists()) {
try {
file.createNewFile();
} catch (IOException e) {
e.printStackTrace();
return false;
}
}
BufferedOutputStream bos;
if(saveBitmap != null) {
try {
bos = new BufferedOutputStream(new FileOutputStream(file));
res = saveBitmap.compress(Bitmap.CompressFormat.JPEG, 80, bos);
try {
bos.flush();
bos.close();
} catch (IOException e) {
e.printStackTrace();
}
} catch (FileNotFoundException e1) {
e1.printStackTrace();
}
if(res) {
System.out.println("图片保存成功,保存路径:"+saveFileName);
}else {
System.out.println("图片保存失败!");
}
}
return res;
}
/**
* 从网络上获取图片
* @param pictureURL
* @param width
* @param height
* @return
*/
public Bitmap getPictureFromNetwork(String pictureURL, int width, int height){
//检查输入条件
if(pictureURL == null) {
return null;
}
Bitmap imageBitmap = null;
try{
//System.out.println("getPictureFromNetwork---pictureURL==="+pictureURL);
if ( pictureURL.startsWith("http://") || pictureURL.startsWith("HTTP://") ) {
URL imageUrl = new URL(pictureURL);
HttpURLConnection conn = (HttpURLConnection)imageUrl.openConnection();
if (conn == null) {
System.out.println("没有获取到数据!");
return null;
}
conn.setConnectTimeout(10*1000); //设置超时时间为10秒
conn.setReadTimeout(5*1000); //设置超时时间为5秒
InputStream is = conn.getInputStream();
if (is == null) {
System.out.println("没有获取到数据!");
return null;
}
BitmapFactory.Options options = new BitmapFactory.Options();
options.inJustDecodeBounds = true;
BitmapFactory.decodeStream(new PatchInputStream(is), null, options);
int inSampleSize = computeSampleSize(options, -1, width * height);
is.close();
conn.disconnect();
imageUrl = new URL(pictureURL);
conn = (HttpURLConnection)imageUrl.openConnection();
if (conn == null) {
return null;
}
conn.setConnectTimeout(10*1000); //设置超时时间为10秒
conn.setReadTimeout(5*1000); //设置超时时间为5秒
is = conn.getInputStream();
if (is == null) {
return null;
}
options = new BitmapFactory.Options();
options.inJustDecodeBounds = false;
options.inSampleSize = inSampleSize;
imageBitmap = BitmapFactory.decodeStream(new PatchInputStream(is), null, options);
is.close();
conn.disconnect();
System.out.println("网络图片下载成功!");
} else {
System.out.println("-----加载本地图片!-----");
imageBitmap = BitmapFactory.decodeFile(pictureURL, null);
}
}catch (OutOfMemoryError e) {
System.out.println("图片下载失败!");
imageBitmap = null;
e.printStackTrace();
} catch (IOException e) {
System.out.println("图片下载失败!");
imageBitmap = null;
e.printStackTrace();
}
return imageBitmap;
}
/**
* 从本地获取图片
* @param picturePath
* @param width
* @param height
* @return
*/
public Bitmap getPictureFromLocal(String pictureName, int width, int height){
String picturePath = MainActivity.OUT_STORAGE_PATH + pictureName;
File file = new File(picturePath);
if( !file.exists() ) {
System.out.println("---getPictureFromLocal--图片不存在!");
return null;
}
//获取缩放比例
BitmapFactory.Options options = new BitmapFactory.Options();
options.inJustDecodeBounds = true;
BitmapFactory.decodeFile(picturePath, options);
int inSampleSize = computeSampleSize(options, -1, width * height);
if(inSampleSize < 1) {
inSampleSize = 1;
}
//读取图片,注意这次要把options.inJustDecodeBounds 设为 false哦
options = new BitmapFactory.Options();
options.inSampleSize = inSampleSize;
options.inJustDecodeBounds = false;
return BitmapFactory.decodeFile(picturePath, options);
}
//根据固定大小对图片进行缩放
public Bitmap resizePicture(int desWidth, int desHeight, Bitmap bitmap) {
int bmpWidth = bitmap.getWidth();
int bmpHeight = bitmap.getHeight();
//缩放图片的尺寸
float scaleWidth = (float) desWidth / bmpWidth; //按固定大小缩放 sWidth 写多大就多大
float scaleHeight = (float) desHeight / bmpHeight;
Matrix matrix = new Matrix();
matrix.postScale(scaleWidth, scaleHeight);
//产生缩放后的Bitmap对象
Bitmap resizeBitmap = Bitmap.createBitmap( bitmap, 0, 0, bmpWidth, bmpHeight, matrix, false );
//回收图片所占的内存
bitmap.recycle();
return resizeBitmap;
}
//让inputstream 数据保持完整性
public class PatchInputStream extends FilterInputStream {
protected PatchInputStream(InputStream in) {
super(in);
// TODO Auto-generated constructor stub
}
public long skip(long n) throws IOException {
long m = 0l;
while (m < n) {
long _m = in.skip(n - m);
if (_m == 0l) {
break;
}
m += _m;
}
return m;
}
}
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 lowerBound;
}
if ((maxNumOfPixels == -1) && (minSideLength == -1)) {
return 1;
} else if (minSideLength == -1) {
return lowerBound;
} else {
return upperBound;
}
}
}