十年网站开发经验 + 多家企业客户 + 靠谱的建站团队
量身定制 + 运营维护+专业推广+无忧售后,网站问题一站解决
#本文以Android api 22为基准
创新互联是一家专业提供卢龙企业网站建设,专注与网站设计、网站建设、H5响应式网站、小程序制作等业务。10年已为卢龙众多企业、政府机构等服务。创新互联专业网站制作公司优惠进行中。在android.graphics.PixelFormat中定义了如下几种(不含deprecated的)RGB格式:
名称 | 值 | 含义 |
RGBA_8888 | 1 | 透明通道和三个颜色通道都是8,可表达的色彩值最广,这是使用最广泛的格式 |
RGBX_8888 | 2 | 与RGBA_8888类似不过,透明通道的值永远为255 |
RGB_888 | 3 | 只有三个颜色通道,存储空间相对前两个较小。 |
Bitmap代表了解码后图片,可用于直接的绘制,Bitmap与一个native层的bitmap对应,使用完后,需要调用recyle函数回收native内存。
android.graphics.Bitmap类代表了java层可绘制实体的最后一步。从一整个页面,到某个view,在到drawable,最后都会汇集到Bitmap。
对于任何一个view来说,在onDraw()回调中,canvas都已经与一个bitmap绑定。
Bitmap类提供了对像素点操作的一些基本接口。
对于开发者来说,关于Bitmap需要的做得事情有,创建Bitmap,操作像素,压缩存储,序列化/反序列化等。
需要自己创建Bitmap时,有两种情况,一种是全新创建,另外一种是加载已有的图片。
对于第一种,可使用Bitmap.createBitmap(...)函数创建,然后使用Bitmap类的像素操作接口填充像素,或者结合Canvas进行更高级的绘制。
对于后一种,图片的来源无非是这几种:network,drawableX目录,assets目录,raw目录,本地持久化存储。所有的这些图片都可以通过android.graphics.BitmapFactory工具类加载,解码并创建为Bitmap。具体如下:
来源于本地存储 | BitmapFactory.decodeFile(String, Options)或者BitmapFactory.decodeFile(String) |
来源于drawableX的纯图片 | BitmapDrawable drawable = (BitmapDrawable) context.getDrawable(int picResId); // 注意这里的picResId必须指向一个纯图片Bitmap bitmap = drawable.getBitmap(); |
来源于一般的drawable | Bitmap.Config config = drawable.getOpacity() != PixelFormat.OPAQUE ? Bitmap.Config.ARGB_8888 : Bitmap.Config.RGB_565;Bitmap bitmap = Bitmap.createBitmap(drawable.getIntrinsicWidth(), drawable.getIntrinsicHeight(), config);Canvas canvas = new Canvas(bitmap);drawable.setBounds(0, 0, w, h);drawable.draw(canvas); |
来源于assets | 假如图片路径为:/assets/img/asset_img.pngBitmap bitmap = BitmapFactory.decodeStream(context.getResources().getAssets().open(“img/asset_img.png")) |
来源于raw | Bitmap bitmap = BitmapFactory.decodeStream(context.getResources().openRawResource(R.raw.raw_img)) |
操作像素
对于像素的操作可以通过Bitmap类自己提供的一些基本的操作接口,也可以通过canvas进行。后者提供了很多人性化的绘制方法,并且可以与很多android graphics框架中许多图形特效类结合使用,绘制出更加出彩的内容。这里只谈前者,后者会在其他文章中继续讨论。
getPixel(int x, int y) | 获取指定位置的像素色彩值 |
getPixels(int[] pixels, int offset, int stride, int x, int y, int width, int height) | 一次获取多个像素点,如果要获取多个像素,调用此方法比循环的调用getPixel()效率要高 |
setPixel(int x, int y) | 设置指定位置的一个像素 |
setPixels(int[] pixels, int offset, int stride, int x, int y, int width, int height) | 批量设置像素,对于同时设置多像素来说,该方法比循环调用setPixel()效率要高 |
copyPixelsToBuffer(Buffer dst) | 复制整个图片像素到一个buffer |
copyPixelsFromBuffer(Buffer src) | 用一个buffer中的像素覆盖当前bitmap中的像素 |
setPixels()和getPixels()参数中的stride代表了参数pixels一行的长度,我们可以把这两个方法看作是一个像素矩阵向另外一个像素矩阵投射的过程,两个矩阵可能大小不同。不管是setPixels()还是getPixels(),当位图像素的读取或设置需要换行时,pixels数组也需要”换行”,这时后者的换行就需要以stride为基准。这也是为甚stride要大于等于width的原因。具体可以看这篇文章:http://ranlic.iteye.com/blog/1313735
压缩存储
Bitmap.compress(CompressFormat format, int quality, OutputStream outStream),其中quality的值范围是[0, 100],0代表最低的质量大的压缩。
序列化与反序列化
Bitmap实现了Parcelable接口,如果是用intnet进行数据传递,可以直接放到extra中。
如果是通过网络传输(这里不考虑需求的合理性,因为实际中很少有直接通过网络传输位图的,都是传输压缩后的图片),则需要调用copyPixelsToBuffer()。
另外有需要云服务器可以了解下创新互联scvps.cn,海内外云服务器15元起步,三天无理由+7*72小时售后在线,公司持有idc许可证,提供“云服务器、裸金属服务器、高防服务器、香港服务器、美国服务器、虚拟主机、免备案服务器”等云主机租用服务以及企业上云的综合解决方案,具有“安全稳定、简单易用、服务可用性高、性价比高”等特点与优势,专为企业上云打造定制,能够满足用户丰富、多元化的应用场景需求。