el-image 加载失败解决方案

最近使用elementUI的el-image发现经常会出现加载src失败的情况,问题估计就是el-image的src路径一旦初始化加载失败的话就没有异步刷新:

1.给:src设置默认值,避免图片加载失败的情况

2.加v-if判断:src中的value值是否为空或者:src的key值是否存在,是则加载图片,否则不加载

3.vue项目error方法绑定once,为避免同一个失败链接无限触发error(加载失败后再次请求图片的方法)

<div v-for="(item, index) in imgList" :key="item">
  <el-image :src="item" @error.once="srcerr(item, index)"></el-image>
</div>

定义好的测试数据:

imgList: [
  'http://10.5.4wei1/data/mvtec_ad/grid/train/good/075.png',
  'http://10.5.4che/liwei1/data/mvtec_ad/grid/train/good/207.png'
],
errobj: {}

图片加载失败后触发error的函数:

srcerr(item, index) {
  if (/^err/.test(this.imgList[index])) {
     this.$set(this.imgList, index, this.imgList[index].slice(3))
   } else {
     if (!this.errobj[item]) {
       this.errobj[item] = 1
     } else {
       if (this.errobj[item] > 2) {
         return
       } else {
         this.errobj[item] += 1
       }
     }
     this.$set(this.imgList, index, 'err' + item)
   }
 }

下面注释枯燥乏味,可以不看,直接复制上边代码使用没什么不可以

  1. 首先,图片加载失败后会触发标签绑定error的函数srcerr,srcerr接收到的参数不必解释,必须要传,有用;
  2. /^err/.test(this.imgList[index])(注意这里匹配的不是item,下面你会明白为什么)判断该图片的链接是否以err开头,第一次触发error当然不是了。
  3. 那么执行this.$set(this.imgList, index, ‘err’ + item),当然err是自己拼接上去的,你可以拼接成任何你喜欢的东西只要和真正图片路径开头不一致即可。
  4. List item这时imgList列表更新重新赋值失败图片的src,当然这次一定会再触发error,因为链接上拼接了err
  5. 这次会执行if里的语句this.$set(this.imgList, index, this.imgList[index].slice(3)),把截掉err的链接重新赋值回imgList,imgList更新又赋值链接给图片,到目前为止该图片已经重新请求了一次正确的地址,正常情况下图片会成功渲染。
  6. 但是,万一链接本身是错误的,就像上边imgList里的数据是不可能请求到图片的。。。
  7. 如此,就会陷入循环地狱,once只能对同一个错误拦截,拼接err链接改变了下一次又截取掉了,所以会无限循环下去,之前一切的努力都付之一炬了。。。
  8. 执行报错函数else条件里的判断就是解决这个问题的,,!this.errobj[item]判断data里定义好的errobj对象里是否存在该条链接,不存在则保存在errobj里对应的值为1。
  9. errobj里存在该链接则判断其值,这里条件为大于2则return掉,否则其值加1,这样的话加载失败的链接无论失败多少次(除了首次),都有最多3次请求的机会,超过3次链接不会拼接err,失败的error就不会再触发。
  10. 使用errobj对象保存每条加载失败的链接好处就是无论页面有多少图片加载失败,每一张都还有3次加载的机会,也能解决掉循环地狱的问题。
  11. 如果你的网速超慢,请求3次都不成功,那么可以尝试条件放大点,请求5次10次。如果还失败,建议不要做无谓的挣扎了,毕竟一张图片单独请求10次还不成功,怀疑它是不是图片。

项目中需要展示的图片超多,经常会出现加载失败的情况,记录该问题解决方案。

原文地址:https://www.cnblogs.com/fengxin1998/p/13994333.html