H5在Canvas中实现自定义途径动画-
在比来的项目中笔者需要做一个新需求:在canvas中实现自定义的途径动画。这里所谓的自定义途径不单单包含一条直线,或许是多条直线的运动组合,甚至还包括了贝塞尔曲线,因而,这个动画或许是下面这个模样的:
那么怎样才干在canvas中实现这种动画结果呢?其实很简略,关于途径的处置svg非常在行,因而在canvas中实现自定义途径动画,我们需要借助svg的力量。
新建Path
制作动画前,先要拿到动画的途径,对此我们可以直接运用svg的path定义法则,比方我们定义了一条较为复杂的途径(它到底长什么样大家可以本人试试,这里就不展现了),然后,我们需要将定义好的途径导入进一个新生成的path元素中(我们只是借助svg的api,因而并不需要将其插到页面内)
const path = 'M0,0 C8,33.90861 25.90861,16 48,16 C70.09139,16 88,33.90861 88,56 C88,78.09139 105.90861,92 128,92 C150.09139,92 160,72 160,56 C160,40 148,24 128,24 C108,24 96,40 96,56 C96,72 105.90861,92 128,92 C154,93 168,78 168,56 C168,33.90861 185.90861,16 208,16 C230.09139,16 248,33.90861 248,56 C248,78.09139 230.09139,96 208,96 L48,96 C25.90861,96 8,78.09139 8,56 Z'; const pathElement = document.createElementNS('http://www.w3.org/2000/svg',"path"); pathElement.setAttributeNS(null, 'd', path);
getTotalLength与getPointAtLength
SVGPathElement供给的这两个api很关键,可以说它是实现途径动画的最为中心的地方(在svg内实现自定义途径动画个别也是通过这两个api去解决)详情请戳:SVGPathElement MDN
getTotalLength办法可以猎取SVGPathElement的总长度
getPointAtLength办法,传入一个长度x,将返回距离SVGPathElement起点的长度为x的终点坐标。
应用这两个api,通过轮回的方式一直去更新canvas内所绘制的图形坐标,即可实现途径动画:
const length = pathElement.getTotalLength(); const duration = 1000; // 动画总时长 const interval = length / duration; const canvas = document.querySelector('canvas'); const context = canvas.getContext('2d'); let time = 0, step = 0; const timer = setInterval(function() { if (time <= duration) { const x = parseInt(pathElement.getPointAtLength(step).x); const y = parseInt(pathElement.getPointAtLength(step).y); move(x, y); // 更新canvas所绘制图形的坐标 step++; } else { clearInterval(timer) } }, interval); function move(x, y) { context.clearRect(0, 0, canvas.width, canvas.height); context.beginPath(); context.arc(x, y, 25, 0, Math.PI*2, true); context.fillStyle = '#f0f'; context.fill(); context.closePath(); }
最后,我们把它封装一下,即可实现一个在canvas中实现自定义动画的简易函数啦:
function customizePath(path, func) { const pathElement = document.createElementNS('http://www.w3.org/2000/svg',"path"); pathElement.setAttributeNS(null, 'd', path); const length = pathElement.getTotalLength(); const duration = 1000; const interval = length / duration; let time = 0, step = 0; const timer = setInterval(function() { if (time <= duration) { const x = parseInt(pathElement.getPointAtLength(step).x); const y = parseInt(pathElement.getPointAtLength(step).y); func(x, y); step++; } else { clearInterval(timer) } }, interval); } const path = 'M0,0 C8,33.90861 25.90861,16 48,16 C70.09139,16 88,33.90861 88,56 C88,78.09139 105.90861,92 128,92 C150.09139,92 160,72 160,56 C160,40 148,24 128,24 C108,24 96,40 96,56 C96,72 105.90861,92 128,92 C154,93 168,78 168,56 C168,33.90861 185.90861,16 208,16 C230.09139,16 248,33.90861 248,56 C248,78.09139 230.09139,96 208,96 L48,96 C25.90861,96 8,78.09139 8,56 Z'; const canvas = document.querySelector('canvas'); const context = canvas.getContext('2d'); function move(x, y) { context.clearRect(0, 0, canvas.width, canvas.height); context.beginPath(); context.arc(x, y, 25, 0, Math.PI*2, true); context.fillStyle = '#f0f'; context.fill(); context.closePath(); } customizePath(path, move);
实现思绪大致如上所述,然而这并不是终究成果。当我们决议要在canvas制作自定义途径动画时,我们不仅要考虑怎样实现,更要考虑机能优化,比方在这个实现思绪中,我们可否可以减少无须要的渲染次数?帧率怎样控制达到最优?等等。
虽然它们并不在这篇文章的计议范畴中,当也应该值得我们思索。
信赖看了本案牍例你已经把握了办法,更多出色请关注 百分百源码网 其它相干文章!
举荐浏览:
H5的Drag与Drop详解
运用canvas实现视频里的弹幕结果
以上就是H5在Canvas中实现自定义途径动画的细致内容,更多请关注 百分百源码网 其它相干文章!