android递归压缩上传多张图片到七牛的实例代码

所属分类: 软件编程 / Android 阅读数: 61
收藏 0 赞 0 分享

最近遇到这样一个需求:要做一个仿微信朋友圈的功能,要求上传最多九张图到七牛。七牛有上传图片的接口,但是每次只能上传一张。如果是九张图片一齐上传,使用for循环的话肯定不行的,很容易出错。因为上传七牛的动作是在子线程完成的,for循环是在主线程的,这就相当于同时开启十个子线程来上传图片,而且都是耗时线程,很容易会ANR的。

最好的解决办法应该是先压缩图片,在200k-300k之间,保证图片不失真,然后一张一张上传,通过七牛的回调,来判断上一张图片是否上传完成,上传完成了,再上传下一张图片。

好了,话不多说,贴代码:

1.压缩图片

/**
   * 质量压缩法
   *
   * @param image
   * @return
   */
  public byte[] compressImage(Bitmap image) {
    ByteArrayOutputStream baos = new ByteArrayOutputStream();
    image.compress(Bitmap.CompressFormat.JPEG, 100, baos);//质量压缩方法,这里100表示不压缩,把压缩后的数据存放到baos中
    int options = 100;
    while (baos.toByteArray().length / 1024 > 250) { //循环判断如果压缩后图片是否大于100kb,大于继续压缩
      baos.reset();//重置baos即清空baos
      image.compress(Bitmap.CompressFormat.JPEG, options, baos);//这里压缩options%,把压缩后的数据存放到baos中
      options -= 10;//每次都减少10
      if (options <= 10) {
        break;
      }
    }
    byte[] byteArray = baos.toByteArray();
    try {
      if (baos != null) {
        baos.close();
      }
    } catch (IOException e) {
      e.printStackTrace();
    }
    return byteArray;
  }

这个之前是压缩到100k的,这个没有按比例压缩,有的图片尺寸比较大的会模糊,所以现在调整到250k,估计压缩的图片大小会在200-300k左右吧。

2.递归上传图片

/**
   * 递归上传图片主要方法
   * @param picUrl 图片的本地路径
   * @param picSize 上传图片总数量
   *        //picNum是计数器,用于计算已上传图片的数目
   *        //snplMomentAddPhotos.getData().get(picNum)是选择图片的开源库,返回一个ArrayList<String>类型的图片路径
   *        BitmapUnit.getInstance().compressImage(BitmapUnit.getInstance().getBItmap(picUrl))//压缩图片
   *        
   */
  private void upPic(String picUrl, int picSize) {
    //根据七牛上传图片的api,封装的上传方法
    QiniuUtils.getInstance().uploadSmallFile(BitmapUnit.getInstance().
            compressImage(BitmapUnit.getInstance().getBItmap(picUrl)),
        url -> {
          //图片成功上传到七牛时回调
          //当前完成上传的图片数量小于总图片数量的时候重新调用该方法递归
          if (picNum < picSize) {
            upPic(snplMomentAddPhotos.getData().get(picNum), picSize);
            Contants.upPicStatus = 1;
            if (loadingDialog != null) {
              loadingDialog.loadingStatus((picNum + 1) + "/" + picSize + "张图片");
            }
            //拼接字符串
            if (TextUtils.isEmpty(picUrls)) {
              picUrls = url;
            } else {
              picUrls = picUrls + "," + url;
            }
          }else {
          //结束递归
            if (loadingDialog != null) {
              loadingDialog.dismiss();
            }
            Contants.upPicStatus = 200;
            WorkManger.getInstance().publishWOrk("1", mClassTimetablesId,
                tvTitle.getText().toString(), etName.getText().toString(), picUrls, mCourseId);
          }
          picNum++;//添加计数器,这个要放到最后,不然会数组角标溢出
        });
  }

这个代码不难看懂,具体的都写在注释里面了,有一些是项目里面用到的,各位看官只要明确在哪里调用方法进行递归和在哪里添加计数器,在哪里结束递归就可以了。

但是这个方法有一点小瑕疵,正常我们在上传图片的过程中,都要有加载进度条,我发现加载进度条在每次上传成功的时候都会稍微卡一下。初步推断是因为压缩图片引起的,压缩图片的时候也是比较耗能的,而且同在主线程,会引起卡顿。提出的解决方案是:把图片压缩部分提出来,放在子线程中,先压缩图片,然后在同意上传。不过还没来的及优化,当然各位如果有什么好的想法,请提出来。感激不尽。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持脚本之家。

更多精彩内容其他人还在看

Android样式和主题之选择器的实例讲解

今天小编就为大家分享一篇关于Android样式和主题之选择器的实例讲解,小编觉得内容挺不错的,现在分享给大家,具有很好的参考价值,需要的朋友一起跟随小编来看看吧
收藏 0 赞 0 分享

Android应用动态修改主题的方法示例

今天小编就为大家分享一篇关于Android应用动态修改主题的方法示例,小编觉得内容挺不错的,现在分享给大家,具有很好的参考价值,需要的朋友一起跟随小编来看看吧
收藏 0 赞 0 分享

Flutter 网络请求框架封装详解

这篇文章主要介绍了Flutter 网络请求框架封装详解,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
收藏 0 赞 0 分享

Flutter倒计时/计时器的实现代码

这篇文章主要介绍了Flutter倒计时/计时器的实现代码,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
收藏 0 赞 0 分享

Android使用google breakpad捕获分析native cash

这篇文章主要介绍了Android使用google breakpad捕获分析native cash 的相关知识,非常不错,具有一定的参考借鉴价值,需要的朋友可以参考下
收藏 0 赞 0 分享

详解Flutter WebView与JS互相调用简易指南

这篇文章主要介绍了详解Flutter WebView与JS互相调用简易指南,分为JS调用Flutter和Flutter调用JS,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
收藏 0 赞 0 分享

Android开发实现ListView和adapter配合显示图片和文字列表功能示例

这篇文章主要介绍了Android开发实现ListView和adapter配合显示图片和文字列表功能,涉及Android使用ListView结合adapter适配器实现图文显示功能相关的布局、解析、权限控制等操作技巧,需要的朋友可以参考下
收藏 0 赞 0 分享

Android文字基线Baseline算法的使用讲解

今天小编就为大家分享一篇关于Android文字基线Baseline算法的使用讲解,小编觉得内容挺不错的,现在分享给大家,具有很好的参考价值,需要的朋友一起跟随小编来看看吧
收藏 0 赞 0 分享

Flutter自定义实现神奇动效的卡片切换视图的示例代码

这篇文章主要介绍了Flutter自定义实现神奇动效的卡片切换视图的示例代码,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
收藏 0 赞 0 分享

Android实现自定义滑动刻度尺方法示例

这篇文章主要给大家介绍了关于Android实现自定义滑动刻度尺的相关资料,文中通过示例代码介绍的非常详细,对各位Android开发者们具有一定的参考学习价值,需要的朋友们下面来一起学习学习吧
收藏 0 赞 0 分享
查看更多