最近一直在測(cè)試前些日子寫的俄羅斯方塊(SWT),發(fā)現(xiàn)了幾個(gè)BUG(只能說我還比較菜,沒設(shè)計(jì)好):

1.方塊類Block的clear和draw方法由于兩個(gè)線程(一個(gè)是主線程,一個(gè)是定時(shí)器線程)都要調(diào)用,而且之前我沒做好線程的同步,所以會(huì)隨機(jī)發(fā)生該擦除的方塊沒能及時(shí)擦除,或是兩個(gè)小方塊重合.

修正方法:
主線程是在方塊的左移,右移,下移,變形,直降 即 moveLeft(),moveRight(),moveDown(),rotateClock(),fall() 這些方法中調(diào)用Block的clear和draw方法的,定時(shí)器線程是在線程活動(dòng)時(shí)調(diào)用moveDown(),所以,moveDown()就成了臨界區(qū),不能保證被調(diào)用的順序,所以需要使他們同步,要使他們同步,只需將他們都寫到一個(gè)方法里,即 move(moveSuit type),并且將move方法同步,即加關(guān)鍵字synchronized即可.

2.還是線程沒有同步造成的問題,在定時(shí)器線程活動(dòng)時(shí)會(huì)判斷方塊是否能下落,如果能就下落,在主線程中,按"下"或空格也會(huì)執(zhí)行前句所說的任務(wù),但由于是兩個(gè)線程各自判斷方塊是否能下落,所以判斷是否能下落的方法和下移方法的調(diào)用順序不能被保證,所以有時(shí)會(huì)發(fā)生這樣的情況:按住下,方塊有時(shí)會(huì)下落到超出面板一格,或是幾個(gè)方塊重合,即主線程判斷方塊不能下落,但定時(shí)器線程在主線程判斷方塊不能下落之前,判斷方塊可以下落,于是方塊就多下落了一格,這個(gè)順序?yàn)?定時(shí)線程判斷可以下落 -> 主線程判斷不能下落 -> 主線程不動(dòng) -> 定時(shí)線程讓方塊下落 -> 造成異常發(fā)生或方塊重合現(xiàn)象.

修正方法:
在 move(moveSuit type)方法的MOVEDOWN情況中,再一次判斷方塊是否能下落,move(moveSuit type)方法是同步的,所以可以很好的解決這個(gè)問題.

1,2修正后代碼如下:
public enum MoveSuit {
        MOVELEFT,
        MOVERIGHT,
        MOVEDOWN,
        ROTATE,
        FALL
    }


    
//移動(dòng)方法,通過移動(dòng)類型決定如何移動(dòng)
    public synchronized void move(MoveSuit type, TetrisBoard tetrisBoard){
        
        
switch(type){
        
        
case MOVELEFT:
            moveLeft();
            
break;
        
case MOVERIGHT:
            moveRight();
            
break;
        
case MOVEDOWN:
            
if(tetrisBoard.canMoveDown(this))
                moveDown();
            
break;
        
case ROTATE:
            clear();
            rotateClock().draw();
            
break;
        
case FALL:
            fall(tetrisBoard);
            
break;
            
        }

    }


3.如果GameOver一次以后再TryAgain,游戲等級(jí)和方塊下落間隔會(huì)在分?jǐn)?shù)到達(dá)100分左右時(shí)突然變到剛才GameOver時(shí)的最高等級(jí)和方塊下落間隔.

修正方法:
游戲等級(jí)和方塊下落間隔都是通過消行總數(shù)判斷的,之前我忘記再每次游戲開始時(shí)將消行總數(shù)設(shè)為0,所以只需要在TetrisBoard類中加一個(gè)setRemovedLines方法,在Game類中的startGame方法中調(diào)用setRemovedLines(0)即可.

4.每個(gè)小方塊的邊框原來我設(shè)為了白色,在兩個(gè)大方塊相臨時(shí)會(huì)將其中一個(gè)大方塊的一部分邊框擦除,比較難看,如果把小方塊長(zhǎng)寬縮小一個(gè)象素,當(dāng)兩個(gè)大方塊相臨時(shí),銜接處就會(huì)有兩個(gè)邊框,也不是很好看.

修正方法:將邊框顏色設(shè)為背景色黑色,這樣邊框被擦除也看不出來,兩個(gè)大方塊銜接處只有一個(gè)邊框,可以兩全其美.雖然這個(gè)方法不太好...


BUG說完了,該說說新功能了,呵呵~

我又添加了一個(gè)可以記錄并顯示最好成績(jī)信息的功能,玩游戲總得有個(gè)奔頭么,嘿嘿!
第一次玩游戲時(shí),最高分為0,最高等級(jí)為1,創(chuàng)造者姓名為"Are you the winner?"
當(dāng)游戲gameover時(shí),如果當(dāng)前游戲分?jǐn)?shù)大于最高分,就讓玩家輸入自己姓名,并將其和最高分?jǐn)?shù),等級(jí)加密后存入myTetris.dat.
重新打開游戲時(shí),會(huì)從myTetris.dat中讀取信息并解密,并將最高分,最高等級(jí)和最高分創(chuàng)造者顯示在游戲界面上

最后添張圖:


最后把jar包和源代碼放出來!希望大家給我留言,互相交流,嘿嘿!
以前忘說了,如果想讓幫助正常顯示的話,需要在和jar包同級(jí)目錄下新建個(gè)文件夾叫pics,然后在里面放一個(gè)叫l(wèi)ogo的圖片.
myTetris下載地址
謝謝大家對(duì)我的支持!


 



what the hell is going on ??!!