从本节开始进行图片的发送,对于图片发送,主要涉及到如下几个大的步骤:
1.生成图片key,这里包括大图和小图(image_key,small_image_key);
2.生成图片Message,包含图片的所有信息
3.生成图片,这里主要进行了图片的压缩操作(image,small_image);
4.生成图片路径(image_path,small_image_path);
5. 将图片保存到本地缓存目录;
6.将图片放入内存缓存中;
7.将步骤2中生成的message插入到数据库中;
8.刷新显示列表,让message处于发送状态;
9.执行发送动作;
之后我会对上面的9个步骤逐一实现,给出具体的实现方法。
[1]生成图片key很简单,这里是通过时间戳来实现(关键字+时间戳)
String image_key = "image_" + Calendar.getInstance().getTimeInMillis();
String small_image_key = "small_" + image_key;
这样就生成饿大图和小图的key.
[2]生成图片message就是一般的创建对象方法
PushMessage message = new PushMessage(image_key,small_image_key);
当然PushMessage还有许多别的参数,这里主要设置了message的大图和小图。
[3]生成图片,即生成压缩之后的图片
压缩图片的目的:避免占用过多内存;发送原图,如果原图太大,浪费流量。
图片在控件上是以Bitmap的形式显示的,bitmap大小=图片长度(px)*图片宽度(px)*单位像素占用的字节数,
单位像素占用的字节数是指图片的色彩模式,在BitmapFactory.Options.inPreferredConfig这里可以找到,一共有4种,默认色彩模式为ARGB_8888,argb各占8位,属于高质量图片格式,单位像素所占字节数是4。
改变Bitmap大小方法大概有三种:改变图片尺寸,改变图片色彩模式,改变图片质量。
public static Bitmap zoomImage(String imgPath, int maxWidth, int maxHeight) { Bitmap desBitmap = null; try { Options options = new Options(); options.inJustDecodeBounds = true; options.inPreferredConfig = ImageLoader.getConfig(); BitmapFactory.decodeFile(imgPath, options); int srcWidth = options.outWidth; int srcHeight = options.outHeight; int scaleWidth = srcWidth / maxWidth; int scaleHeight = srcHeight / maxHeight; int scale = scaleWidth < scaleHeight ? scaleWidth : scaleHeight; if (scale < 1) { scale = 1; } options.inSampleSize = scale; options.inJustDecodeBounds = false; desBitmap = BitmapFactory.decodeFile(imgPath, options); if (desBitmap != null) { desBitmap = zoomSmallImageByMaxSize(desBitmap, maxWidth, maxHeight); } } catch (Exception e) { if (EnvConstants.DBG_D) { e.printStackTrace(); } } return desBitmap; }
zoomImage()该方法只能做到粗略压缩,无法做到精确压缩;
因此,需要对此进一步做精确压缩,<span style="font-family: Arial, Helvetica, sans-serif;">zoomSmallImageByMaxSize()方法可以做到。</span>
<span style="font-family: Arial, Helvetica, sans-serif;"></span><pre name="code" class="java"> private static Bitmap zoomSmallImageByMaxSize(Bitmap srcImage, int maxWidth, int maxHeight) { if (srcImage == null) { return null; } float width = srcImage.getWidth(); float height = srcImage.getHeight(); if(width <= maxWidth && height <= maxHeight){ return srcImage; } float scaleWidth = (float)maxWidth / width; float scaleHeight = (float)maxHeight / height; float scale = scaleWidth < scaleHeight ? scaleWidth : scaleHeight; Matrix matrix = new Matrix(); matrix.postScale(scale, scale); Bitmap bitmap = Bitmap.createBitmap(srcImage, 0, 0, (int) width, (int) height, matrix, true); if (srcImage != bitmap) { srcImage.recycle(); } return bitmap; }
先进行粗略压缩的目的是为了防止图片过大,发生内存溢出(OOM)。
粗略压缩的时候只是对图片的轮廓进行压缩,不压缩内容,图片内容并没有载入内存,所以不会发生OOM。
粗略压缩为精确压缩的过渡,目的就是不会因为图片过大而发生OOM,导致系统崩溃。
粗略压缩可以将1280大小的图片压缩到640到1280之间,无法精确到640。
这里主要是对图片的大小进行了压缩,随后将图片保存到本地缓存目录的时候还会对其进行图片质量的压缩。