未完成的JS作品之二:应用面向对象思想写的俄罗斯方块

发表于:2007-06-30来源:作者:点击数: 标签:
练手的时候写的,后面写得好乱,8( 比较满意的是方块的储存和旋转,是我见过同类 游戏 中最简洁的 html head title俄罗斯方块/title script /******************************** 俄罗斯方块 Version 1.0beta 2001年10月19日 By 黄砾(Stone) (bbs.online.jx.cn)
练手的时候写的,后面写得好乱,8(

比较满意的是方块的储存和旋转,是我见过同类游戏中最简洁的

<html>
<head>
<title>俄罗斯方块</title>
<script>
/********************************
俄罗斯方块 Version 1.0beta
2001年10月19日 By 黄砾(Stone) (bbs.online.jx.cn)

这段脚本可以免费使用于任何非商业用途。引用时请保留本段说明。

Tetris version 1.0beta
by Li Huang, October 19th 2001
*******************************/

//存储各方块的形状
var Shapes = new Array (
    new Array (2,1,0,0,1,0,2,0,1,1),
    new Array (2,1,0,0,1,0,1,1,2,1),
    new Array (2,1,1,0,2,0,0,1,1,1),
    new Array (1,1,0,0,1,0,0,1,1,1),
    new Array (2,1,0,0,1,0,2,0,0,1),
    new Array (2,1,0,0,1,0,2,0,2,1),
    new Array (3,2,0,1,1,1,2,1,3,1));

function tetris(name,width,height) {
    this.width = width;
    this.height = height;
    document.write(@#<table name=@# + name + @# id=@# + name + @# border=1 cellSpacing=0 bgcolor=#C0C0C0 BORDERCOLOR=#C0C0C0 style=\"font-size:12pt;LINE-HEIGHT:12pt;\">@#);
    for (var y=0;y<this.height;y++) {
        document.write(@#<tr>@#);
        for (var x=0;x<this.width;x++)
            document.write(@#<td width=12 height=12>&nbsp;</td>@#);
        document.write(@#</tr>@#);
    }
    document.write(@#</table>@#);
    this.Box = eval(name);

    this.checkDot = function(x,y) {
        if (x<0 || y<0 || x>=this.width || y>=this.height)
            return false;
        else if (this.Box.rows(y).cells(x).borderColorDark == @##ffffff@#)
            return false;
        else
            return true;
    }
    this.dot = function(x,y) {
        if (this.checkDot(x,y))
            with (this.Box.rows(y).cells(x)) {
                borderColorDark = @##FFFFFF@#;
                borderColorLight = @##808080@#;
            }
    }
    this.clearDot = function(x,y) {
        with (this.Box.rows(y).cells(x)) {
            borderColorDark = @##C0C0C0@#;
            borderColorLight = @##C0C0C0@#;
        }
    }
    this.eraseLine = function() {
        var line = 0, ny=this.height-1;
        for (var y=this.height-1;y>=0;y--) {
            var erase=true;
            for (var x=0;x<this.width;x++)
                if (this.checkDot(x,y)) {
                    this.clearDot(x,ny);
                    erase=false;
                }
                else
                    this.dot(x,ny);
            if (!erase)
                ny--;
            else
                line++;
        }
        return line;
    }
    this.clear=function() {
        for (var y=0;y<this.height;y++)
            for (var x=0;x<this.width;x++)
                this.clearDot(x,y);
    }
}
function pos(x,y) {
    this.x = x;
    this.y = y;
    return this;
}
function block(obj,Shape) {
    this.x = 0;
    this.y = 1;
    this.obj = obj;
    this.shape = new Array();
    for (var i=0;i<Shape.length;i+=2)
        this.shape[i>>1] = new pos(Shape[i],Shape[i+1]);
    this.setObj = function(obj) {
        this.obj = obj;
    }
    this.turn = function() {
        var i,tmp;
          with (this) {
            for (i=1;i<shape.length;i++) {
                tmp = shape[i].y;
                shape[i].y = shape[i].x;
                shape[i].x = shape[0].y - tmp;
            }
            tmp=shape[0].x; shape[0].x=shape[0].y; shape[0].y=tmp;
            if (!check()) {
                for (i=1;i<shape.length;i++) {
                    tmp = shape[i].x;
                    shape[i].x=shape[i].y;
                    shape[i].y=shape[0].x-tmp;
                }
                tmp=shape[0].x; shape[0].x=shape[0].y; shape[0].y=tmp;
            }
        }
    }
    this.check = function() {
        with (this)
            for (var i=1;i<shape.length;i++)
                if (!obj.checkDot(shape[i].x+x,shape[i].y+y))
                    return false;
        return true;
    }
    this.left = function() {
        with (this) {
            x--;
            if (!check())
                x++;
        }
    }
    this.right = function() {
        with (this) {
            x++;
            if (!check())
                x--;
        }
    }
    this.down = function() {
        with (this) {
            y++;
            if (!check()) {
                y--;
                return false;
            }
        }
        return true;
    }
    this.clear = function() {
        with (this)
            for (var i=1;i<shape.length;i++)
                obj.clearDot(shape[i].x+x,shape[i].y+y);
    }
    this.draw = function() {
        with (this)
            for (var i=1;i<shape.length;i++)
                obj.dot(shape[i].x+x,shape[i].y+y);
    }
}

var Hiscore=0, score=0, line=0, level=1, speed=1500, handle=NaN;
    
function keyPlay() {
    Block.clear();
    switch (window.event.keyCode) {
    case 73:
    case 105:Block.turn(); break;
    case 74:
    case 106:Block.left(); break;
    case 75:
    case 107:if (!isNaN(handle))
            window.clearTimeout(handle);
        down();
        break;
    case 76:
    case 108:Block.right();
    }
    Block.draw();
}
function keyWait() {
    if (window.event.keyCode==115 || window.event.keyCode==83)
        gameStart();
}
function gameStart() {
    Message.style.visibility = "hidden";
    score=0; line=0; level=1; speed=1500;

    Tetris.clear();
    Preview.clear();
    show();

    Block = new block(Tetris,Shapes[Math.round(Math.random()*6)]);
    NextBlock = new block(Preview,Shapes[Math.round(Math.random()*6)]);
    Block.draw();
    NextBlock.draw();
    
    handle = window.setTimeout(@#down()@#,speed);
    document.body.onkeypress = keyPlay;
}
function gameOver() {
    handle = NaN;
    document.body.onkeypress = keyWait;
    Message.innerHTML = @#俄罗斯方块 v1.0beta<br><br><font size=5>游戏结束!</font><br><br>按 S 键重新开始,<br>J,K,L键控制方块移动,<br>按 I 键控制方块旋转<br><br>2001-10-19 by 黄砾(stone)<br>http://bbs.online.jx.cn@#;
    Message.style.visibility = @#visible@#;
}
function show() {
    Show.innerHTML = @#<P><b>Hiscore</b><br>@# + Hiscore + @#</P><P><b>Score</b><br>@# + score + @#</P><P><b>Level</b><br>@# + level + @#</P><P><b>Line</b><br>@# + line + @#</P><P> </P><P> </P><P> </P>@#;
}
function down() {
    Block.clear();
    if (!Block.down()) {
        Block.draw();
        var eraseLine = Tetris.eraseLine();
        line += eraseLine;
        score+= 50*((1<<eraseLine)-1);
        if (score>Hiscore)
            Hiscore=score;
        if ((score>>9)>level) {
            level++;
            speed=Math.round(speed/1.3);
            if (speed<80)
                speed=80;
        }
        
        NextBlock.clear();
        Block = NextBlock;
        Block.setObj(Tetris);
        
        show();
        
        if (!Block.check()) {
            gameOver();
            return;
        }
        NextBlock = new block(Preview,Shapes[Math.round(Math.random()*6)]);
        NextBlock.draw();
    }
    Block.draw();
    handle = window.setTimeout("down()",speed);
}
</script>
</head>
<body bgcolor=#C0C0C0>
<div id=Message align=center style="position:absolute; left:30; top:100; width:200; z-index:2; border:2px double white; background-color: #c0c0c0; layer-background-color: #c0c0c0; visibility: hidden"></div>
<table border=2 cellSpacing=2 bgcolor=#C0C0C0 BORDERCOLOR=#C0C0C0>
<tr>
<td BORDERCOLOR=#FFFFFF rowspan=2><script>Tetris = new tetris(@#Box@#,10,20);</script></td>
<td BORDERCOLOR=#FFFFFF align=center><b>NEXT</b><br><script>Preview = new tetris(@#Next@#,4,3);</script></td>
</tr>
<tr>
<td name=Show id=Show BORDERCOLOR=#FFFFFF align=center valign=top>
<P> </P>
<P> </P>
<P> </P>
<P> </P>
<P> </P>
<P> </P>
<P> </P>
</td>
</tr>
</table>
<script>
gameOver();
</script>
</body>
</html>

原文转自:http://www.ltesting.net