javascript實(shí)現(xiàn)俄羅斯方塊游戲的思路和方法
觀摩一下《編程之美》:“程序雖然很難寫(xiě),卻很美妙。要想把程序?qū)懞茫枰獙?xiě)好一定的基礎(chǔ)知識(shí),包括編程語(yǔ)言、數(shù)據(jù)結(jié)構(gòu)與算法。程序?qū)懙煤茫枰b密的邏輯思維能力和良好的梳理基礎(chǔ),而且熟悉編程環(huán)境和編程工具?!?/p>
學(xué)了幾年的計(jì)算機(jī),你有沒(méi)有愛(ài)上編程。話說(shuō),沒(méi)有嘗試自己寫(xiě)過(guò)一個(gè)游戲,算不上熱愛(ài)編程。
俄羅斯方塊曾經(jīng)造成的轟動(dòng)與造成的經(jīng)濟(jì)價(jià)值可以說(shuō)是游戲史上的一件大事,它看似簡(jiǎn)單但卻變化無(wú)窮,令人上癮。相信大多數(shù)同學(xué),曾經(jīng)為它癡迷得茶不思飯不想。
游戲規(guī)則
1、一個(gè)用于擺放小型正方形的平面虛擬場(chǎng)地,其標(biāo)準(zhǔn)大?。盒袑挒?0,列高為20,以每個(gè)小正方形為單位。
2、一組由4個(gè)小型正方形組成的規(guī)則圖形,英文稱為Tetromino,中文通稱為方塊共有7種,分別以S、Z、L、J、I、O、T這7個(gè)字母的形狀來(lái)命名。
I:一次最多消除四層
J(左右):最多消除三層,或消除二層
L:最多消除三層,或消除二層
O:消除一至二層
S(左右):最多二層,容易造成孔洞
Z (左右):最多二層,容易造成孔洞
T:最多二層
方塊會(huì)從區(qū)域上方開(kāi)始緩慢繼續(xù)落下。玩家可以以90度為單位旋轉(zhuǎn)方塊,以格子為單位左右移動(dòng)方塊,讓方塊加速落下。方塊移到區(qū)域最下方或是著地到其他方塊上無(wú)法移動(dòng)時(shí),就會(huì)固定在該處,而新的方塊出現(xiàn)在區(qū)域上方開(kāi)始落下。當(dāng)區(qū)域中某一列橫向格子全部由方塊填滿,則該列會(huì)消失并成為玩家的得分。同時(shí)刪除的列數(shù)越多,得分指數(shù)上升。
分析與解法
每塊方塊落下的過(guò)程中,我們可以做:
1)旋轉(zhuǎn)到合適的方向
2)水平移動(dòng)到某一列
3)垂直下落到底部
首先,需要用一個(gè)二維數(shù)組,area[18][10]表示18*10的游戲區(qū)域。其中,數(shù)組中值為0表示空,1表示有方塊。
方塊一共7種,每種有4種方向。定義activeBlock[4],在編譯之前這個(gè)數(shù)組的值預(yù)定算好,在程序中直接使用。
難點(diǎn)
1)邊界檢查。
//檢查左邊界,嘗試著朝左邊移動(dòng)一個(gè),看是否合法。 function checkLeftBorder(){ for(var i=0; i<activeBlock.length; i++){ if(activeBlock[i].y==0){ return false; } if(!isCellValid(activeBlock[i].x, activeBlock[i].y-1)){ return false; } } return true; } //同理,需要檢測(cè)右邊界和底邊界
2)旋轉(zhuǎn), 需要數(shù)理邏輯, 一個(gè)點(diǎn)相對(duì)另外一個(gè)點(diǎn)旋轉(zhuǎn)90度的問(wèn)題。
3)定時(shí)和監(jiān)聽(tīng)鍵盤事件機(jī)制讓游戲自動(dòng)運(yùn)行下去。
//開(kāi)始 function begin(e){ e.disabled = true; status = 1; tbl = document.getElementById("area"); if(!generateBlock()){ alert("Game over!"); status = 2; return; } paint(); timer = setInterval(moveDown,1000); } document.onkeydown=keyControl;
程序過(guò)程
1)用戶點(diǎn)開(kāi)始->構(gòu)造一個(gè)活動(dòng)圖形, 設(shè)置定時(shí)器。
//當(dāng)前活動(dòng)的方塊, 它可以左右下移動(dòng), 變型。當(dāng)它觸底后, 將會(huì)更新area; var activeBlock; //生產(chǎn)方塊形狀, 有7種基本形狀。 function generateBlock(){ activeBlock = null; activeBlock = new Array(4); //隨機(jī)產(chǎn)生0-6數(shù)組,代表7種形態(tài)。 var t = (Math.floor(Math.random()*20)+1)%7; switch(t){ case 0:{ activeBlock[0] = {x:0, y:4}; activeBlock[1] = {x:1, y:4}; activeBlock[2] = {x:0, y:5}; activeBlock[3] = {x:1, y:5}; break; } //省略部分代碼.............................. case 6:{ activeBlock[0] = {x:0, y:5}; activeBlock[1] = {x:1, y:4}; activeBlock[2] = {x:1, y:5}; activeBlock[3] = {x:1, y:6}; break; } } //檢查剛生產(chǎn)的四個(gè)小方格是否可以放在初始化的位置. for(var i=0; i<4; i++){ if(!isCellValid(activeBlock[i].x, activeBlock[i].y)){ return false; } } return true; }
2)每次向下移動(dòng)后, 都檢查是否觸底, 如果觸底了, 則嘗試消行。
//消行 function deleteLine(){ var lines = 0; for(var i=0; i<18; i++){ var j=0; for(; j<10; j++){ if(area[i][j]==0){ break; } } if(j==10){ lines++; if(i!=0){ for(var k=i-1; k>=0; k--){ area[k+1] = area[k]; } } area[0] = generateBlankLine(); } } return lines; }
3)完了之后再構(gòu)造一個(gè)活動(dòng)圖形, 再設(shè)置定時(shí)器。
效果圖
有待優(yōu)化
1)設(shè)置不同形狀方塊的顏色。
思路:在創(chuàng)建方塊函數(shù)內(nèi),設(shè)定activeBlockColor顏色,七種不同形態(tài)方塊顏色各異(除了修改generateBlock方法之外,還需要修改paintarea方法。因?yàn)橐婚_(kāi)始考慮不周全,消除一行后,重繪方塊的同時(shí)將顏色統(tǒng)一,因此可以考慮移除表格n行,然后在頂部增添n行,以保證沒(méi)消除方塊的完整性)。
2)當(dāng)當(dāng)前方塊下落時(shí),可以提前查看下一個(gè)方塊。
思路:將generateBlock方法拆分成兩部分,一部分用于隨機(jī)嘗試下一個(gè)方塊,一部分用于緩存當(dāng)前所要描繪的方塊。當(dāng)當(dāng)前方塊碰到底部被固定后,下一方塊開(kāi)始描繪,同時(shí)又再次隨機(jī)產(chǎn)生新方塊。如此反復(fù)。
以上所述就是本文給大家分享的全部?jī)?nèi)容了,希望大家能夠喜歡。
- JS俄羅斯方塊,包含完整的設(shè)計(jì)理念
- JS 俄羅斯方塊完美注釋版代碼
- JAVASCRIPT代碼編寫(xiě)俄羅斯方塊網(wǎng)頁(yè)版
- 60行js代碼實(shí)現(xiàn)俄羅斯方塊
- 使用JS代碼實(shí)現(xiàn)俄羅斯方塊游戲
- JavaScript實(shí)現(xiàn)簡(jiǎn)潔的俄羅斯方塊完整實(shí)例
- JavaScript實(shí)現(xiàn)俄羅斯方塊游戲過(guò)程分析及源碼分享
- JS+Canvas實(shí)現(xiàn)的俄羅斯方塊游戲完整實(shí)例
- js html5 css俄羅斯方塊游戲再現(xiàn)
- JavaScript canvas實(shí)現(xiàn)俄羅斯方塊游戲
相關(guān)文章
給應(yīng)用部分的js代碼設(shè)定一個(gè)統(tǒng)一的入口
javascript是種腳本語(yǔ)言,瀏覽器下載到哪兒就會(huì)執(zhí)行到哪兒,下面為大家介紹下,如何給應(yīng)用部分的js代碼一個(gè)統(tǒng)一的入口2014-06-06JS解決移動(dòng)web開(kāi)發(fā)手機(jī)輸入框彈出的問(wèn)題
在移動(dòng)web開(kāi)發(fā)中和pc端不同的是,手機(jī)的輸入是軟鍵盤,這樣就會(huì)有個(gè)問(wèn)題,那就是當(dāng)有輸入的時(shí)候,鍵盤彈起來(lái),整個(gè)頁(yè)面難免會(huì)發(fā)生變化。怎么解決這個(gè)問(wèn)題呢?下面腳本之家小編給大家分享JS解決移動(dòng)web開(kāi)發(fā)手機(jī)輸入框彈出的問(wèn)題2017-03-03利用javascript的面向?qū)ο蟮奶匦詫?shí)現(xiàn)限制試用期
Javascript是一種面向?qū)ο蟮哪_本語(yǔ)言,其也具有面向?qū)ο蟮娜筇匦?,但是今天我們不詳?xì)的講解javascript的面向?qū)ο筇匦?,今天我們?jiǎn)單的了解一下javascript的面向?qū)ο筇匦裕缓髮W(xué)習(xí)一下怎樣實(shí)現(xiàn)試用期的限制!2011-08-08JS數(shù)組索引檢測(cè)中的數(shù)據(jù)類型問(wèn)題詳解
這篇文章主要給大家介紹了關(guān)于JS數(shù)組索引檢測(cè)中的數(shù)據(jù)類型問(wèn)題的相關(guān)資料,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2021-01-01JavaScript中的一些實(shí)用小技巧總結(jié)
這篇文章主要給大家總結(jié)介紹了關(guān)于JavaScript中的一些實(shí)用小技巧,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家學(xué)習(xí)或者使用JavaScript具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2019-04-04JavaScript實(shí)現(xiàn)LRU算法的示例詳解
不知道屏幕前的朋友們,有沒(méi)有和我一樣,覺(jué)得LRU算法原理很容易理解,實(shí)現(xiàn)起來(lái)卻很復(fù)雜。所以本文就為大家整理了一下實(shí)現(xiàn)的示例代碼,需要的可以參考一下2023-04-04