Bitmap使用

一.Bitmap

1.Bitmap的生成

/**
     * 由本地文件路径、网络url或者项目的资源文件,生成Bitmap(旧,极端情况下可能造成OOM)
     * @param filePath
     */
    private void productBitmap(String filePath){
        Bitmap des_bitmap = null;
        BitmapFactory.Options options  = new BitmapFactory.Options();

        //本地文件路径或者网络url
        Uri uri = Uri.parse(filePath);
        des_bitmap = BitmapFactory.decodeFile(uri.toString(),options);

        //项目资源文件
        des_bitmap = BitmapFactory.decodeResource(getResources(),R.drawable.ic_launcher);

        if(iv_bitmap_test!=null) {
            iv_bitmap_test.setImageBitmap(des_bitmap);
        }else{
            iv_bitmap_test = (ImageView) findViewById(R.id.iv_bitmap_test);
            iv_bitmap_test.setImageBitmap(des_bitmap);
        }
    }

2.bitmap缩放、等图像变换

(1)长宽相同比例缩放

用BitmapFactory的decodeFile方法,然后通过传递进去 BitmapFactory.Option类型的参数进行取缩略图,在Option中,属性值inSampleSize表示缩略图大小为原始图片大小的几分之一,即如果这个值为2,则取出的缩略图的宽和高都是原始图片的1/2,图片大小就为原始大小的1/4。

经过阅读文档发现,Options中有个属性inJustDecodeBounds,文档中的是这么说的:

If set to true, the decoder will return null (no bitmap), but the out... fields will still be set, allowing the caller to query the bitmap without having to allocate the memory for its pixels.  

意思就是说如果该值设为true那么将不返回实际的bitmap对象,不给其分配内存空间但是可以得到一些解码边界信息即图片大小等信息。因此我们可以通过设置inJustDecodeBounds为true,获取到outHeight(图片原始高度)和 outWidth(图片的原始宽度),然后计算一个inSampleSize(缩放值),就可以取图片了,这里要注意的是,inSampleSize 可能等于0,必须做判断。也就是说先将Options的属性inJustDecodeBounds设为true,先获取图片的基本大小信息数据(信息没有保存在bitmap里面,而是保存在options里面),通过options.outHeight和 options. outWidth获取的大小信息以及自己想要到得图片大小计算出来缩放比例inSampleSize,然后紧接着将inJustDecodeBounds设为false,就可以根据已经得到的缩放比例得到自己想要的图片缩放图了。

/**
     * 由File转成长宽固定相同比例的bitmap。实现长宽等比例缩放
     * @return
     */
    private Bitmap resizeBitmap(String filePath){
        Bitmap des_bitmap ;

        BitmapFactory.Options options = new BitmapFactory.Options();
        //表示缩略图大小为原始图片大小的几分之一,即如果这个值为2,则取出的缩略图的宽和高都是原始图片的1/2,图片大小就为原始大小的1/4
        options.inJustDecodeBounds = true;
        des_bitmap = BitmapFactory.decodeFile(filePath,options);//des_bitmap为null.因为options.inJustDecodeBounds = true,节省内存

        //长宽按照相同比例缩放
        int height = options.outHeight;
        int width = options.outWidth;
        int scale;//缩放值,因为为等比例缩放.
        if(height > width){//以高为准
            scale = (int) (height/200.0f);//该200说明目标大小为200PX
        }else{
            scale = (int) (width/200.0f);//该200说明目标大小为200PX
        }
        if(scale<=0){
            scale = 1;
        }
        options.inSampleSize = scale;
        options.inJustDecodeBounds = false;
        Bitmap new_bitmap = BitmapFactory.decodeFile(filePath,options);//des_bitmap不为null
        if(des_bitmap!=new_bitmap){
            des_bitmap.recycle();//注意销毁不用的bitmap
        }
        return new_bitmap;
    }

(2)Bitmap与Matrix搭配,实现缩放或者其他形变例如旋转

