今天開始,我們就要征戰(zhàn)路徑最后也是最難的部分了——高級(jí)路徑。之前我們學(xué)習(xí)的都是繪制線條(基本路徑),接下來的四節(jié)課我們詳細(xì)看看繪制曲線(高級(jí)路徑)的有關(guān)方法。
劇透一下,主要有四個(gè)方法:
arc()quadraticCurveTo()bezierCurveTo()在開始之前,我們優(yōu)化一下我們的作圖環(huán)境。靈感來自于上節(jié)課的紋理,如果不喜歡這個(gè)背景,我在images目錄下還提供了其他的背景圖,供大家選擇。另外把所有的樣式表都寫在了<head>下。
<!DOCTYPE html>
<html lang="zh">
<head>
<meta charset="UTF-8">
<title>新的畫布</title>
<style>
body { background: url("./images/bg3.jpg") repeat; }
#canvas { border: 1px solid #aaaaaa; display: block; margin: 50px auto; }
</style>
</head>
<body>
<div id="canvas-warp">
<canvas id="canvas">
你的瀏覽器居然不支持Canvas?!趕快換一個(gè)吧??!
</canvas>
</div>
<script>
window.onload = function(){
var canvas = document.getElementById("canvas");
canvas.width = 800;
canvas.height = 600;
var context = canvas.getContext("2d");
context.fillStyle = "#FFF";
context.fillRect(0,0,800,600);
}
</script>
</body>
</html>
運(yùn)行結(jié)果:

之所以要繪制一個(gè)空白的矩形填滿畫布,是因?yàn)槲覀冎罢f過,canvas是透明的,如果不設(shè)置背景色,那么它就會(huì)被我設(shè)置的<body>紋理所覆蓋,想要使其擁有背景色(白色),只有繪制矩形覆蓋canvas這一個(gè)方法。
怎么樣,是不是非常的酷?
arc()繪制圓弧arc()的使用方法如下:
context.arc(x,y,radius,startAngle,endAngle,anticlockwise)
前面三個(gè)參數(shù),分別是圓心坐標(biāo)與圓半徑。startAngle、endAngle使用的是弧度值,不是角度值。弧度的規(guī)定是絕對(duì)的,如下圖。

anticlockwise表示繪制的方法,是順時(shí)針還是逆時(shí)針繪制。它傳入布爾值,true表示逆時(shí)針繪制,false表示順時(shí)針繪制,缺省值為false。
弧度的規(guī)定是絕對(duì)的,什么意思呢?就是指你要繪制什么樣的圓弧,弧度直接按上面的那個(gè)標(biāo)準(zhǔn)填就行了。
比如你繪制 0.5pi ~ 1pi 的圓弧,如果順時(shí)針畫,就只是左下角那1/4個(gè)圓??;如果逆時(shí)針畫,就是與之互補(bǔ)的右上角的3/4圓弧。此處自己嘗試,不再舉例。
下面,我們結(jié)合基本路徑和高級(jí)路徑的知識(shí),繪制一個(gè)圓角矩形。
圓角矩形是由四段線條和四個(gè)1/4圓弧組成,拆解如下。

