本篇文章給大家分享的是有關(guān)使用canvas怎么實(shí)現(xiàn)一個(gè)俄羅斯方塊,小編覺得挺實(shí)用的,因此分享給大家學(xué)習(xí),希望大家閱讀完這篇文章后可以有所收獲,話不多說,跟著小編一起來看看吧。
為文登等地區(qū)用戶提供了全套網(wǎng)頁設(shè)計(jì)制作服務(wù),及文登網(wǎng)站建設(shè)行業(yè)解決方案。主營業(yè)務(wù)為成都網(wǎng)站制作、網(wǎng)站建設(shè)、外貿(mào)網(wǎng)站建設(shè)、文登網(wǎng)站設(shè)計(jì),以傳統(tǒng)方式定制建設(shè)網(wǎng)站,并提供域名空間備案等一條龍服務(wù),秉承以專業(yè)、用心的態(tài)度為用戶提供真誠的服務(wù)。我們深信只要達(dá)到每一位用戶的要求,就會(huì)得到認(rèn)可,從而選擇與我們長期合作。這樣,我們也可以走得更遠(yuǎn)!
界面的實(shí)現(xiàn)
整個(gè)面板就是以左上角(0,0)為原點(diǎn)的坐標(biāo)系,右上角(12,0)左下角(0,20)右下角(12,20),每個(gè)點(diǎn)的坐標(biāo)位置都可以確定。是否已經(jīng)填充方塊,我們可以將每個(gè)方格看成一個(gè)數(shù)組元素,0表示沒有,1表示已經(jīng)填充。12 * 20 的面板使用兩層數(shù)組,即用20個(gè)長度為12的數(shù)組實(shí)現(xiàn)。
var maps = [[0,0,0,0,0,0,0,0,0,0,0,0],[0,0,0,0,0,0,0,0,1,0,1,0], ...];
畫出面板的代碼,用最基礎(chǔ)的canvas的api就能實(shí)現(xiàn)
//格子 for(var i=0;i<12;i++){ for(var j=0;j<20;j++){ ctx.fillRect(i*40,j*40,40,40); ctx.strokeRect(i*40,j*40,40,40); if(this.maps[j][i]==1){//方格已經(jīng)有填充內(nèi)容 ctx.save(); ctx.lineWidth=4; ctx.fillStyle='hsla(200,100%,50%,.5)'; ctx.strokeStyle='hsla(200,100%,50%,.9)'; ctx.fillRect(i*40,j*40,40,40); ctx.strokeRect(i*40+2,j*40+2,38,38); ctx.restore(); } } } //邊框 ctx.lineWidth=4; ctx.strokeStyle='hsla(0,100%,0%,.3)'; ctx.moveTo(0,0); ctx.lineTo(0,20*40); ctx.lineTo(12*40,20*40); ctx.lineTo(12*40,0); ctx.stroke(); ctx.restore();
方塊的實(shí)現(xiàn)
游戲中用到以下 7 種圖形
結(jié)合上面介紹的坐標(biāo)系,數(shù)組 [x1, y1, x2, y2, x3, y3, x4, y4] 就是上面圖形中4個(gè)點(diǎn)坐標(biāo)的數(shù)據(jù)表現(xiàn)形式,7 種圖形的坐標(biāo)分別如下:
var Arr = [[4,0,4,1,5,1,6,1],[4,1,5,1,6,1,6,0],[4,0,5,0,5,1,6,1],[4,1,5,0,5,1,6,0], [5,0,4,1,5,1,6,1],[4,0,5,0,6,0,7,0],[5,0,6,0,5,1,6,1]];
方塊的移動(dòng),遍歷整個(gè)數(shù)組,加上位移向量就行,非常簡單
class Shape { constructor(m){ this.m = Object.assign([],m); } move(x,y){ // 位移 var m = this.m, l = m.length; y = y||0; for (var i=0;i<l;i=i+2){ m[i]+=x; m[i+1]+=y; } return this; }
方塊的旋轉(zhuǎn),俄羅斯方塊里面方塊除了左右和上下運(yùn)動(dòng),還會(huì)旋轉(zhuǎn),不是嗎?稍微思考下就知道,這不過就是矩陣變換而已,也就是每次圖形繞中心點(diǎn)旋轉(zhuǎn)90度。我這里用數(shù)組第三個(gè)點(diǎn)作為圖形變換的中心點(diǎn),當(dāng)然這樣處理不夠完善。
class Shape { transform(){//二維矩陣變換 var m =this.m, l = m.length, c = Math.ceil(l/2), x = m[c], y = m[c+1], cos = Math.cos(Math.PI/180 * 90), sin = Math.sin(Math.PI/180 * 90); for (var i=0;i<l;i=i+2){ if(i == c) continue; var mx = m[i]- x, my = m[i+1] - y, nx = mx*cos - my*sin, ny = my*cos + mx*sin; m[i]=x+nx; m[i+1]=y+ny; } return this; }
邊界條件
主要包括如下三個(gè)方面
方塊位置不能超出界面的判斷;
方塊到達(dá)底部或放置完成的判斷;
游戲結(jié)束的判斷。
遍歷數(shù)組 (1)任意一個(gè)點(diǎn)y坐標(biāo)為19時(shí)表示到達(dá)了底部;(2)獲取該坐標(biāo)的y+1位置在maps的信息,如果為1表示已經(jīng)填充。這兩種情況下,運(yùn)動(dòng)方塊的周期結(jié)束,將該方塊的坐標(biāo)填充到maps對(duì)應(yīng)的數(shù)組里面即可。
如果坐標(biāo)的y+1已經(jīng)有填充,同時(shí)當(dāng)前坐標(biāo)小于1,即已經(jīng)在界面的頂部了,那么表示游戲結(jié)束。
var isEnd = false,isOver=false,x,y; for(var i=0,sl=that.shape.m.length;i<sl;i=i+2){ x=that.shape.m[i]; y=that.shape.m[i+1]; if(y >= 19){ // 到了底部 isEnd = true;break; } if(that.maps[y+1][x]==1){ // y+1位置已經(jīng)填充 isEnd = true; if(y <= 1){isOver=true;} // 游戲結(jié)束 break; } }
方塊運(yùn)動(dòng)周期結(jié)束時(shí)檢測(cè)每一層是否滿格,以及滿格后的處理。某項(xiàng)數(shù)組全部元素都為1則表示已經(jīng)滿格,那么刪除該項(xiàng)數(shù)組,同時(shí)列表頭再壓入一項(xiàng)每個(gè)元素都為0的數(shù)組即可。
checkPoint(){ var that = this, maps = that.maps; for(var i=0,l=maps.length;i<l;i++){ if(Math.min.apply(null,maps[i]) == 1){// 表示該層已經(jīng)滿格 that.maps.splice(i,1); that.score+=10; // 增加分?jǐn)?shù) that.maps.unshift([0,0,0,0,0,0,0,0,0,0,0,0]); } } return this; }
綁定事件
主要就是綁定keydown事件,要注意的是左移和右移事件包括了邊界判斷
bindEvent(){ var that = this; document.addEventListener('keydown',function(e){ switch(e.keyCode){ case 13: //enter cancelAnimationFrame(that.timer); that.init().update(); break; case 80: //p that.pause = !that.pause; break; case 40: //down that.d = 0.5; break; case 37: //left var over = false, maps = that.maps, shape = that.shape, m = shape.m; for(var i=0,l=m.length;i<l;i=i+2){ if(m[i]<=0 || maps[m[i+1]][m[i]-1] == 1){ over = true;break; } } if(!over) shape.move(-1,0); break; case 39: //right var over = false, shape = that.shape, maps = that.maps, m = shape.m; for(var i=0,l=m.length;i<l;i=i+2){ if(m[i]>=11 || maps[m[i+1]][m[i]+1] == 1){ over = true;break; } } if(!over) shape.move(1,0); break; case 32: //space that.shape.transform(); break; } },false); }
以上就是使用canvas怎么實(shí)現(xiàn)一個(gè)俄羅斯方塊,小編相信有部分知識(shí)點(diǎn)可能是我們?nèi)粘9ぷ鲿?huì)見到或用到的。希望你能通過這篇文章學(xué)到更多知識(shí)。更多詳情敬請(qǐng)關(guān)注創(chuàng)新互聯(lián)行業(yè)資訊頻道。
網(wǎng)頁標(biāo)題:使用canvas怎么實(shí)現(xiàn)一個(gè)俄羅斯方塊
路徑分享:http://muchs.cn/article18/gdohgp.html
成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供手機(jī)網(wǎng)站建設(shè)、、定制開發(fā)、網(wǎng)站建設(shè)、微信公眾號(hào)、App開發(fā)
聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請(qǐng)盡快告知,我們將會(huì)在第一時(shí)間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如需處理請(qǐng)聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時(shí)需注明來源: 創(chuàng)新互聯(lián)