一、html2canvas + jspdf
1、创建一个文件htmlToPdf.js
import html2canvas from 'html2canvas';
import { jsPDF } from 'jspdf';
export function htmlToPdf(selector,title,callback=()=>{}){
document.body.scrollTop = document.documentElement.scrollTop = 0
if (!selector) {
throw new Error('缺少selector')
}
let el = document.querySelector(selector)
if (!el) {
throw new Error('未找到' + selector + '对应的dom节点')
}
html2canvas(el, {
allowTaint:true,
useCORS:true,
dpi: 120, // 图片清晰度问题
background: '#FFFFFF', //如果指定的div没有设置背景色会默认成黑色,这里是个坑
}).then(canvas => {
//未生成pdf的html页面高度
var leftHeight = canvas.height
var a4Width = 190
var a4Height = 277 //A4大小,210mm x 297mm,四边各保留10mm的边距,显示区域190x277
// var a4Width = 595.28
// var a4Height = 841.89 //A4大小,210mm x 297mm,四边各保留10mm的边距,显示区域190x277
//一页pdf显示html页面生成的canvas高度;
var a4HeightRef = Math.floor((canvas.width / a4Width) * a4Height)
//pdf页面偏移
var position = 0
var pageData = canvas.toDataURL('image/jpg', 1.0)
var pdf = new jsPDF('p', 'mm', 'a4') //A4纸,纵向
var index = 1,
canvas1 = document.createElement('canvas'),
height
pdf.setDisplayMode('fullwidth', 'continuous', 'FullScreen')
var pdfName = title
function createImpl(canvas) {
console.log(leftHeight, a4HeightRef)
if (leftHeight > 0) {
index++
var checkCount = 0
if (leftHeight > a4HeightRef) {
var i = position + a4HeightRef
for (i = position + a4HeightRef; i >= position; i--) {
var isWrite = true
for (var j = 0; j < canvas.width; j++) {
var c = canvas.getContext('2d').getImageData(j, i, 1, 1).data
if (c[0] != 0xff || c[1] != 0xff || c[2] != 0xff) {
isWrite = false
break
}
}
if (isWrite) {
checkCount++
if (checkCount >= 10) {
break
}
} else {
checkCount = 0
}
}
height = Math.round(i - position) || Math.min(leftHeight, a4HeightRef)
if (height <= 0) {
height = a4HeightRef
}
} else {
height = leftHeight
}
canvas1.width = canvas.width
canvas1.height = height
console.log(index, 'height:', height, 'pos', position)
var ctx = canvas1.getContext('2d')
ctx.drawImage(
canvas,
0,
position,
canvas.width,
height,
0,
0,
canvas.width,
height,
)
var pageHeight = Math.round((a4Width / canvas.width) * height)
// pdf.setPageSize(null, pageHeight)
if (position != 0) {
pdf.addPage()
}
pdf.addImage(
canvas1.toDataURL('image/jpeg', 1.0),
'JPEG',
10,
10,
a4Width,
(a4Width / canvas1.width) * height,
)
leftHeight -= height
position += height
if (leftHeight > 0) {
setTimeout(createImpl, 30, canvas)
} else {
pdf.save(pdfName + '.pdf')
// console.log(pdf.output('datauristring'))
callback(pdf.output('datauristring'))
}
}
}
//当内容未超过pdf一页显示的范围,无需分页
if (leftHeight < a4HeightRef) {
pdf.addImage(
pageData,
'JPEG',
10,
10,
a4Width,
(a4Width / canvas.width) * leftHeight,
)
pdf.save(pdfName + '.pdf')
// console.log(pdf.output('datauristring'))
callback(pdf.output('datauristring'))
} else {
try {
pdf.deletePage(0)
setTimeout(createImpl, 30, canvas)
} catch (err) {
// console.log(err);
}
}
})
}
2、使用方式
htmlToPdf('#print', 'title', (res) => {
console.log(res)
})