在前面簡(jiǎn)單講述了一下HTML里的Canvas,這次根據(jù)Canvas完成了“海浪效果”(水波上升)。
(O(∩_∩)O哈哈哈~作者我能看這個(gè)動(dòng)畫看一下午)

上升水波.gif
- 動(dòng)畫分析
構(gòu)成:貝塞爾曲線
畫布:Canvas
效果:波浪漲潮(上升、波動(dòng))
觸發(fā)條件:點(diǎn)擊按鈕

貝塞爾曲線.gif
算法實(shí)現(xiàn)分析:從sin()函數(shù)切入,sin()越大波度起伏越大,簡(jiǎn)單說就是通過不斷改變sin()值來實(shí)現(xiàn)海浪效果動(dòng)畫
干貨開始:
1、創(chuàng)建觸發(fā)條件(按鈕)
<button type="button"
onclick="Beisizer()"http://點(diǎn)擊時(shí)觸發(fā)JS事件
onmouseover="bcd()"http://鼠標(biāo)經(jīng)過時(shí)JS事件
onmouseleave="out()"http://鼠標(biāo)離開時(shí)JS事件
id="Anniu">確                     定</button>
2、創(chuàng)建畫布Canvas
<canvas id="Theback"></canvas>
3、創(chuàng)建JS事件(屬性設(shè)置)
//獲取畫布
var beisizer = document.getElementById("Theback");
var ContenofBeisizer = beisizer.getContext("2d");
//設(shè)置波浪海域(海浪寬度,高度)
var beisizerwidth = beisizer.width;
var beisizerheight = beisizer.height;
var beisizerlinewidth = 2;
//曲線
var sinX = 0;
var sinY = beisizerheight/2.0;
//軸長(zhǎng)
var axisLenght = beisizerwidth;
//弧度寬度
var waveWidth = 0.014;
//海浪高度
var waveHeight = beisizerheight / 15.0;
ContenofBeisizer.lineWidth = beisizerlinewidth;
4、畫貝塞爾曲線
var drawSin = function (xofspeed) {
ContenofBeisizer.save();
//存放貝塞爾曲線的各個(gè)點(diǎn)
var points = [];
ContenofBeisizer.beginPath();
//創(chuàng)建貝塞爾點(diǎn)
for (var x = sinX;x < sinX +axisLenght;x+=80/axisLenght){
// var y = -Math.sin((sinX+x)*waveWidth); 測(cè)試請(qǐng)解開注釋,注釋下一行
var y = -Math.sin((sinX+x)*waveWidth+xofspeed);
// points.push([x,sinY + y * waveHeight]); 測(cè)試請(qǐng)解開注釋,注釋下一行
points.push([x,rand+y*waveHeight]);
// ContenofBeisizer.lineTo(x,sinY + y * waveHeight); 測(cè)試請(qǐng)解開注釋,注釋下一行
ContenofBeisizer.lineTo(x,rand + y * waveHeight);
}
ContenofBeisizer.lineTo(axisLenght,beisizerheight);
ContenofBeisizer.lineTo(sinX,beisizerheight);
ContenofBeisizer.lineTo(points[0][0],points[0][1]);
ContenofBeisizer.stroke();
ContenofBeisizer.restore();
//貝塞爾曲線樣式設(shè)置
ContenofBeisizer.strokeStyle = "#3bc777";
ContenofBeisizer.fillStyle = "#3bc777";
ContenofBeisizer.fill();
};
這一段代碼已經(jīng)完成靜態(tài)貝賽爾曲線的繪制了,可以通過解開以下語句嘗試運(yùn)行看下效果。
var y = -Math.sin((sinX+x)*waveWidth);
points.push([x,rand+y*waveHeight]);
var y = -Math.sin((sinX+x)*waveWidth+xofspeed);
運(yùn)行方法執(zhí)行 drawSin()

靜態(tài)貝塞爾曲線.png
5、海浪效果的實(shí)現(xiàn)
需要在屬性中加入一下代碼進(jìn)行速率的設(shè)置
var speed = 0.1; 數(shù)值越大速率越快
var xofspeed = 0; 波浪橫向的偏移量
var rand = beisizerheight;波浪高度
var rendY = function () {
ContenofBeisizer.clearRect(0,0,beisizerwidth,beisizerheight);
//控制海浪高度
var tmp = 0.1;
rand-=tmp;
var b = beisizerheight - rand;
//控制循環(huán)漲潮
if (parseInt(b)==beisizerheight){
rand = beisizerheight;
}
drawSin(xofspeed);
drawSinl(xofspeed);
xofspeed += speed;
requestAnimationFrame(rendY);
};
通過調(diào)用自身產(chǎn)生不同的高度,來產(chǎn)生海浪效果。這里設(shè)置的屬性值配合第四步畫貝塞爾曲線一起進(jìn)行理解。
運(yùn)行方式 rendY();
總結(jié)
貝賽爾曲線也可以制作音波,心跳儀等??梢試L試改變頻率值來實(shí)現(xiàn)。