寫在前面得話: 這篇文章主要記錄了我是怎麼一步一步寫出俄羅斯方塊,整個代碼用的函數編程,主要是為了讓一些不熟悉es6, 面向對象寫法得 新手能更容易看明白,全部得代碼中都是一些js的基礎知識,很容易理解。要說有點麻煩的,那就是游戲過程中的各種檢測。但是只要你多思考,你就能理解代碼為什麼要那樣寫,你也 ...
寫在前面得話:
這篇文章主要記錄了我是怎麼一步一步寫出俄羅斯方塊,整個代碼用的函數編程,主要是為了讓一些不熟悉es6, 面向對象寫法得 新手能更容易看明白,全部得代碼中都是一些js的基礎知識,很容易理解。要說有點麻煩的,那就是游戲過程中的各種檢測。但是只要你多思考,你就能理解代碼為什麼要那樣寫,你也可以實現這個游戲。(當然也許你有更好的實現方法)。
預覽地址:http://blog.cwlserver.top/demo/Tetris.html
1,先理清游戲邏輯
- 游戲場景:場景大小為 10*18,
- 下落時間:初始方塊每隔1秒,會下落一格。隨著游戲進行時間得增加,方塊下落時間間隔會縮短。
- 操作方法:方向鍵得 上下左右 分別控制方塊得, 變形,加速下落,左移,右移。
- 方塊類型:一共7種類型得方塊。每次隨機出現一種, 每種方塊由數個 1*1大小得小方塊組成
- 方塊下落:當方塊落到底, 或者下一格已經被占,方塊停止下落,然後會有一個新的方塊出現
- 方塊左右移動:方塊左右移動時,如果左,右是牆或者是已經被占,方塊將不能移動。
- 方塊變形:方塊逆時針旋轉90°,變形時需要判斷方塊是否可以變形。
- 游戲會有下一個方塊得提示
- 消行:當一行被填滿時,這一行將被消除
- 計分規則: 消1行得2分,2行4分,3行8分,4行16分
- 游戲結束: 當方塊下落到底,並且方塊超出游戲場景時,判定游戲結束
2,分步實現游戲中得功能
html結構
<div id="box">
<canvas id="canvas" width="300" height="540"></canvas>
<div class="scorebox">
<p>游戲已進行: <span id="game-time">00:00:00</span></p><br>
<p>當前得分: <span id="score">0</span></p><br>
<p>下一個方塊:</p><br>
<canvas id="next" width="120" height="120"></canvas><br>
<p class="btns"><button id="pause">暫停</button><button id="restart">重新開始</button></p>
</div>
</div>
構建場景
因為場景大小是10x18,所以我決定用一個 10x18得二維數組來模擬場景,這樣方便和方塊做碰撞檢測。
//定義列數
var ROW = 10;
//定義行數
var COL = 18;
//游戲得分
var SCORE = 0;
//游戲場景
var area = new Array(COL);
for(var i=0; i<area.length; i++){
area[i] = new Array(ROW).fill(0);
}
/*
最終得到得area是這樣得
area = [
[0,0,0,0....]
[0,0,0,0....]
[0,0,0,0....]
...
]
*/
構建小方塊
小方塊我同樣使用二維數組來構建
//定義各種方塊得數組, 一共7種不同得方塊,數組中的1,2,3,4..這些數字主要是為了每個方塊設置不同的顏色
var data = {
'o':[
[1, 1],
[1, 1]
],
's':[
[2, 0, 0],
[2, 2, 0],
[0, 2, 0]
],
'5':[
[0, 0, 3],
[0, 3, 3],
[0, 3, 0]
],
'l':[
[4, 0, 0],
[4, 0, 0],
[4, 4, 0]
],
't':[
[5, 5, 5],
[0, 5, 0],
[0, 0, 0]
],
'j':[
[0, 0, 6],
[0, 0, 6],
[0, 6, 6]
],
'|':[
[0, 7, 0, 0],
[0, 7, 0, 0],
[0, 7, 0, 0],
[0, 7, 0, 0]
]
};
//定義方塊得顏色,每個數字對應一種顏色
var aColor = ['', '#fff', '#0000FF', '#00FF00', '#CC00FF', '#CCFFFF','#FFFF33','#99FFFF'];
//將data中得key放到一個字元串中 方便隨機調用
var sKey = 'os5ltj|';
//定義當前方塊, 當前方塊預設null;
var cur = null;
//因為游戲中會有下一個方塊得提示, 所以這裡要提前聲明一下
var next = null;
//定義一個生成方塊得函數
function createBox(){
//首先創建提示方塊
if(!next){
//從skey中隨機取出一個鍵名
var rnd = Math.floor(Math.random()*