圖片加載失敗解決方案 以及canvas即時生成提示圖片

目前項目碰到一個問題,有時後臺給的圖片路徑會有404,原來的方案是添加一個onerror把地址重指向一個404的本地默認地址。 可是問題是在於若是默認地址也404.就會形成無限加載vue

因爲項目用的是vue開發,在vue中有一個once的修飾符,我們先來試試這個辦法canvas

看樣子是能夠的,也沒有循環調用,可是這樣不行!項目onerror太多了一個個替換位置太麻煩(懶得義正詞嚴),咱嘗試給它封裝個方法。數組

在main註冊全局方法(原型鏈掛載),而後img調用app

而後就發現不行的,在一番debug以後才發現果真js基礎仍是不夠,在函數內部去改變原參數的指針這樣是不行的,這個函數只能改變url的指針而不能改變intInf.logo的指針,因此這樣是沒用的,那麼怎麼辦呢?改造一下吧:函數

這樣就ok啦,這個其實也不用函數的,不過這樣看上去會好點的樣子。this

可是!我還有一個想法,若是error返回一個即時生成的圖像,是否是就不會有循環請求圖片的問題了。 try try:url

ok,這就算完成了,頁面也顯示正常spa

可是有一些問題,每次error就要從新繪圖煩不煩啊,已經畫過的能夠不能夠找地方存着等須要的時候直接用呢, 因而我改良了一下:

可是還有問題,目前是能夠繪製圖片了,繪製的圖片畢竟美觀度欠佳,萬一要添加已有圖片的地址呢?可是若是該地址又404怎麼辦?因而我又改良了一下下:prototype

完事,到此問題算是解決了。debug

Vue.prototype.imgError = function (name,url,str) {//name是替換的地址名稱,url爲默認加載錯誤圖片的地址,str爲生成圖片的提示語(10字以內)
  if(typeof name !==String){
    for (let key in this){
      if(name===this[key]){
        name=key+'';
        break
      }
    }
  }
  str=str||"圖片加載錯誤"
  window.errorImgUrl= window.errorImgUrl||[];
  window.errorImgUrl.push(event.target.src);//錯誤的地址再也不獲取第二次
  url=isErrorImg(url)?false:url
  this[name]=url||generateImg(str);
  //獲取默認圖片
  function generateImg(str){
    window.imgErrorStr= window.imgErrorStr||[];//全部的提示詞數組
    window.imgErrorDataURI= window.imgErrorDataURI||[];//全部已經生成過的圖像
    if(window.imgErrorStr.includes(str)){//該提示詞的圖像是否生成過
        return window.imgErrorDataURI[window.imgErrorStr.indexOf(str)]
    }else{
        return Mapping(str);
    }
  }
  //繪製默認圖片
  function Mapping(str){
    var canvas=document.createElement('canvas')
    canvas.width=200;
    canvas.height=200;
    var  context = canvas.getContext('2d');
    context.font="Bold 20px Arial";
    context.fillText(str,(200-str.length*20)/2,90);	
    context.lineWidth =2; //設置線寬
    context.strokeStyle='rgb(100,180,120)';
    context.beginPath(); //路徑開始
    context.moveTo(0,0);
    context.lineTo(0,200);
    context.lineTo(200,200);
    context.lineTo(200,0);
    context.lineTo(0,0);
    context.stroke();
    var strDataURI=canvas.toDataURL("image/png"); 
    window.imgErrorStr.push(str);
    window.imgErrorDataURI.push(strDataURI);
    return strDataURI;
  }
  function isErrorImg(url){//該地址是否錯誤的地址
    for(let i in window.errorImgUrl){
      if(window.errorImgUrl[i].indexOf(url)>=0){
        return true;
      }
    }
    return false;
  }
};複製代碼
相關文章
相關標籤/搜索