移動端 html2canvas 踩坑記錄

背景

最近在作的微信 html5 項目有個需求:頁面包含 一張大的背景圖片 + 一個用戶的連接二維碼圖片 拼成一張圖片,讓用戶長按保存的時候,能夠把整個頁面都保存起來,而不是隻保存二維碼。php

思考

1.先後端哪一個實現方法會更高效html

雖然圖片均可以從後臺獲取,可是一來須要 等待二維碼生成->添加到大圖上->轉換成一張圖片->傳輸,是一個同步過程,耗時比較久;二來看到網上的評價,後臺使用的庫生成的圖片偶爾會出錯,修改起來也麻煩。所以決定在前端完成。前端

2.使用 svg 仍是 canvasvue

考慮到移動端對 html5 新特性支持得比較好以及高分辨率屏幕,使用 svg 看起來很適合------若是沒看到前輩的踩坑文章的話,會是這樣的~~html5

根據 https://www.jianshu.com/p/458... 所說,步驟是 html-->svg-->canvas-->img ,問題出在使用跨域圖片的時候:canvas

clipboard.png

也便是 iphone 系列都被拒之門外 ...後端

所以決定用 html2canvas 庫,完成 html-->canvas-->img 的轉變。如下是踩坑心得。跨域


坑一

圖片模糊微信

此爲想不到的坑,浪費了不少時間在代碼檢查上...app

圖片描述

問題: html2canvas 渲染背景圖片 background-image 會不清晰。

解決方法:使用 Img 標籤。

坑二

高分辨率下,文字模糊

此爲預料中的狀況,獲取了設備像素比 window.devicePixelRatio 百分比伸展 canvas 畫布便可......纔怪......

而後發現這是 0.5 版本須要作的操做,1.0 版本的默認參數 scale 已經設置好了,但仍是不太清晰。

最後從同事處獲得啓發,最終解決方法是!!

一概設爲 4 倍!即

html2canvas(ele, {
    sacle: 4
}).then((canvas) => {});

簡單粗暴...雖然圖片體積所以變大了...

坑三

IOS 下,機率性出現大圖繪製不出來的狀況

對於這個需求,本來的操做是在 img 標籤裏的 src 屬性寫上大圖連接,在 activated() 裏生成二維碼再建立新的 img 標籤附到大圖裏(用的 vue)。在 IOS 上,常常出現頁面上只有背景顏色和二維碼的圖片的狀況。

緣由: 大圖還未下載完畢即開始了繪製。

解決方法: 給 img 添加 onload 事件,下載完畢再調用繪製方法。

坑四

html 元素的隱藏

由於是要讓用戶長按保存整個頁面,因此用 html2canvas 將全部內容轉成圖片。而其並不能繪製隱藏的內容,所以須要先顯示頁面,在圖片生成後再隱藏。在 vue 裏就是 v-show 的值的變化過程。

問題: 頁面會有閃爍,再顯示圖片

解決方法: 組件直接設爲 v-show = false,html2canvas 添加參數 onclone ,生成一個複製的虛擬組件,設置爲顯示,便可獲取進行繪製,且虛擬組件不會顯示在頁面上。

html2canvas(ele, {
    onclone(doc) {
        let e = doc.querySelector('#wrapper');
        e.style.display = 'block';
    }
}).then((canvas) => {});

其餘坑

圖片高度

問題: UI 只給了一張圖片,寬度能夠稍微拉伸,高度在全面屏下會不足以覆蓋整個屏幕,漏出白底;強制設置爲屏幕高度圖片會失真。

解決方法: 讓 UI 幫忙別把圖片底部設計得五光十色,只保留一種顏色。而後將頁面的背景顏色設爲同種顏色便可。

二維碼圖片的位置定位

問題: 如何讓二維碼圖片在不一樣屏幕下都定位到正確的位置。

解決方法: 設爲絕對定位,使用屏幕寬度做爲基準設置 left、top 值。

.qr {
    width: 32vw;
    position: absolute;
    left: 16vw;
    top: 97vw;
}

圖片跨域等

其餘更多相似圖片跨域等問題能夠參考如下兩篇文章:

http://www.php-master.com/pos...

https://www.jianshu.com/p/458...

相關文章
相關標籤/搜索