/**
     * 由Bitmap转成指定大小的Bitmap,实现缩放成指定准确大小Bitmap
     * @param filePath
     * @param sWidth 目标宽
     * @param sHeight 目标高
     */
    private Bitmap resizeBitmap(String filePath,int sWidth,int sHeight){
        //缩放到指定的长宽
        Bitmap mBitmap;
        BitmapFactory.Options options = new BitmapFactory.Options();
        options.inJustDecodeBounds = false;
        mBitmap = BitmapFactory.decodeFile(filePath,options);
        if(mBitmap == null){
            return null;
        }
        int bmpWidth = mBitmap.getWidth();
        int bmpHeight = mBitmap.getHeight();
        // 缩放图片的尺寸
        float scaleWidth = (float) sWidth / bmpWidth; // 按固定大小缩放 sWidth 写多大就多大
        float scaleHeight = (float) sHeight / bmpHeight; //
        Matrix matrix = new Matrix();
    //matrix.postScale(1, -1); //镜像垂直翻转    //matrix.postScale(-1, 1); //镜像水平翻转    //matrix.postRotate(-90); //旋转-90度
matrix.postScale(scaleWidth, scaleHeight);// 产生缩放后的Bitmap对象 Bitmap resizeBitmap = Bitmap.createBitmap(mBitmap, 0, 0, bmpWidth, bmpHeight, matrix, false); mBitmap.recycle(); return resizeBitmap; }

3.bitmap模糊处理

(二)自定义的模糊

(一)高斯模糊

4.bitmap保存图像文件

(一)保存

/**
     * 保存内存中的bitmap到本地文件
     * @param bitmap 要保存的bitmap
     * @param localPath 保存在本地的文件名,绝对路径
     * */
    public static void saveBitmap2File(Bitmap bitmap,String localPath){
        if (bitmap == null) {
            return;
        }
        try {
            File file = new File(localPath);
            FileOutputStream fos = new FileOutputStream(file);
            assert bitmap != null;
            bitmap.compress(Bitmap.CompressFormat.JPEG, 100, fos);
            fos.flush();
            fos.close();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

5.Bitmap的防止内存泄露小方法

(一)生成Bitmap时使用FileDescriptor

/**
     * 由本地文件生成bitmap时,节省内存的方法
     * @param context
     * @param filePath
     * @throws Exception
     */
    private void productBitmap(Context context,String filePath) throws Exception {
        Bitmap des_bitmap = null;
        BitmapFactory.Options options = new BitmapFactory.Options();

        //方法一.本地文件路径
        File file = new File(filePath);
        try {
            FileInputStream is = new FileInputStream(file);
            FileDescriptor fd = is.getFD();
            des_bitmap = BitmapFactory.decodeFileDescriptor(fd,null,options);
            if(iv_bitmap_test!=null) {
                iv_bitmap_test.setImageBitmap(des_bitmap);
            }
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }

        //方法二。
        //不允许网络url,只允许本地绝对路径即file://sdcard//开头
//        String url = "http://itfish.net/Home/Modules/Images/itfish_54346_0.jpg";
//        String url = Environment
//                .getExternalStorageDirectory().getAbsolutePath()
//                + File.separator+"fitmix"+File.separator+"Cover"+File.separator+"137_radio.jpg";
        String url = "file:///sdcard/"+"fitmix"+File.separator+"Cover"+File.separator+"137_radio.jpg";//注意路径
        ParcelFileDescriptor parcelFileDescriptor = context.getContentResolver().openFileDescriptor(Uri.parse(url),"r");
        FileDescriptor fileDescriptor ;
        if(parcelFileDescriptor != null){
            fileDescriptor = parcelFileDescriptor.getFileDescriptor();
        }else{
            fileDescriptor = null;
        }

        options.inJustDecodeBounds = true;
        BitmapFactory.decodeFileDescriptor(fileDescriptor, null, options);

        int inSampleSize = 1;

        if (options.outHeight > 200.0f || options.outWidth > 200.0f) {
            // Calculate the largest inSampleSize value that is a power of 2 and keeps both
            // height and width lower or equal to the requested height and width.
            while ((options.outHeight / inSampleSize) > 200.0f || (options.outWidth / inSampleSize) > 200.0f) {
                inSampleSize *= 2;
            }
        }

        options.inSampleSize = inSampleSize;
        options.inJustDecodeBounds = false;

        Bitmap decodeSampledBitmap = BitmapFactory.decodeFileDescriptor(fileDescriptor, null, options);
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
            parcelFileDescriptor.close();
        }

        iv_bitmap_test.setImageBitmap(decodeSampledBitmap);
    }

5.bitmap原理

时间: 2024-10-25 14:45:33

Bitmap使用的相关文章

WPF笔记整理 - Bitmap和BitmapImage

项目中有图片处理的逻辑,因此要用到Bitmap.而WPF加载的一般都是BitmapImage.这里就需要将BitmapImage转成Bitmap 1. 图片的路径要用这样的,假设图片在project下的Images目录,文件名XXImage.png. pack://application:,,,/xxx;component/Images/XXImage.png 2. 代码: Bitmap bmp = null; var image = new BitmapImage(new Uri(this.X

【Android自学日记】关于Bitmap的理解和使用-不完整版

最近的Android自学刚好学习到异步线程的使用,对于开启异步线程加载网络图片中用到的Bitmap有点小蒙逼,这到底是个啥???所以我就自信的打开了百度!!以下就是我学习到的知识! 百度定义: 位图文件(Bitmap),扩展名可以是.bmp或者.dib.位图是Windows标准格式图形文件,它将图像定义为由点(像素)组成,每个点可以由多种色彩表示,包括2.4.8.16.24和32位色彩.例如,一幅1024×768分辨率的32位真彩图片,其所占存储字节数为:1024×768×32/(8*1024)

bitset bitmap 海量数据处理

bitmap:是一个十分有用的结构.所谓的Bit-map就是用一个bit位来标记某个元素对应的Value, 而Key即是该元素.由于采用了Bit为单位来存储数据,因此在存储空间方面,可以大大节省.      适用范围:可进行数据的快速查找,判重,删除,一般来说数据范围是int的10倍以下 基本原理及要点:使用bit数组来表示某些元素是否存在,比如8位电话号码 扩展:bloom filter可以看做是对bit-map的扩展 问题实例: 1)已知某个文件内包含一些电话号码,每个号码为8位数字,统计不

Android异步加载全解析之Bitmap

Android异步加载全解析之Bitmap 在这篇文章中,我们分析了Android在对大图处理时的一些策略--Android异步加载全解析之大图处理  戳我戳我 那么在这篇中,我们来对图像--Bitmap进行一个更加细致的分析,掌握Bitmap的点点滴滴. 引入 Bitmap这玩意儿号称Android App头号杀手,特别是3.0之前的版本,简直就是皇帝般的存在,碰不得.摔不得.虽然后面的版本Android对Bitmap的管理也进行了一系列的优化,但是它依然是非常难处理的一个东西.在Androi

基于Redis bitmap实现开关配置功能

作者:zhanhailiang 日期:2014-12-21 bitmap api SETBIT key offset value 对key所储存的字符串值,设置或清除指定偏移量上的位(bit). 位的设置或清除取决于value参数,可以是0也可以是1. 当key不存在时,自动生成一个新的字符串值. 字符串会进行伸展(grown)以确保它可以将value保存在指定的偏移量上. 当字符串值进行伸展时,空白位置以0填充. offset参数必须大于或等于0,小于2^32(bit映射被限制在512MB之内

基于Redis bitmap实现签到功能

作者:zhanhailiang 日期:2014-12-21 需求场景 Bitmap 对于一些特定类型的计算非常有效. 假设现在我们希望记录自己网站上的用户的上线频率,比如说,计算用户A上线了多少天,用户B上 线了多少天,诸如此类,以此作为数据,从而决定让哪些用户参加beta测试等活动--这个模式可以使 用SETBIT和BITCOUNT来实现. 比如说,每当用户在某一天上线的时候,我们就使用SETBIT,以用户名作为key,将那天所代表的网站 的上线日作为offset 参数,并将这个offset

Android艺术——Bitmap高效加载和缓存(1)

通过Bitmap我们可以设计一个ImageLoader,实现应该具有的功能是: 图片的同步加载:图片的异步加载:图片的压缩:内存缓存:磁盘缓存:网络获取: 1.加载 首先提到加载:BitmapFactory类提供了四类方法:decodeFile.decodeResource.decodeStream和decideByteArray.分别是文件系统.资源.输入流和字节数加载Bitmap对象. 2.压缩 如何进行图片的压缩?首先我们为什么图片压缩呢?因为很多时候ImageView尺寸小于图片原始尺寸

C# Bitmap类型与Byte[]类型相互转化

Bitmap   =>   byte[] Bitmap b = new Bitmap( "test.bmp "); MemoryStream ms = new MemoryStream(); b.Save(ms,System.Drawing.Imaging.ImageFormat.Bmp); byte[] bytes= ms.GetBuffer(); //byte[] bytes= ms.ToArray(); 这两句都可以,至于区别么,下面有解释 ms.Close(); byte

Bitmap 内存优化

Android在加载大背景图或者大量图片时,经常导致内存溢出(Out of Memory  Error),本文根据我处理这些问题的经历及其它开发者的经验,整理解决方案如下(部分代码及文字出处无法考证):  方案一.读取图片时注意方法的调用,适当压缩  尽量不要使用setImageBitmap或setImageResource或BitmapFactory.decodeResource来设置一张大图,因为这些函数在完成decode后,最终都是通过java层的createBitmap来完成的,需要消耗

Android开发之Bitmap的高效加载

BitmapFactory类提供了四类方法:decodeFile, decodeResource, decodeStream和decodeByteArray 分别用于支持从文件系统,资源,输入流以及字节数组中加载出一个Bitmap对象,前两者又间接调用了decodeStream 为了避免OOM,可以通过采样率有效的加载图片 如果获取采样率? 1.将BitmapFactory.Options的inJustDecodeBounds的参数设置为true并加载图片 2.从BitmapFactory.Op