安卓 - 轮子 - Matisse 图片选择器

作者: 七零八落问号 | 来源:发表于2017-04-26 22:22 被阅读744次

    GitHub地址
    知乎APP开源的一个图片选择器,并内置了两套主题,UI设计基本满足大部分APP需求。

    官方给出来的示例图片
    接入:

    非常简单,只需要在gradle中配置:

    repositories {
        jcenter()
    }
    
    dependencies {
        compile 'com.zhihu.android:matisse:0.4.3'
    }
    

    你还需要在Manifest添加2个权限:

    <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
    <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
    

    在6.0以上的版本时,需要使用动态权限:Android 6.0 运行时权限处理完全解析

    使用:

    使用上也比较方便,官方给出的示例:

    // 配置和启用
    Matisse.from(MainActivity.this)
            .choose(MimeType.allOf())
            .countable(true)
            .maxSelectable(9)
            .addFilter(new GifSizeFilter(320, 320, 5 * Filter.K * Filter.K))
            .gridExpectedSize(getResources().getDimensionPixelSize(R.dimen.grid_expected_size))
            .restrictOrientation(ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED)
            .thumbnailScale(0.85f)
            .imageEngine(new GlideEngine())
            .forResult(REQUEST_CODE_CHOOSE);
    
    // 在Activity或Fragment中接收结果
    List<Uri> mSelected;
    @Override
    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        super.onActivityResult(requestCode, resultCode, data);
        if (requestCode == REQUEST_CODE_CHOOSE && resultCode == RESULT_OK) {
            mSelected = Matisse.obtainResult(data);
            Log.d("Matisse", "mSelected: " + mSelected);
        }
    }
    

    我们慢慢的分析

    /*
     * Start Matisse from an Activity.
     * 需要传入一个Activity作为参数,返回一个Matisse实例,一切的基础
     */
    Matisse.from(MainActivity.this)
    
    /* 
     * 选择图片可选类型,并返回一个SelectionSpecBuilder对象,通过这个对象进行进一步的配置
     * 参数要求为Set<MimeType>,MimeType是一个枚举,包括 JPEG,PNG,GIF 3个类型
     * 作用要注意,这里不是设置显示图片的类型,而是设置可选的图片类型
     * 简单来说,例如这里配置GIF,图片选择器仍然会显示所有类型的图片,但是只有GIF格式的图片是可选的
     * 可以使用MimeType.allOf()允许选择所有格式,也可以使用MimeType.of(MimeType...)限制选择部分格式
     */
    .choose(MimeType.allOf())
    
    /*
     * 当选择图片的时候,图片的右上角是显示普通的“√”,还是显示具体的数字,true则为显示具体数字
     * 显示数字的话,会根据你选择的顺序,将右上角的标识显示为 1,2,3,4...
     */
    .countable(true)
    
    /*
     * 图片选择的最大数量,默认为1(这个1大有深意,我也不知道为什么)
     */
    .maxSelectable(9)
    
    /*
     * 添加过滤器
     * GifSizeFilter是simple里面的一个过滤器示例,
     * 注意这个过滤器的作用,不是用来过滤图片类型的,
     * 而是在选择图片的时候,当图片满足一定情况下,弹出一个提示框,并禁止选择该图片。
     * 如示例的GifSizeFilter,作用是在支持选择GIF的前提下,对宽度或高度不足320,或体积大于5m的GIF图片作出拦截,
     * 当选择符合该特征的图片时,Filter会返回一个带有错误信息的UncapableCause类,其中的信息将会在一个弹出框中显示
     * 总结就是:禁止选择某些指定条件的图片,并告诉用户为什么不能选
     */
    .addFilter(new GifSizeFilter(320, 320, 5 * Filter.K * Filter.K))
    
    /*
     * 设置Grid布局中图片的宽度,但是由于显示的图片布局性质,设置的值不一定会准确执行,但是会接近给出的值
     * 例如屏幕是1000的话,设置300,图片有2种可能
     * 图片宽度250,一行4张图片 / 图片宽度330,一行3张图片
     * 由于宽度330比较接近给出的数值300,图片布局将会使用一行3个的布局
     * 如果以上情况套用到了1200的屏幕宽度的话,自然就会显示为一行4个的布局
     */
    .gridExpectedSize(getResources().getDimensionPixelSize(R.dimen.grid_expected_size))
    
    /*
     * 这个图片选择器Activity的显示方向,默认为竖屏 SCREEN_ORIENTATION_PORTRAIT
     * 通常的参数
     * SCREEN_ORIENTATION_UNSPECIFIED : 由Android系统自己选择合适的方向
     * SCREEN_ORIENTATION_PORTRAIT    : 竖屏
     * SCREEN_ORIENTATION_LANDSCAPE   : 横屏 (由于默认一行3个的布局,不设置gridExpectedSize的话,图片将会无比巨大)
     */
    .restrictOrientation(ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED)
    
    /*
     * 缩略图的压缩值,要求(0.0, 1.0]区间的float参数,默认0.5,既压缩一半
     * 注意框架不会帮你自动修正,设置错误直接就会抛出一个IllegalArgumentException
     */
    .thumbnailScale(0.85f)
    
    /**
     * 关键的一点,设置图片加载引擎,不设置不闪退算我输
     * 参数是一个实现ImageEngine接口的类,官方提供了两个已经实现好的引擎参数:
     * GlideEngine   :使用Glide实现的ImageEngine,内部使用了Glide作为加载框架
     * PicassoEngine :使用Picasso实现的ImageEngine
     * 如果你使用其他框架,或者不使用框架,你需要自行实现一个ImageEngine
     * 总之就是要设置一个imageEngine
     */
    .imageEngine(new GlideEngine())
    
    /* 
     * 配置完成后,调用这个方法就可以进入图片选择框架了
     * 这里的REQUEST_CODE_CHOOSE其实是自定义的RequestCode,在方法内部调用的startActivityForResult使用该参数
     * 通过startActivityForResult跳转到MatisseActivity
     * 配置的参数被保存到了SelectionSpec的InstanceHolder中
     */
    .forResult(REQUEST_CODE_CHOOSE);
    

    由于使用了startActivityForResult启动Activity的方式,接收回调就需要使用onActivityResult()

    List<Uri> mSelected;
    ...
    /*
     * 返回的数据使用了ArrayList<Uri>封装,通过putParcelableArrayListExtra添加到intent,
     * 键为 String EXTRA_RESULT_SELECTION = "extra_result_selection";
     * 或者直接使用Matisse.obtainResult去解析返回的intent,取出List<Uri>的返回值
     */
    mSelected = Matisse.obtainResult(data);
    

    以上就是官方示例的详细解析。

    配置SelectionSpecBuilder余下的其他方法:

    /*
     * 设置Style,官方给出两个主题
     * R.style.Matisse_Zhihu   :知乎的蓝色主题
     * R.style.Matisse_Dracula :上面图片中部黑色一坨(黑中带蓝)的主题
     * 你也可以根据这两个主题去自定义自己的主题
     */ 
    public SelectionSpecBuilder theme(@StyleRes int themeId) 
    
    /*
     * 一个优秀的图片选择框架必然能拍照,这里就是拍照开关了
     * 然后你还需要调用captureStrategy()设置照片信息,不设置不闪退算我又输
     */
    public SelectionSpecBuilder capture(boolean enable)
    
    /*
     * 传入一个CaptureStrategy对象设置拍照的照片信息
     * 这个CaptureStrategy的构造方法要求传入两个值
     * boolean isPublic:是否公开,true的话会把图片存放到ExternalStoragePublicDirectory的PICTURES目录下,
       否则将会放在ExternalFilesDir的PICTURES目录下
     * String authority:用于配置FileProvider(注1),与provider配置中的android:authorities属性保持一致
     */
    public SelectionSpecBuilder captureStrategy(CaptureStrategy captureStrategy)
    
    /*
     * 设置一行图片的数量,设置成5,一行就会显示5张图片,适用于横竖屏
     * 如果设置了gridExpectedSize的话,将会优先使用gridExpectedSize计算出的数量
     * 如果你需要适配横竖屏,可以优先选择设置gridExpectedSize
     */
    public SelectionSpecBuilder spanCount(int spanCount) 
    

    注1:关于FileProvider,可以参考FileProvider共享文件、缓存
    以及可能出现的FileProvider相关 Failed to find configured root that contains

    混淆:

    官方文档上的混淆规则,其实就是当你使用了图片框架时,图片框架自己的混淆规则

    如使用了GlideEngine,就使用了Glide的混淆规则:

    -keep public class * implements com.bumptech.glide.module.GlideModule
    -keep public enum com.bumptech.glide.load.resource.bitmap.ImageHeaderParser$** {
      **[] $VALUES;
      public *;
    }
    
    # for DexGuard only
    -keepresourcexmlelements manifest/application/meta-data@value=GlideModule
    

    使用使用PicassoEngine,则是Picasso的混淆规则:

    -dontwarn com.squareup.okhttp.**
    

    所以,其实可以根据具体的使用情况,进行配置混淆。
    相当于不用写,手动滑稽

    如对你有帮助,欢迎点赞喜欢支持

    相关文章

      网友评论

        本文标题:安卓 - 轮子 - Matisse 图片选择器

        本文链接:https://www.haomeiwen.com/subject/tndwzttx.html