上節中講了如何尋路,在和朋友們討論時都反應有時走的不太對,繞遠路了,其實代碼主要是大方向的判斷 比如目標在右上,那應該是先右還是先上 這個並沒有做處理,如果這個做了處理,效果會更好一些,但也難免會走彎路。 貪心就是這樣,不是最優,接近最優。也希望其他的同學有意見的可以討論下。我這也只是個人想法。
既然可以走動了,那就可以判斷是否可以消除同樣顏色的行、列或斜線了。只要>=5個同樣的色球,就清除他們,並且可以繼續移動。如果不可以清除,那就再增加3個球。
clearLine: function (x1, y1, color, isClick) { if (this.isEmpty(x1, y1)) { if (isClick) game.ready.flyin(); return; }; //給定一個坐標,看是否有滿足的line可以被消除 //4根線 一 | / \ var current = this.getBubble(x1, y1); if (!current.color) { console.log(current); } var arr1, arr2, arr3, arr4; arr1 = this.bubbles[y1];//橫線很簡單,就是數組的一項,現成的 arr2 = []; for (var y = 0; y < game.cellCount; y++) arr2.push(this.getBubble(x1, y));//豎線就是一列。 arr3 = [current]; arr4 = [current]; for (var i = 1; i < game.cellCount ; i++) { if (x1 - i >= 0 && y1 - i >= 0)//\斜線的上半部分... arr3.unshift(this.getBubble(x1 - i, y1 - i)); if (x1 + i < game.cellCount && y1 + i < game.cellCount)//\斜線的下半部分 arr3.push(this.getBubble(x1 + i, y1 + i)); if (x1 - i >= 0 && y1 + i < game.cellCount)// /斜線的下半部分 arr4.push(this.getBubble(x1 - i, y1 + i)); if (x1 + i < game.cellCount && y1 - i >= 0)// /斜線的上班部分 arr4.unshift(this.getBubble(x1 + i, y1 - i)); } var line1 = getLine(arr1); var line2 = getLine(arr2); var line3 = getLine(arr3); var line4 = getLine(arr4); var line = line1.concat(line2).concat(line3).concat(line4); if (line.length < 5) { if (isClick) game.ready.flyin(); return; } else { var me = this; var i = 0; game.play("clearline", function () { if (i == line.length) { game.score.addScore(line.length); game.stop("clearline"); me.isMoving = false; //game.ready.flyin(); return; } me.isMoving = true; var p = line[i]; me.setBubble(p.x, p.y, null); i++; }, 100); } function getLine(bubbles) { var line = []; for (var i = 0; i < bubbles.length; i++) { var b = bubbles[i]; if (b.color == color) { line.push({ "x": b.x, "y": b.y }); } else { if (line.length < 5) line = []; else return line; } } if (line.length < 5) return []; return line; } },
大家可以看看代碼,主要有兩點 1、或許需要處理的 橫豎斜線 4個數組,然后看這4個數組是否有連續的。判斷是否連續只需要一個狀態數組來維持就可以了。
由於考慮到同時消除多行的情況,所以要把連續的line 連接在一起,並在結算得分時考慮獎勵。
isClick參數主要用於判斷是否是用戶點擊進行消行的還是新泡泡飛入產生的。 如果達不到消行條件並且是飛入的,那就不能再調用飛入了,否則死循環了。
滿足的消行代碼也比較簡單,就是播放一個消行動畫,其實這個動畫真心沒勁,要想設計好些可以做個漸變偏移消除。 現在我發現起初沒有設計一個數組來維護狀態有些不太明智,因為還有獎勵的星星和炸彈要繪制,挺麻煩的。。 那么,把積分顯示出來吧。 這樣就可以先試玩起來了:)
game.score = { basic: 0, operate: 0, star1: 0, star2: 0, boom: 0, draw: function () { var startX = game.cellWidth * 10 + game.map.startX; var startY = game.map.startY; var ctx = game.ctx; ctx.save(); ctx.translate(startX, startY); ctx.clearRect(0, 0, 150, 400); ctx.strokeStyle = "#456"; //ctx.strokeRect(0, 0, 150, 200); ctx.font = "24px 微軟雅黑"; ctx.fillStyle = "#fefefe"; ctx.fillText("score:" + (this.basic * 5 + this.star1 * 8 + this.star2 * 10 + this.boom * 20), 0, 30); ctx.stroke(); ctx.restore(); }, addScore: function (length) { switch (length) { case 5: this.basic++; break; case 6: this.star1++; break; case 7: this.star2++; break; default: this.boom++; break; } this.draw(); console.log(this.score); }, };
第三節在設計里談到了 百搭星和炸彈,我太懶了,不打算講了,因為這些處理也沒有什么復雜的,HTML5 Canvas的的基礎學習也算可以了。后面應該學一些更深入的東西,比如如何處理性能、物體碰撞、運動學神馬的。。。
現在游戲應該還有bug,大家可以看看代碼發現吧,這個系列就到這了,謝謝大家。
試玩地址:http://zhengliangjun.sinaapp.com/colorline.html
源碼下載:http://download.csdn.net/download/maddemon/4154990