因?yàn)槲覀円獙懙氖呛瘮?shù)而不是一個(gè)固定的圓角矩形,所以這里列出的是函數(shù)需要的參數(shù)。分析好之后,直接敲出代碼。
<!DOCTYPE html>
<html lang="zh">
<head>
<meta charset="UTF-8">
<title>圓角矩形</title>
<style>
body { background: url("./images/bg3.jpg") repeat; }
#canvas { border: 1px solid #aaaaaa; display: block; margin: 50px auto; }
</style>
</head>
<body>
<div id="canvas-warp">
<canvas id="canvas">
你的瀏覽器居然不支持Canvas?!趕快換一個(gè)吧?。? </canvas>
</div>
<script>
window.onload = function(){
var canvas = document.getElementById("canvas");
canvas.width = 800;
canvas.height = 600;
var context = canvas.getContext("2d");
context.fillStyle = "#FFF";
context.fillRect(0,0,800,600);
drawRoundRect(context, 200, 100, 400, 400, 50);
context.strokeStyle = "#0078AA";
context.stroke();
}
function drawRoundRect(cxt, x, y, width, height, radius){
cxt.beginPath();
cxt.arc(x + radius, y + radius, radius, Math.PI, Math.PI * 3 / 2);
cxt.lineTo(width - radius + x, y);
cxt.arc(width - radius + x, radius + y, radius, Math.PI * 3 / 2, Math.PI * 2);
cxt.lineTo(width + x, height + y - radius);
cxt.arc(width - radius + x, height - radius + y, radius, 0, Math.PI * 1 / 2);
cxt.lineTo(radius + x, height +y);
cxt.arc(radius + x, height - radius + y, radius, Math.PI * 1 / 2, Math.PI);
cxt.closePath();
}
</script>
</body>
</html>
運(yùn)行結(jié)果:

建議大家自己動(dòng)手繪制一個(gè)圓角矩形,這樣有助于對(duì)路徑的掌握。
下面我們用這個(gè)函數(shù)來做點(diǎn)其他的事情。
對(duì)代碼不做過多講解,大家自己研究研究,建議自己動(dòng)手先嘗試寫一下。因?yàn)槲疫@里采用的是硬編碼,所以不是很好,大家也可嘗試優(yōu)化一下。
<!DOCTYPE html>
<html lang="zh">
<head>
<meta charset="UTF-8">
<title>2048游戲界面</title>
<style>
body { background: url("./images/bg3.jpg") repeat; }
#canvas { border: 1px solid #aaaaaa; display: block; margin: 50px auto; }
</style>
</head>
<body>
<div id="canvas-warp">
<canvas id="canvas">
你的瀏覽器居然不支持Canvas?!趕快換一個(gè)吧??!
</canvas>
</div>
<script>
window.onload = function(){
var canvas = document.getElementById("canvas");
canvas.width = 800;
canvas.height = 600;
var context = canvas.getContext("2d");
context.fillStyle = "#FFF";
context.fillRect(0,0,800,600);
drawRoundRect(context, 200, 100, 400, 400, 5);
context.fillStyle = "#AA7B41";
context.strokeStyle = "#0078AA";
context.stroke();
context.fill();
for(var i = 1; i <= 4; i++){
for(var j = 1; j <= 4; j++){
drawRoundRect(context, 200 + 16 * i + 80 * (i - 1), 100 + 16 * j + 80 * (j - 1), 80, 80, 5);
context.fillStyle = "#CCBFB4";
context.strokeStyle = "#0078AA";
context.stroke();
context.fill();
}
}
}
function drawRoundRect(cxt, x, y, width, height, radius){
cxt.beginPath();
cxt.arc(x + radius, y + radius, radius, Math.PI, Math.PI * 3 / 2);
cxt.lineTo(width - radius + x, y);
cxt.arc(width - radius + x, radius + y, radius, Math.PI * 3 / 2, Math.PI * 2);
cxt.lineTo(width + x, height + y - radius);
cxt.arc(width - radius + x, height - radius + y, radius, 0, Math.PI * 1 / 2);
cxt.lineTo(radius + x, height +y);
cxt.arc(radius + x, height - radius + y, radius, Math.PI * 1 / 2, Math.PI);
cxt.closePath();
}
</script>
</body>
</html>
運(yùn)行結(jié)果:

這個(gè)圓角矩形的函數(shù)寫好之后,可以自己封裝進(jìn)JS文件里,以后遇到什么好的函數(shù)都可以放進(jìn)去,這樣積累下來,這個(gè)文件就是一套屬于自己的圖形庫和游戲引擎了,是不是非常的酷?
其實(shí)游戲制作是Canvas的主要用途,但是要知道每一個(gè)游戲設(shè)計(jì)師都是一個(gè)藝術(shù)家。是不是覺得前途一片光明?讓我們繼續(xù)前進(jìn)!