canvas把多张图片拼成长图
最近看到一个用canvas实现给图片加水印的文章,学习了之后做了个把多张图片拼成长图的功能。
需要了解的知识点:
步骤是:
- 用
<input type="file">来选择本地文件 - 用
FileReader的readAsDataURL来拿到作为图片src的dataURL - 把图片实例化,然后画在
canvas中 - 用
HTMLCanvasElement.toDataURL()拿到拼好的图的dataURL
完整代码如下。
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>拼长图</title>
</head>
<body>
<input id="upload-input" type="file" accept="image/*" multiple="multiple" style="display: none;">
<label for="upload-input">点击选择图片</label>
<div id="image-container"></div>
<script>
// 拼出来的图片的宽度
const width = 300
// 拼出来的图片的质量,0-1之间,越大质量越好
const encoderOptions = 0.5
const uploadInput = document.getElementById('upload-input')
const imageDiv = document.getElementById('image-container')
uploadInput.addEventListener('change', event => {
const files = Array.from(event.target.files)
filesToInstances(files, instances => {
drawImages(instances, finalImageUrl => {
imageDiv.innerHTML = `<div><a download href=${finalImageUrl}>点击下载</a><br><img src=${finalImageUrl}></div>`
})
})
})
// 根据图片文件拿到图片实例
const filesToInstances = (files, callback) => {
const length = files.length
let instances = []
let finished = 0
files.forEach((file, index) => {
const reader = new FileReader()
// 把文件读为 dataUrl
reader.readAsDataURL(file)
reader.onload = e => {
const image = new Image()
image.src = e.target.result
image.onload = () => {
// 图片实例化成功后存起来
instances[index] = image
finished ++
if (finished === length) {
callback(instances)
}
}
}
})
}
// 拼图
const drawImages = (images, callback) => {
const heights = images.map(item => width / item.width * item.height)
const canvas = document.createElement('canvas')
canvas.width = width
canvas.height = heights.reduce((total, current) => total + current)
const context = canvas.getContext('2d')
let y = 0
images.forEach((item, index) => {
const height = heights[index]
context.drawImage(item, 0, y, width, height)
y += height
})
callback(canvas.toDataURL('image/jpeg', encoderOptions))
}
</script>
</body>
</html>还有许多别的canvas处理图片的应用场景,感兴趣的可以自行搜索。
完。
相关推荐
northwindx 2020-05-31
xdyangxiaoromg 2020-03-27
大地飞鸿 2020-11-12
星星有所不知 2020-10-12
jinxiutong 2020-07-26
MIKUScallion 2020-07-05
songfens 2020-07-05
songfens 2020-06-11
songfens 2020-06-08
northwindx 2020-05-31
northwindx 2020-05-27
northwindx 2020-05-25
MIKUScallion 2020-05-25
jinxiutong 2020-05-10
xdyangxiaoromg 2020-05-10
大地飞鸿 2020-05-06