zoukankan      html  css  js  c++  java
  • canvas动画—圆形扩散、运动轨迹

    介绍

    在ECharts中看到过这种圆形扩散效果,类似css3,刚好项目中想把它用上,but我又不想引入整个echart.js文件,更重要的是想弄明白它的原理,所以自己动手。在这篇文章中我们就来分析实现这种效果的两种方法,先上效果图:
    圆形扩散

    实现原理

    通过不断的改变圆的半径大小,不断重叠达到运动的效果,在运动的过程中,设置当前canvas的透明度context.globalAlpha=0.95,使得canvas上的圆逐渐透明直至为0,从而实现这种扩散、渐变的效果。

    实现方法一

    1. 关键技术点
    context.globalAlpha = 0.95; //设置主canvas的绘制透明度。
    创建临时canvas来缓存主canas的历史图像,再叠加到主canvas上。

    2. 绘制过程
    首先,我们先来写一个绘制圆的方法:

    //画圆
    var drawCircle = function() {
        context.beginPath();
        context.arc(150, 100, radius, 0, Math.PI * 2);
        context.closePath();
        context.lineWidth = 2; //线条宽度
        context.strokeStyle = 'rgba(250,250,50,1)'; //颜色
        context.stroke();
        radius += 0.5; //每一帧半径增加0.5
    
        //半径radius大于30时,重置为0
        if (radius > 30) {
            radius = 0;
        }
    };

    然后,我们创建一个临时canvas用来缓存主canvas上的历史图像,设置主canvas的透明度context.globalAlpha=0.95(关键一步),在每次调用drawCircle方法绘制一个新圆之前都把主canvas上的图像,也就是之前的图像给绘制到临时的canvas中,等到drawCircle方法绘制完新圆后,再把临时canvas的图像绘制回主canvas中。

    绘制流程

    核心代码如下:

    //创建一个临时canvas来缓存主canvas的历史图像
    var backCanvas = document.createElement('canvas'),
        backCtx = backCanvas.getContext('2d');
        backCanvas.width = width;
        backCanvas.height = height;
    
        //设置主canvas的绘制透明度
        context.globalAlpha = 0.95;
    
        //显示即将绘制的图像,忽略临时canvas中已存在的图像
        backCtx.globalCompositeOperation = 'copy';
    
    var render = function() {
        //1.先将主canvas的图像缓存到临时canvas中
        backCtx.drawImage(canvas, 0, 0, width, height);
    
        //2.清除主canvas上的图像
        context.clearRect(0, 0, width, height);
    
        //3.在主canvas上画新圆
        drawCircle();
    
        //4.等新圆画完后,再把临时canvas的图像绘制回主canvas中
        context.drawImage(backCanvas, 0, 0, width, height);
    };

    实现方法二

    与上一种方法相比,这种方法更加简单,同样是用到了透明度逐渐减小直到为0的原理,不同的是这里并没有创建临时canvas,而是运用了context.globalCompositeOperation属性值source-overdestination-in来配合使用,查看globalCompositeOperation属性介绍

    核心代码如下:

    var render = function() {
        //默认值为source-over
        var prev = context.globalCompositeOperation;
    
        //只显示canvas上原图像的重叠部分
        context.globalCompositeOperation = 'destination-in';
    
        //设置主canvas的绘制透明度
        context.globalAlpha = 0.95;
    
        //这一步目的是将canvas上的图像变的透明
        context.fillRect(0, 0, width, height);
    
        //在原图像上重叠新图像
        context.globalCompositeOperation = prev;
    
        //在主canvas上画新圆
        drawCircle();
    };

    地图上的应用

    这里我采用的是第二种方式,将扩散、渐变效果运用到了百度地图上,感觉还比较炫,查看更多demo

    圆形扩散动画
    百度地图圆形扩散

    运动轨迹动画
    百度地图运动轨迹动画

    总结

    方法一、二都能实现同样的效果,如果动画绘制、操作canvas比较频繁,建议采用第一种方式,用临时canvas来缓存历史图像,效率更高。

  • 相关阅读:
    Mac下的类似apt-get的包管理工具Homebrew(笔记)
    C# 通过模拟http请求来调用soap、wsdl
    提高 ASP.NET Web 应用性能
    Ajax ContentType 列表大全
    关于多核游览器指定渲染内核的方法。
    Aspx页面模拟WebService功能
    Dapper完美兼容Oracle,执行存储过程,并返回结果集。
    简单爬虫,突破IP访问限制和复杂验证码,小总结
    在子线程中创建新的窗体,遇到的问题。
    【干货】jsMind思维导图整合Easyui的右键菜单
  • 原文地址:https://www.cnblogs.com/10manongit/p/12904077.html
Copyright © 2011-2022 走看看