簡介:
canvas是html5最重要的元素阔涉,提供了一個(gè)畫布的功能诗祸,有強(qiáng)大的圖形處理能力
canvas標(biāo)簽添加
要使用canvas,首先要在body中添加上canvas標(biāo)簽
canvas標(biāo)簽是一塊默認(rèn)300*150大小的畫布
畫布寬高設(shè)置:
使用canvas標(biāo)簽的屬性,width及height直接在行間設(shè)置
此處注意:不要用css樣式去改畫布大小迂苛,這個(gè)會(huì)導(dǎo)致畫布中的圖像被拉伸
<canvas id="canvas1" width="800" height="500"></canvas>
畫布css樣式
畫布的其他css樣式可以正常設(shè)置
canvas標(biāo)簽中的內(nèi)容
canvas標(biāo)簽中的內(nèi)容是(包括標(biāo)簽)只有在不支持此效果的低版本瀏覽器中才會(huì)顯示的;在高版本瀏覽器中不會(huì)顯示出來
<canvas id="canvas1" width="800" height="500">
只是一個(gè)canvas標(biāo)簽鼓择,然而你看不到
</canvas>
獲取canvas標(biāo)簽及上下文
canvas標(biāo)簽使用js正常dom節(jié)點(diǎn)的獲取方法獲取
var canvas = document.getElementById('canvas1');
上下文是記錄canvas執(zhí)行命令語句的地方三幻,獲取如下,后面的參數(shù)現(xiàn)在只有2d可選
var context = canvas.getContext('2d');
canvas坐標(biāo)系
左上角是00點(diǎn)呐能,x軸正方向向右念搬,y軸正方向向下
樣式設(shè)置
邊框設(shè)置:context.strokeStyle
填充設(shè)置:context.fillStyle
線寬設(shè)置:context.lineWidth
context.strokeStyle = "red";
context.lineWidth = 2;
context.fillStyle = 'yellow';
繪制圖形
繪制命令
- 邊框式繪制:
context.stroke();
- 填充式繪制:
context.fill();
新建路徑beginPath()
這個(gè)方法代表重新開始一段路徑,也可以理解為新建一個(gè)圖層
這個(gè)的方法之后執(zhí)行的繪制動(dòng)作摆出,不會(huì)執(zhí)行到這個(gè)方法之前的命令
context.beginPath();
繪制直線:
- 設(shè)置畫筆開始位置:
context.moveTo(x,y)
- 設(shè)置畫筆結(jié)束位置:
context.lineTo(x,y)
- 線段兩邊圓角:
context.lineCap = "round"
context.strokeStyle = "red";
context.lineWidth = 2;
context.moveTo(100,100);
context.lineTo(500,100);
context.stroke();
繪制三角:方法就是繪制3條直線
繪制多條連續(xù)線段時(shí)朗徊,不必每次重新定義起始點(diǎn)
畫筆會(huì)停在上一段線段的終點(diǎn),并默認(rèn)為下一次繪制的起始點(diǎn)
context.strokeStyle = "red";
context.lineWidth = 2;
context.moveTo(10,10);
context.lineTo(10,110);
context.lineTo(110,110);
context.lineTo(10,10);
context.stroke();
注意偎漫,此處用繪制直線的方法爷恳,進(jìn)行圖形的繪制時(shí);直線封閉處會(huì)出現(xiàn)瑕疵象踊,不會(huì)完全閉合
閉合方法:context.closePath()
加上上面的閉合命令后温亲,閉合處的瑕疵就會(huì)被修復(fù)
這個(gè)方法會(huì)自動(dòng)將起點(diǎn)與末點(diǎn)相連,所以不必再將路徑回到起始點(diǎn)
context.strokeStyle = "red";
context.lineWidth = 2;
context.beginPath();
context.moveTo(10,10);
context.lineTo(10,110);
context.lineTo(110,110);
context.closePath(); //封閉路徑后最后一個(gè)點(diǎn)就不用定義了
context.stroke();
繪制矩形
定義矩形:context.rect(x,y,w,h);
- x:起始位置x坐標(biāo)(矩形左上角)
- y:起始位置y坐標(biāo)(矩形左上角)
- w:矩形寬
- h:矩形高
直接繪制:省去了定義矩形的步驟杯矩,按照定義的樣式直接填充或描邊
context.fillRect(x,y,w,h)
context.strokeRect(x,y,w,h)
橡皮擦功能:clearRect(x,y,w,h)
- 擦除矩形范圍之內(nèi)的內(nèi)容
- 常用來擦除整個(gè)畫布以實(shí)現(xiàn)動(dòng)畫效果
圖形繪制方式
邊框式繪制:
context.strokeStyle = "red";
context.lineWidth = 2;
context.rect(150,150,200,100);
context.stroke();
填充式繪制:
context.fillStyle = 'yellow';
context.rect(150,150,200,100);
context.fill();
填充+描邊同時(shí)使用注意:
這兩個(gè)效果同時(shí)使用時(shí)栈虚,先后順序的不同會(huì)導(dǎo)致效果的差異
一般是在填充后再去描邊,如下效果
context.strokeStyle = "red";
context.lineWidth = 2;
context.rect(150,150,200,100);
context.fill();
context.stroke();
如果是描邊后再填充的話史隆,填充效果會(huì)遮擋一半的邊框
//線寬被遮擋一半
context.strokeStyle = "red";
context.lineWidth = 2;
context.rect(150,150,200,100);
context.stroke();
context.fill();
繪制弧形
常用方法:context.arc(x,y,r,θ1,θ2,boolean)
- x:中心點(diǎn)x坐標(biāo)
- y:中心點(diǎn)y坐標(biāo)
- r:圓半徑
- θ1:起始角度
- θ2:結(jié)束角度
- 布爾值:false逆時(shí)針(默認(rèn))节芥,true順時(shí)針
//畫弧線
context.strokeStyle = "red";
context.lineWidth = 2;
context.arc(300,100,100,0,Math.PI/2,true)
context.stroke();
//畫圓
context.beginPath();
context.arc(300,200,100,0,Math.PI*2,true)
context.stroke();
繪制文字
設(shè)置文字樣式:context.font = 'italic size family'
- italic:斜體
- size:字體大小
- family:字體
設(shè)置文字內(nèi)容:context.strokeText("text",x,y)
- "text":中文字內(nèi)容
- x:起始x坐標(biāo)
- y:起始y坐標(biāo)
context.lineWidth = 1;
context.strokeStyle = "green";
context.font = "italic 150px arial"
context.strokeText("我是文字",50,200);
漸變樣式
線性漸變:createLinearGradient(x1,y1,x2,y2)
- x1/y1:漸變起始位置坐標(biāo)
- x2/y2:漸變結(jié)束位置坐標(biāo)
徑向漸變:createRadiusGradient(x1,y1,r1,x2,y2,r2)
- x1/y1:漸變起始圓的圓心位置坐標(biāo)
- r1:漸變起始圓半徑
- x2/y2:漸變結(jié)束圓的圓心位置坐標(biāo)
- r2:漸變結(jié)束圓半徑
漸變顏色設(shè)置:addColorStop(%,"color");
- %:漸變進(jìn)度,用[0,1]之間的數(shù)字表示
- "color":每個(gè)漸變階段的顏色
var linearGradient = context.createLinearGradient(100,300,800,500);
linearGradient.addColorStop(0,"red");
linearGradient.addColorStop(0.4,"yellow");
linearGradient.addColorStop(0.8,"green");
linearGradient.addColorStop(1,"blue");
context.fillStyle = linearGradient;
context.font = "italic 150px arial"
context.fillText("我是文字",50,200);
繪制陰影
陰影顏色:shadowColor = "color";
陰影模糊度:shadowblur = number;
陰影偏移X:shadowOffsetX = number;
陰影偏移Y:shadowOffsetY = number;
context.shadowColor = "black";
context.shadowBlur = 20;
context.shadowOffsetX = 10;
context.shadowOffsetY = 5;
context.strokeRect(100,100,100,100);
坐標(biāo)變換
相關(guān)例子可以看我的另一篇博客canvas鐘表效果
坐標(biāo)系平移:translate(x,y)
- 即是將坐標(biāo)系的00點(diǎn)變換到(x,y)位置
坐標(biāo)系旋轉(zhuǎn):rotate(θ)
- 將坐標(biāo)系旋轉(zhuǎn)θ度
- θ > 0時(shí)順時(shí)針旋轉(zhuǎn),θ < 0時(shí)逆時(shí)針旋轉(zhuǎn)
坐標(biāo)系縮放:scale(x,y)
- 將坐標(biāo)系x方向放大x倍
- 將坐標(biāo)系y方向放大y倍
注意:因?yàn)樽鴺?biāo)系在經(jīng)過變換之后头镊,之后重新繪制的圖形都會(huì)以這個(gè)新的坐標(biāo)系為參考蚣驼;所以在繪制的時(shí)候會(huì)非常的麻煩
解決方案如下:
save()
:保存當(dāng)前坐標(biāo)系
restore()
:讀取保存的坐標(biāo)系
- 每次在進(jìn)行坐標(biāo)系變換之前,先使用
save()
將原始坐標(biāo)系保存下來 - 在進(jìn)行變換之后相艇,再使用
restore()
將坐標(biāo)系恢復(fù)為初始坐標(biāo)系 - 每個(gè)
restore()
對(duì)應(yīng)相應(yīng)的一個(gè)save()
颖杏,所以在全局中保存一次隨后無限restore()
的做法是無效的
繪制貝塞爾曲線/二次曲線
相關(guān)例子可以看我另一篇博客canvas隨拖動(dòng)變化的貝塞爾曲線
先用moveTo(x,y)設(shè)置起始點(diǎn)坐標(biāo)
貝塞爾曲線:bezierCurveTo(cpx1,cpy1,cpx2,cpy2,dx,dy)
- cpx1/xpy1:控制點(diǎn)1坐標(biāo)
- cpx2/xpy2:控制點(diǎn)2坐標(biāo)
- dx/dy:終點(diǎn)坐標(biāo)
二次曲線quadraticCurveTo(cpx,cpy,dx,dy)
- cpx/xpy:控制點(diǎn)坐標(biāo)
- dx/dy:終點(diǎn)坐標(biāo)
context.beginPath();
context.moveTo(300,100);
//貝塞爾曲線
context.bezierCurveTo(200,100,300,300,200,300);
context.stroke()
//二次曲線
context.moveTo(300,300);
context.quadraticCurveTo(400,150,500,300);
context.stroke();