原生js+canvas實(shí)現(xiàn)貪吃蛇效果
本文實(shí)例為大家分享了canvas實(shí)現(xiàn)貪吃蛇效果的具體代碼,供大家參考,具體內(nèi)容如下
效果展示:
源碼展示:
頁(yè)面布局展示:worm.html
<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title>貪吃蛇</title> <style type="text/css"> canvas{ border: 1px solid black; } div{ width: 50px; height: 50px; border: 1px solid black; cursor: pointer; text-align: center; line-height: 50px; } </style> <script type="text/javascript" src="Node.js" ></script> <script type="text/javascript" src="Worm.js" ></script> <script src="Stage.js" type="text/javascript" charset="utf-8"></script> <script type="text/javascript"> function load () { //創(chuàng)建一個(gè)舞臺(tái) 調(diào)用print方法打印 stage=new Stage(); //獲取ctx var mCanvas=document.getElementById("mCanvas"); ctx=mCanvas.getContext('2d'); stage.print(ctx); startPrint(); } function changeDir(dir){ DIR=dir; } var task; var stage; var ctx; function startPrint () { task=window.setInterval(function () { stage.worm.step(); stage.print(ctx); }, SPEED); } function endPrint () { window.clearInterval(task); } </script> </head> <body onload="load()"> <canvas id="mCanvas" width="500" height="500"> </canvas> <table> <tr> <td></td> <td> <div onclick="changeDir(UP)">UP</div> </td> <td></td> </tr> <tr> <td> <div onclick="changeDir(LEFT)">LEFT</div> </td> <td></td> <td> <div onclick="changeDir(RIGHT)">RIGHT</div> </td> </tr> <tr> <td></td> <td> <div onclick="changeDir(DOWN)">DOWN</div> </td> <td></td> </tr> </table> </body> </html>
節(jié)點(diǎn)類的js :Node.js
/* 節(jié)點(diǎn)類 */ function Node (x, y) { this.x=x; this.y=y; this.equals=function (i, j) { return this.x==i && this.y==j; }; }
舞臺(tái)類js:Stage.js
/** 舞臺(tái)類 */ function Stage () { this.width=50; this.height=50; this.worm=new Worm(); /* 在canvas中繪制舞臺(tái)的內(nèi)容 */ this.print=function (ctx) { for(i=0; i<this.width; i++){ for(j=0; j<this.height; j++){ //如果當(dāng)前節(jié)點(diǎn)是蛇身子的一部分 //那么換一種顏色繪制 if(this.worm.contains(i,j)){ ctx.fillStyle="#ab55ff"; ctx.fillRect(i*10, j*10, 10, 10); }else if(this.worm.food.equals(i, j)){ ctx.fillStyle="#000000"; ctx.fillRect(i*10, j*10, 10, 10); }else{ ctx.fillStyle="#dddddd"; ctx.fillRect(i*10, j*10, 10, 10); } } } //在舞臺(tái)的左上角繪制分?jǐn)?shù) ctx.font="30px Arial"; ctx.fillStyle="#880000"; ctx.fillText("score:"+SCORE, 10,40); }; }
蛇類js:Worm.js
/** 蛇類 */ var UP=0; var DOWN=1; var LEFT=2; var RIGHT=3; var DIR=UP; var SCORE=0; var SPEED=300; //蛇類初始化的形狀 function Worm () { this.nodes=[]; this.nodes[this.nodes.length]=new Node(20,10); this.nodes[this.nodes.length]=new Node(20,11); this.nodes[this.nodes.length]=new Node(20,12); this.nodes[this.nodes.length]=new Node(20,13); this.nodes[this.nodes.length]=new Node(20,14); this.nodes[this.nodes.length]=new Node(20,15); this.nodes[this.nodes.length]=new Node(21,15); this.nodes[this.nodes.length]=new Node(22,15); this.nodes[this.nodes.length]=new Node(23,15); this.nodes[this.nodes.length]=new Node(24,15); this.nodes[this.nodes.length]=new Node(24,16); this.nodes[this.nodes.length]=new Node(24,17); this.nodes[this.nodes.length]=new Node(24,18); this.nodes[this.nodes.length]=new Node(24,19); /* 蛇會(huì)走一步 */ this.step=function () { //計(jì)算出頭結(jié)點(diǎn) 把頭節(jié)點(diǎn)添加到nodes數(shù)組中 var oldHead=this.nodes[0]; var newHead; switch (DIR){ case UP: if(oldHead.y-1<0){ newHead=new Node(oldHead.x, 49); }else{ newHead=new Node(oldHead.x, oldHead.y-1); } break; case DOWN: if(oldHead.y+1>49){ newHead=new Node(oldHead.x, 0); }else{ newHead=new Node(oldHead.x, oldHead.y+1); } break; case LEFT: if(oldHead.x-1<0){ newHead=new Node(49, oldHead.y); }else{ newHead=new Node(oldHead.x-1, oldHead.y); } break; case RIGHT: if(oldHead.x+1>49){ newHead=new Node(0, oldHead.y); }else{ newHead=new Node(oldHead.x+1, oldHead.y); } break; } this.nodes.unshift(newHead); if(!this.food.equals(newHead.x, newHead.y)){ //把尾節(jié)點(diǎn)刪掉 (在沒有吃到食物的時(shí)候) this.nodes.pop(); }else{ //吃到了食物 重新生成食物 this.food=this.randomFood(); SCORE+=10; SPEED-=50; endPrint(); startPrint(); } }; /* 判斷i,j節(jié)點(diǎn)是否是當(dāng)前蛇身子的一部分 */ this.contains=function (i, j) { for(k=0; k<this.nodes.length; k++){ var node=this.nodes[k]; if(node.x==i && node.y==j){ return true; } } return false; }; //聲明生成食物的方法 this.randomFood=function () { var x; var y; do{ x=Math.floor(Math.random()*50); y=Math.floor(Math.random()*50); }while(this.contains(x, y)); return new Node(x, y); }; //聲明食物 this.food=this.randomFood(); }
以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
JavaScript獲取時(shí)間戳的方法總結(jié)
JavaScript獲得時(shí)間戳的方法有五種,后四種都是通過(guò)實(shí)例化時(shí)間對(duì)象new Date() 來(lái)進(jìn)一步獲取當(dāng)前的時(shí)間戳,下面我們就一起學(xué)習(xí)一下具體獲取的方法吧2023-09-09點(diǎn)擊單元格后可編輯單元格內(nèi)文本如何制作
點(diǎn)擊單元格后可編輯單元格內(nèi)文本如何制作...2006-10-10js實(shí)現(xiàn)可鍵盤控制的簡(jiǎn)單抽獎(jiǎng)程序
這篇文章主要為大家詳細(xì)介紹了js實(shí)現(xiàn)可鍵盤控制的簡(jiǎn)單抽獎(jiǎng)程序,代碼簡(jiǎn)潔,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2016-07-07

關(guān)閉瀏覽器輸入框自動(dòng)補(bǔ)齊 兼容IE,FF,Chrome等主流瀏覽器

JS實(shí)現(xiàn)可視化音頻效果的實(shí)例代碼

JavaScript面試技巧之?dāng)?shù)組的一些不low操作

javascript cookie解碼函數(shù)(兼容ff)