`

俄罗斯方块

    博客分类:
  • ajax
阅读更多
1.初始化下方块组合的图形阶面
//方块的大小
SQUARE_SIZE = 16;
//背景的宽度和高度
BACKGROUND_WIDTH = 336;
BACKGROUND_HEIGHT = 343;
//方块区最左上角的方块位置的水平偏移距离
X_OFFSET = 134;
//方块区最左上角的方块位置的垂直偏移距离
Y_OFFSET = 4;
//下一个方块组合的位置的水平偏移距离
X_OFFSET_NEXT = 47;
//下一个方块组合的位置的垂直偏移距离
Y_OFFSET_NEXT = 8;
//下一个再下一个方块组合的位置的水平偏移距离
X_OFFSET_NEXT_NEXT = 47;
//下一个再下一个方块组合的位置的垂直偏移距离
Y_OFFSET_NEXT_NEXT = 84;

//方块区水平方向的容量
HORIZONTAL_COUNT = 12;
//方块区垂直方向的容量
VERTICAL_COUNT = 21;
//方块在水平方向的出发点(在中间,即索引为5)
INIT_HORIZONTAL_POS = 5;
//方块在垂直方向的出发点(第二格,即索引为1)
INIT_VERTICAL_POS = 1;

//目标对象的漂浮层
LOW_Z_INDEX = 3;
HIGH_Z_INDEX = 10;

//每个方块组合组由4 个方块组成
BLOCKS_SIZE = 4;
//方块组合的类型(7种方块组合和空方块)
SQUARE = 0;
BLOCKS_1 = 1;
BLOCKS_2 = 2;
BLOCKS_3 = 3;
BLOCKS_4 = 4;
BLOCKS_5 = 5;
LONG = 6;
NOTHING = 7;
//方块组合的类型的个数
TYPE_COUNT = 8;
//方块组合的方向的个数
DIRECTION = 4;

//下面的位图路径数组分别代表七种不同的方块及空方块
var squareImagePath = [];
squareImagePath[NOTHING] = "image/nothing.jpg";
squareImagePath[SQUARE] = "image/square0.jpg";
squareImagePath[BLOCKS_1] = "image/square1.jpg";
squareImagePath[BLOCKS_2] = "image/square2.jpg";
squareImagePath[BLOCKS_3] = "image/square3.jpg";
squareImagePath[BLOCKS_4] = "image/square4.jpg";
squareImagePath[BLOCKS_5] = "image/square5.jpg";
squareImagePath[LONG] = "image/square6.jpg";
//下面的位图路径数组分别代表七种不同的方块组合及空方块
var nextBlockImagePath = [];
nextBlockImagePath[NOTHING] = "image/nextnothing.jpg";
nextBlockImagePath[SQUARE] = "image/nextblock0.jpg";
nextBlockImagePath[BLOCKS_1] = "image/nextblock1.jpg";
nextBlockImagePath[BLOCKS_2] = "image/nextblock2.jpg";
nextBlockImagePath[BLOCKS_3] = "image/nextblock3.jpg";
nextBlockImagePath[BLOCKS_4] = "image/nextblock4.jpg";
nextBlockImagePath[BLOCKS_5] = "image/nextblock5.jpg";
nextBlockImagePath[LONG] = "image/nextblock6.jpg";

//记录方块的位图的数组(1D)
var squareImage = [];
//记录已经着地方块的类型的数组(2D)
var fellBlocks = [];
////记录修改前的已经着地方块的类型的数组(2D)
//var fellBlocksBeforeModify = [];
//记录已经着地方块的图形的容器的数组(2D)
fellBlocksDiv = [];
//记录再下一个方块组合的图形
var nextImage;
//记录再下一个再下一个方块组合的图形
var nextAndNextImage;


//初始化方块的位图的数组
for (type = 0; type < TYPE_COUNT; type ++)
{
	image = document.createElement("img");
	image.src = squareImagePath[type];
	squareImage[type] = image;
}

//初始化已经着地方块的图形的容器
for (i = 0; i < HORIZONTAL_COUNT; i ++)
{
	//变为二维数组
	fellBlocks[i] = [];
//	fellBlocksBeforeModify[i] = [];
	fellBlocksDiv[i] = [];
	for (j = 0; j < VERTICAL_COUNT; j ++)
	{	
		fellBlocks[i][j] = NOTHING;
//		fellBlocksBeforeModify[i][j] = NOTHING;
		
		//新建DIV元素
		div = document.createElement("div");
		//通过style属性对容器进行定位
		div.style.position = "absolute";
		div.style.left = i * SQUARE_SIZE + X_OFFSET;
		div.style.top = j * SQUARE_SIZE + Y_OFFSET;
		div.style.zIndex = HIGH_Z_INDEX;
		//把容器记录到二维数组
		fellBlocksDiv[i][j] = div;
		document.getElementById("BackGroundArea").appendChild(div);
		
		//复制图像元素
		image = squareImage[NOTHING].cloneNode(true);
		//把图像添加到对应的容器
		div.appendChild(image);

	}
}


//初始化下一个方块组合的图形
image = document.createElement("img");
image.src = nextBlockImagePath[NOTHING];
image.style.position = "absolute";
image.style.left = X_OFFSET_NEXT;
image.style.top = Y_OFFSET_NEXT;
image.style.zIndex = 10;
nextImage = image;
document.getElementById("BackGroundArea").appendChild(image);

//初始化下一个再下一个方块组合的图形
image = document.createElement("img");
image.src = nextBlockImagePath[NOTHING];
image.style.position = "absolute";
image.style.left = X_OFFSET_NEXT_NEXT;
image.style.top = Y_OFFSET_NEXT_NEXT;
image.style.zIndex = 10;
nextAndNextImage = image;
document.getElementById("BackGroundArea").appendChild(image);

image.src = squareImagePath[NOTHING];
div.style.zIndex = HIGH_Z_INDEX;

2.初始化新的方块组合,并处理方块组合
//定义类FallingBlocks
function FallingBlocks()
{
	//方块组合的方向
	this.direction;
	this.directionCount = 0;
	//方块组合横、纵坐标数组(每个方块组合组由4 个方块组成)
	this.x = [];
	this.y = [];
	//方块组合的重心的横、纵坐标
	this.xOfHeart;
	this.yOfHeart;
	//方块组合下落一格后的横、纵坐标数组(每个方块组合组由4 个方块组成)
	this.xPos = [];
	this.yPos = [];
	//方块组合下落一格后的重心的横、纵坐标
	this.xPosOfHeart;
	this.yPosOfHeart;
	
	//方块组合的类型(7种方块组合和空方块)
	this.type;
	//下一个方块组合的类型
	temp = Math.random() * 6;
	this.typeOfNext = Math.floor(temp);
	//下一个再下一个方块组合的类型
	temp = Math.random() * 6;
	this.typeOfNextAndNext = Math.floor(temp);

	//初始化新的方块组合,并把它放在最顶的位置
	this.initFallingBlocks;
	//根据方块组合的类型,及其重心的位置,测试它的形状(即计算各个方块的位置)
	this.testBlocksShape;
	//把完成测试的形状记录到方块组合的位置坐标
	this.saveBlocksShape;
	//设定SQUARE
	this.setSquare;
	//设定LONG
	this.setLong;
	//设定BLOCKS_1
	this.setBlocks1;
	//设定BLOCKS_2
	this.setBlocks2;
	//设定BLOCKS_3
	this.setBlocks3;
	//设定BLOCKS_4
	this.setBlocks4;
	//设定BLOCKS_5
	this.setBlocks5;
	//检查方块的坐标是否超出范围
	this.isOut;
	//绘制正在下落的方块组合
	this.paintFallingBlocks;
	//处理着地的方块组合
	this.processFellBlocks;
}

//初始化新的方块组合,并把它放在最顶的位置
FallingBlocks.prototype.initFallingBlocks = function()
{
	//获得当前方块组合的类型
	this.type = this.typeOfNext;
	//获得下一个方块组合的类型
	this.typeOfNext = this.typeOfNextAndNext;
	//设定下一个再下一个方块组合的类型
	temp = Math.random() * 6;
	this.typeOfNextAndNext = Math.floor(temp);
	//每30个方块组合,出现一次长条
	this.directionCount ++;
	if (this.directionCount % 30 == 0)
	{
		this.typeOfNextAndNext = LONG;
	}
	//设定方块组合的重心的初始横、纵坐标
	this.xPosOfHeart = INIT_HORIZONTAL_POS;
	this.yPosOfHeart = INIT_VERTICAL_POS;
	//重新把方块组合的方向变为0
	this.direction = 0;
	//若测试的形状符合要求,则记录方块组合的形状
	if (this.testBlocksShape())
	{
		this.saveBlocksShape();
		//绘制正在下落的方块组合
		this.paintFallingBlocks();
	}
}


//根据方块组合的类型,及其重心的位置,测试它的形状(即计算各个方块的位置)
FallingBlocks.prototype.testBlocksShape = function()
{
	//对方块组合的类型分类处理
	switch (this.type)
	{
	case SQUARE:
		this.setSquare();
		break;
	case LONG:
		this.setLong();
		break;
	case BLOCKS_1:
		this.setBlocks1();
		break;
	case BLOCKS_2:
		this.setBlocks2();
		break;
	case BLOCKS_3:
		this.setBlocks3();
		break;
	case BLOCKS_4:
		this.setBlocks4();
		break;
	case BLOCKS_5:
		this.setBlocks5();
		break;
	}
	//测试新的形状是否符合要求
	for (var i = 0; i < BLOCKS_SIZE; i ++)
	{
		//若第i 个方块的坐标超出范围
		if (this.isOut(this.xPos[i], this.yPos[i]))
		{
			return false;
		}
		//若第i 个方块的坐标有已经着地的方块
		if (tetris.fellBlocks[this.xPos[i]][this.yPos[i]] != NOTHING )
		{
			return false;
		}
	}
	return true;
}


//把完成测试的形状记录到方块组合的位置坐标
FallingBlocks.prototype.saveBlocksShape = function()
{
	this.xOfHeart = this.xPosOfHeart;
	this.yOfHeart = this.yPosOfHeart;
	for (var i = 0; i < BLOCKS_SIZE; i ++)
	{
		this.x[i] = this.xPos[i];
		this.y[i] = this.yPos[i];
	}
}

//设定SQUARE
FallingBlocks.prototype.setSquare = function()
{
	switch (this.direction)
	{
	//4个方向都一样
	case 0:
	case 1:
	case 2:
	case 3:
		this.xPos[0] = this.xPosOfHeart;
		this.yPos[0] = this.yPosOfHeart;
		this.xPos[1] = this.xPosOfHeart + 1;
		this.yPos[1] = this.yPosOfHeart;
		this.xPos[2] = this.xPosOfHeart;
		this.yPos[2] = this.yPosOfHeart + 1;
		this.xPos[3] = this.xPosOfHeart + 1;
		this.yPos[3] = this.yPosOfHeart + 1;
		break;
	}
}


//设定LONG
FallingBlocks.prototype.setLong = function()
{
	switch (this.direction)
	{
	//两个方向都一样
	case 0:
	case 2:
		this.xPos[0] = this.xPosOfHeart - 1;
		this.yPos[0] = this.yPosOfHeart;
		this.xPos[1] = this.xPosOfHeart;
		this.yPos[1] = this.yPosOfHeart;
		this.xPos[2] = this.xPosOfHeart + 1;
		this.yPos[2] = this.yPosOfHeart;
		this.xPos[3] = this.xPosOfHeart + 2;
		this.yPos[3] = this.yPosOfHeart;
		break;
	//两个方向都一样
	case 1:
	case 3:
		this.xPos[0] = this.xPosOfHeart;
		this.yPos[0] = this.yPosOfHeart - 1;
		this.xPos[1] = this.xPosOfHeart;
		this.yPos[1] = this.yPosOfHeart;
		this.xPos[2] = this.xPosOfHeart;
		this.yPos[2] = this.yPosOfHeart + 1;
		this.xPos[3] = this.xPosOfHeart;
		this.yPos[3] = this.yPosOfHeart + 2;
		break;
	}
}

//设定BLOCKS_1
FallingBlocks.prototype.setBlocks1 = function()
{
	switch (this.direction)
	{
	case 0:
		this.xPos[0] = this.xPosOfHeart - 1;
		this.yPos[0] = this.yPosOfHeart;
		this.xPos[1] = this.xPosOfHeart;
		this.yPos[1] = this.yPosOfHeart;
		this.xPos[2] = this.xPosOfHeart + 1;
		this.yPos[2] = this.yPosOfHeart;
		this.xPos[3] = this.xPosOfHeart;
		this.yPos[3] = this.yPosOfHeart - 1;
		break;
	case 1:
		this.xPos[0] = this.xPosOfHeart;
		this.yPos[0] = this.yPosOfHeart - 1;
		this.xPos[1] = this.xPosOfHeart;
		this.yPos[1] = this.yPosOfHeart;
		this.xPos[2] = this.xPosOfHeart;
		this.yPos[2] = this.yPosOfHeart + 1;
		this.xPos[3] = this.xPosOfHeart + 1;
		this.yPos[3] = this.yPosOfHeart;
		break;
	case 2:
		this.xPos[0] = this.xPosOfHeart - 1;
		this.yPos[0] = this.yPosOfHeart;
		this.xPos[1] = this.xPosOfHeart;
		this.yPos[1] = this.yPosOfHeart;
		this.xPos[2] = this.xPosOfHeart + 1;
		this.yPos[2] = this.yPosOfHeart;
		this.xPos[3] = this.xPosOfHeart;
		this.yPos[3] = this.yPosOfHeart + 1;
		break;
	case 3:
		this.xPos[0] = this.xPosOfHeart;
		this.yPos[0] = this.yPosOfHeart - 1;
		this.xPos[1] = this.xPosOfHeart;
		this.yPos[1] = this.yPosOfHeart;
		this.xPos[2] = this.xPosOfHeart;
		this.yPos[2] = this.yPosOfHeart + 1;
		this.xPos[3] = this.xPosOfHeart - 1;
		this.yPos[3] = this.yPosOfHeart;
		break;
	}
}


//设定BLOCKS_2
FallingBlocks.prototype.setBlocks2 = function()
{
	switch (this.direction)
	{
	//两个方向都一样
	case 0:
	case 2:
		this.xPos[0] = this.xPosOfHeart - 1;
		this.yPos[0] = this.yPosOfHeart;
		this.xPos[1] = this.xPosOfHeart;
		this.yPos[1] = this.yPosOfHeart;
		this.xPos[2] = this.xPosOfHeart;
		this.yPos[2] = this.yPosOfHeart + 1;
		this.xPos[3] = this.xPosOfHeart + 1;
		this.yPos[3] = this.yPosOfHeart + 1;
		break;
	//两个方向都一样
	case 1:
	case 3:
		this.xPos[0] = this.xPosOfHeart;
		this.yPos[0] = this.yPosOfHeart - 1;
		this.xPos[1] = this.xPosOfHeart;
		this.yPos[1] = this.yPosOfHeart;
		this.xPos[2] = this.xPosOfHeart - 1;
		this.yPos[2] = this.yPosOfHeart;
		this.xPos[3] = this.xPosOfHeart - 1;
		this.yPos[3] = this.yPosOfHeart + 1;
		break;
	}
}


//设定BLOCKS_3
FallingBlocks.prototype.setBlocks3 = function()
{
	switch (this.direction)
	{
	//两个方向都一样
	case 0:
	case 2:
		this.xPos[0] = this.xPosOfHeart + 1;
		this.yPos[0] = this.yPosOfHeart;
		this.xPos[1] = this.xPosOfHeart;
		this.yPos[1] = this.yPosOfHeart;
		this.xPos[2] = this.xPosOfHeart;
		this.yPos[2] = this.yPosOfHeart + 1;
		this.xPos[3] = this.xPosOfHeart - 1;
		this.yPos[3] = this.yPosOfHeart + 1;
		break;
	//两个方向都一样
	case 1:
	case 3:
		this.xPos[0] = this.xPosOfHeart - 1;
		this.yPos[0] = this.yPosOfHeart - 1;
		this.xPos[1] = this.xPosOfHeart - 1;
		this.yPos[1] = this.yPosOfHeart;
		this.xPos[2] = this.xPosOfHeart;
		this.yPos[2] = this.yPosOfHeart;
		this.xPos[3] = this.xPosOfHeart;
		this.yPos[3] = this.yPosOfHeart + 1;
		break;
	}
}


//设定BLOCKS_4
FallingBlocks.prototype.setBlocks4 = function()
{
	switch (this.direction)
	{
	case 0:
		this.xPos[0] = this.xPosOfHeart - 1;
		this.yPos[0] = this.yPosOfHeart;
		this.xPos[1] = this.xPosOfHeart - 1;
		this.yPos[1] = this.yPosOfHeart + 1;
		this.xPos[2] = this.xPosOfHeart;
		this.yPos[2] = this.yPosOfHeart + 1;
		this.xPos[3] = this.xPosOfHeart + 1;
		this.yPos[3] = this.yPosOfHeart + 1;
		break;
	case 1:
		this.xPos[0] = this.xPosOfHeart;
		this.yPos[0] = this.yPosOfHeart - 1;
		this.xPos[1] = this.xPosOfHeart - 1;
		this.yPos[1] = this.yPosOfHeart - 1;
		this.xPos[2] = this.xPosOfHeart - 1;
		this.yPos[2] = this.yPosOfHeart;
		this.xPos[3] = this.xPosOfHeart - 1;
		this.yPos[3] = this.yPosOfHeart + 1;
		break;
	case 2:
		this.xPos[0] = this.xPosOfHeart - 1;
		this.yPos[0] = this.yPosOfHeart;
		this.xPos[1] = this.xPosOfHeart;
		this.yPos[1] = this.yPosOfHeart;
		this.xPos[2] = this.xPosOfHeart + 1;
		this.yPos[2] = this.yPosOfHeart;
		this.xPos[3] = this.xPosOfHeart + 1;
		this.yPos[3] = this.yPosOfHeart + 1;
		break;
	case 3:
		this.xPos[0] = this.xPosOfHeart + 1;
		this.yPos[0] = this.yPosOfHeart - 1;
		this.xPos[1] = this.xPosOfHeart + 1;
		this.yPos[1] = this.yPosOfHeart;
		this.xPos[2] = this.xPosOfHeart + 1;
		this.yPos[2] = this.yPosOfHeart + 1;
		this.xPos[3] = this.xPosOfHeart;
		this.yPos[3] = this.yPosOfHeart + 1;
		break;
	}
}


//设定BLOCKS_5
FallingBlocks.prototype.setBlocks5 = function()
{
	switch (this.direction)
	{
	case 0:
		this.xPos[0] = this.xPosOfHeart + 1;
		this.yPos[0] = this.yPosOfHeart;
		this.xPos[1] = this.xPosOfHeart + 1;
		this.yPos[1] = this.yPosOfHeart + 1;
		this.xPos[2] = this.xPosOfHeart;
		this.yPos[2] = this.yPosOfHeart + 1;
		this.xPos[3] = this.xPosOfHeart - 1;
		this.yPos[3] = this.yPosOfHeart + 1;
		break;
	case 1:
		this.xPos[0] = this.xPosOfHeart - 1;
		this.yPos[0] = this.yPosOfHeart - 1;
		this.xPos[1] = this.xPosOfHeart - 1;
		this.yPos[1] = this.yPosOfHeart;
		this.xPos[2] = this.xPosOfHeart - 1;
		this.yPos[2] = this.yPosOfHeart + 1;
		this.xPos[3] = this.xPosOfHeart;
		this.yPos[3] = this.yPosOfHeart + 1;
		break;
	case 2:
		this.xPos[0] = this.xPosOfHeart - 1;
		this.yPos[0] = this.yPosOfHeart;
		this.xPos[1] = this.xPosOfHeart;
		this.yPos[1] = this.yPosOfHeart;
		this.xPos[2] = this.xPosOfHeart + 1;
		this.yPos[2] = this.yPosOfHeart;
		this.xPos[3] = this.xPosOfHeart - 1;
		this.yPos[3] = this.yPosOfHeart + 1;
		break;
	case 3:
		this.xPos[0] = this.xPosOfHeart;
		this.yPos[0] = this.yPosOfHeart - 1;
		this.xPos[1] = this.xPosOfHeart + 1;
		this.yPos[1] = this.yPosOfHeart - 1;
		this.xPos[2] = this.xPosOfHeart + 1;
		this.yPos[2] = this.yPosOfHeart;
		this.xPos[3] = this.xPosOfHeart + 1;
		this.yPos[3] = this.yPosOfHeart + 1;
		break;
	}
}


//检查方块的坐标是否超出范围
FallingBlocks.prototype.isOut = function(x, y)
{
	if (x < 0 || x >= HORIZONTAL_COUNT)
	{
		return true;
	}
	if (y >= VERTICAL_COUNT)
	{
		return true;
	}
	return false;
}


//绘制正在下落的方块组合(被Tetris调用的方法)
FallingBlocks.prototype.paintFallingBlocks = function()
{
	//清空之前的
	for (var i = 0; i < BLOCKS_SIZE; i ++)
	{
		//暂存对应的DIV
		div = fellBlocksDiv[this.x[i]][this.y[i]];
		//旧的图像元素
		oldImage = div.firstChild;
		//新的图像元素
		newImage = squareImage[NOTHING].cloneNode(true);
		//替换图像元素
		div.replaceChild(newImage, oldImage);
	}
	//绘制当前的
	for (var i = 0; i < BLOCKS_SIZE; i ++)
	{
		//暂存对应的DIV
		div = fellBlocksDiv[this.xPos[i]][this.yPos[i]];
		//旧的图像元素
		oldImage = div.firstChild;
		//新的图像元素
		newImage = squareImage[this.type].cloneNode(true);
		//替换图像元素
		div.replaceChild(newImage, oldImage);
	}
}


//处理着地的方块组合(被Tetris调用的方法)
FallingBlocks.prototype.processFellBlocks = function()
{
	//计算方块组合最低的位置和最高的位置
	tetris.lowest = INIT_VERTICAL_POS;
	//记录方块组合到已经着地方块
	for (var i = 0; i < BLOCKS_SIZE; i ++)
	{
		tetris.fellBlocks[this.x[i]][this.y[i]] = this.type;
		//修改最低的位置(lowest越大,位置越低)
		if (tetris.lowest < this.y[i])
		{
			tetris.lowest = this.y[i];
		}
	}
	
	//遍历所有已经着地方块
	findHighest:
	for (j = 0; j < VERTICAL_COUNT; j ++)
	{
		for (i = 0; i < HORIZONTAL_COUNT; i ++)
		{
			//找到已经着地方块的最高位置
			if (tetris.fellBlocks[i][j] != NOTHING)
			{
				tetris.highest = j;
				break findHighest;
			}
		}
	}
	//如果最低的位置已经在垂直方向的出发点,则认为游戏已经结束
	if (tetris.lowest <= INIT_VERTICAL_POS)
	{
		tetris.isLose = true;
		return;
	}

	nextRow:
	//搜索消减方块(从最低位置的那行遍历到垂直方向出发点的下面一行)
	for (var j = tetris.lowest; j > INIT_VERTICAL_POS; )
	{
		//假设这行全部是空
		isAllEmpty = true;
		//假设这行全部是满
		isAllFull = true;
		//遍历每一行
		for (var i = 0; i < HORIZONTAL_COUNT; i ++)
		{
			//若这格是空
			if (tetris.fellBlocks[i][j] == NOTHING)
			{
				isAllFull = false;
			}
			//若这格是满
			else
			{
				isAllEmpty = false;
			}
			//若已经不是全满且已经不是全空
			if (! isAllFull && ! isAllEmpty)
			{
				//搜索上面的一行
				j --;
				continue nextRow;
			}
		}
		//若这行全部是满,删除这一行
		if (isAllFull)
		{
			for (var jMove = j; jMove > INIT_VERTICAL_POS; jMove --)
			{
				for (var iMove = 0; iMove < HORIZONTAL_COUNT; iMove ++)
				{
					//向下移动一格
					tetris.fellBlocks[iMove][jMove] = 
						tetris.fellBlocks[iMove][jMove - 1];
				}
			}
			//继续遍历这一行
			continue;
		}
		//若这行全部是空,完成消减方块,退出循环
		if (isAllEmpty)
		{
			break;
		}
	}

	//检查游戏是否结束
	for (var i = 0; i < HORIZONTAL_COUNT; i ++)
	{
		//若在第二行有一个格不是空
		if (tetris.fellBlocks[i][INIT_VERTICAL_POS] != NOTHING)
		{
			tetris.isLose = true;
			break;
		}
	}
	this.initFallingBlocks();
}

3.键盘监听,及方块组合的形状规律
//定义类Tetris
function Tetris()
{
	//已经着地方块的类型的数组
	this.fellBlocks = fellBlocks;
	//定义正在下落的方块组合
	this.fallingBlocks;
	//游戏是否结束的旗标
	this.isLose = false;

	//处理按下键盘的函数
	this.keyPressed;
	//定义每1 秒执行一次的事件监听器
	this.timer;
	//总的初始化的方法
	this.init;
	//用于重绘图象的方法
	this.repaint;
	//绘制已经着地方块
	this.paintFellBlocks;
	//定义所有方块最高的位置
	this.highest;
	//定义方块组合最低的位置
	this.lowest;
}

//定义键盘监听的函数
Tetris.prototype.keyPressed = function(event)
{
	fallingBlocks = tetris.fallingBlocks;
	//兼容IE和Firefox
	if (event == null)
	{
		curKey = window.event.keyCode;
	}
	else
	{
		curKey = event.charCode;
	}
	switch (curKey)
	{
	//按下向左键或A键时,方块向左移动一格
	case 97:
	case 65:
		//测试的横坐标减1
		fallingBlocks.xPosOfHeart --;
		//若测试的形状符合要求,则记录方块组合的形状
		if (fallingBlocks.testBlocksShape())
		{
			//绘制正在下落的方块组合
			fallingBlocks.paintFallingBlocks();
			fallingBlocks.saveBlocksShape();
		}
		//否则还原横坐标
		else
		{
			fallingBlocks.xPosOfHeart ++;
		}
		break;
	//按下向右键或D键时,方块向右移动一格
	case 100:
	case 68:
		//测试的横坐标加1
		fallingBlocks.xPosOfHeart ++;
		//若测试的形状符合要求,则记录方块组合的形状
		if (fallingBlocks.testBlocksShape())
		{
			//绘制正在下落的方块组合
			fallingBlocks.paintFallingBlocks();
			fallingBlocks.saveBlocksShape();
		}
		//否则还原横坐标
		else
		{
			fallingBlocks.xPosOfHeart --;
		}
		break;
	//按下向上键或W键时,方块向下移动一格
	case 119:
	case 87:
		//测试的纵坐标加1
		fallingBlocks.yPosOfHeart ++;
		//若测试的形状符合要求,则记录方块组合的形状
		if (fallingBlocks.testBlocksShape())
		{
			//绘制正在下落的方块组合
			fallingBlocks.paintFallingBlocks();
			fallingBlocks.saveBlocksShape();
		}
		//否则还原纵坐标
		else
		{
			fallingBlocks.yPosOfHeart --;
		}
		break;
	//按下向下键或D键时,方块向下移动到尽头
	case 115:
	case 83:
		while (true)
		{
			//测试的纵坐标加1
			fallingBlocks.yPosOfHeart ++;
			//若测试的形状符合要求,则记录方块组合的形状
			if (fallingBlocks.testBlocksShape())
			{
				//绘制正在下落的方块组合
				fallingBlocks.paintFallingBlocks();
				fallingBlocks.saveBlocksShape();
			}
			//否则还原纵坐标,处理着地的方块组合
			else
			{
				fallingBlocks.yPosOfHeart --;
				fallingBlocks.processFellBlocks();
				tetris.repaint();
				//跳出循环,终止向下移动
				break;
			}
		}
		break;
	//按下小键盘1键或J键时,方块向顺时针转动
	case 106:
	case 74:
		//测试的方向加1
		fallingBlocks.direction = 
			(fallingBlocks.direction + 1) % 4;
		//若测试的形状符合要求,则记录方块组合的形状
		if (fallingBlocks.testBlocksShape())
		{
			//绘制正在下落的方块组合
			fallingBlocks.paintFallingBlocks();
			fallingBlocks.saveBlocksShape();
		}
		//否则还原方向
		else
		{
			fallingBlocks.direction = 
			(fallingBlocks.direction - 1 + 4) % 4;
		}
		break;
	//按下小键盘2键或K键时,方块向逆时针转动
	case 107:
	case 75:
		//测试的方向减1
		fallingBlocks.direction = 
		(fallingBlocks.direction - 1 + 4) % 4;
		//若测试的形状符合要求,则记录方块组合的形状
		if (fallingBlocks.testBlocksShape())
		{
			//绘制正在下落的方块组合
			fallingBlocks.paintFallingBlocks();
			fallingBlocks.saveBlocksShape();
		}
		//否则还原方向
		else
		{
			fallingBlocks.direction = 
			(fallingBlocks.direction + 1) % 4;
		}
		break;
	}
}



//定义每1 秒执行一次的事件监听器
Tetris.prototype.timer = function()
{
	//测试的纵坐标加1
	this.fallingBlocks.yPosOfHeart ++;
	//若测试的形状符合要求,则记录方块组合的形状
	if (this.fallingBlocks.testBlocksShape())
	{
		//绘制正在下落的方块组合
		this.fallingBlocks.paintFallingBlocks();
		this.fallingBlocks.saveBlocksShape();
	}
	//否则还原纵坐标,处理着地的方块组合
	else
	{
		this.fallingBlocks.yPosOfHeart --;
		this.fallingBlocks.processFellBlocks();
		tetris.repaint();
	}

	//如果游戏还没有结束
	if (this.isLose != true)
	{
		//0.8秒后激发一次计时器
		temp = this.timer;
		setTimeout("tetris.timer();" , 800);
	}
}


//总的初始化的方法
Tetris.prototype.init = function() 
{
	//创建FallingBlocks的实例,并初始化
	this.fallingBlocks = new FallingBlocks();
	this.fallingBlocks.initFallingBlocks();
	//开始计时器
	this.timer();
	//注册键盘监听的函数
	document.onkeypress = this.keyPressed;
}


//用于重绘图象的方法
Tetris.prototype.repaint = function()
{
//	//绘制背景
//	document.getElementById("BackGroundImage").src = "image/background.jpg";
	//绘制下一个方块组合
	nextImage.src = nextBlockImagePath[this.fallingBlocks.typeOfNext];
	//绘制下一个再下一个方块组合
	nextAndNextImage.src = nextBlockImagePath[this.fallingBlocks.typeOfNextAndNext];
	//绘制已经着地方块
	this.paintFellBlocks();
	//如果游戏已经结束
	if (this.isLose)
	{
		alert("游戏结束!");
	}
}

//绘制已经着地方块
Tetris.prototype.paintFellBlocks = function()
{
	//遍历最高行到最低行的已经着地方块的类型
	for (var j = this.highest; j <= this.lowest; j ++)
	{
		for (var i = 0; i < HORIZONTAL_COUNT; i ++)
		{
			newType = this.fellBlocks[i][j];
			//暂存对应的DIV
			div = fellBlocksDiv[i][j];
			//旧的图像元素
			oldImage = div.firstChild;
			//新的图像元素
			newImage = squareImage[newType].cloneNode(true);
			//替换图像元素
			div.replaceChild(newImage, oldImage);
		}
	}
}

4.方块游戏的启动
//创建Tetris的对象
var tetris = new Tetris();
tetris.init();

5.html中显示方块游戏
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<title>JavaScript俄罗斯方块</title>
<meta http-equiv="Content-Type" content="text/html; charset=gbk" />
</head>

<body>
<div id="BackGroundArea">
			<img id="BackGroundImage" src="image/background.jpg"
			style="position:absolute; left:0; top: 0; z-index:5"></img>
		</div>
		<div id="ReadMe" 
		style="position:absolute; left:0; top: 343; z-index:10">
			JavaScript俄罗斯方块
			<br/>
            操作说明:
			<br/>
			向左移一格:A
			<br/>
			向右移一格:D
			<br/>
			向下移一格:W
			<br/>
			向下到底:S
			<br/>
			顺时针转动:J
			<br/>
			逆时针转动:K
		</div>
	</body>
	<script language="JavaScript" src="init.js"></script>
	<script language="JavaScript" src="fallingblocks.js"></script>
	<script language="JavaScript" src="tetris.js"></script>
	<script language="JavaScript" src="run.js"></script>
</body>
</html>
0
0
分享到:
评论

相关推荐

    python基于pygame的俄罗斯方块小游戏源码.zip

    python基于pygame的俄罗斯方块小游戏源码。python基于pygame的俄罗斯方块小游戏源码。python基于pygame的俄罗斯方块小游戏源码。python基于pygame的俄罗斯方块小游戏源码。python基于pygame的俄罗斯方块小游戏源码。...

    java毕业设计——俄罗斯方块项目(论文+答辩PPT+源代码+数据库+讲解视频).zip

    java毕业设计——俄罗斯方块项目(论文+答辩PPT+源代码+数据库+讲解视频).zip java毕业设计——俄罗斯方块项目(论文+答辩PPT+源代码+数据库+讲解视频).zip java毕业设计——俄罗斯方块项目(论文+答辩PPT+源代码+...

    VC可视化俄罗斯方块源码

    俄罗斯方块是我大学一年级刚学VC++时的课程设计,当时的课程设计有三种,单文档、多文档和俄罗斯方块。我选择俄罗斯方块,就是因为它是游戏。 之前我是玩过俄罗斯方块的,一种是单人的(单人版),一种是两人对战的...

    俄罗斯方块(C语言版) 俄罗斯方块

    C语言版本的俄罗斯方块,实现了俄罗斯方块的基本功能。

    Java俄罗斯方块源代码,Java俄罗斯方块源代码

    俄罗斯方块源代码,俄罗斯方块源代码,俄罗斯方块源代码,

    俄罗斯方块俄罗斯方块俄罗斯方块俄罗斯方块

    俄罗斯方块,用java写的小项目,适合课程设计和Java刚学习的人做的项目

    C#俄罗斯方块(winform)

    C#俄罗斯方块(winform)C#俄罗斯方块(winform)C#俄罗斯方块(winform)C#俄罗斯方块(winform)C#俄罗斯方块(winform)C#俄罗斯方块(winform)C#俄罗斯方块(winform)

    java编的俄罗斯方块

    好游戏java编的俄罗斯方块好游戏java编的俄罗斯方块好游戏java编的俄罗斯方块好游戏java编的俄罗斯方块好游戏java编的俄罗斯方块好游戏java编的俄罗斯方块好游戏java编的俄罗斯方块好游戏java编的俄罗斯方块好游戏...

    俄罗斯方块 俄罗斯方块

    俄罗斯方块 俄罗斯方块 俄罗斯方块 俄罗斯方块

    200行Python代码实现俄罗斯方块游戏所有功能源码.zip

    200行Python代码实现俄罗斯方块所有功能源码200行Python代码实现俄罗斯方块所有功能源码200行Python代码实现俄罗斯方块所有功能源码200行Python代码实现俄罗斯方块所有功能源码200行Python代码实现俄罗斯方块所有...

    基于强化学习的AI俄罗斯方块

    基于强化学习的AI俄罗斯方块基于强化学习的AI俄罗斯方块基于强化学习的AI俄罗斯方块基于强化学习的AI俄罗斯方块基于强化学习的AI俄罗斯方块基于强化学习的AI俄罗斯方块基于强化学习的AI俄罗斯方块基于强化学习的AI...

    PSP俄罗斯方块.iso

    PSP俄罗斯方块.iso

    基于c的俄罗斯方块、俄罗斯方块、俄罗斯方块

    俄罗斯方块、俄罗斯方块、俄罗斯方块、俄罗斯方块、俄罗斯方块、俄罗斯方块、俄罗斯方块、

    俄罗斯方块 c# 俄罗斯方块

    顶下俄罗斯方块 c#俄罗斯方块 c#俄罗斯方块 c#顶下俄罗斯方块 c#俄罗斯方块 c#俄罗斯方块 c#顶下俄罗斯方块 c#俄罗斯方块 c#俄罗斯方块 c#顶下俄罗斯方块 c#俄罗斯方块 c#俄罗斯方块 c#

    基于Java俄罗斯方块游戏的设计与开发大学毕业论文

    俄罗斯方块是一款非常经典的游戏,风靡全球,,经久不衰,是学习面向对象的编程思想的理想实例。本毕业设计论文介绍用JAVA语言设计一个“俄罗斯方块”游戏的过程,整个游戏系统是一个应用程序(Java Application),...

    俄罗斯方块源程序俄罗斯方块源程序俄罗斯方块源程序俄罗斯方块源程序

    俄罗斯方块源程序俄罗斯方块源程序俄罗斯方块源程序俄罗斯方块源程序俄罗斯方块源程序俄罗斯方块源程序俄罗斯方块源程序俄罗斯方块源程序

    俄罗斯方块.txt

    俄罗斯方块游戏,C语言实现。 世界上最流行的休闲游戏之一——俄罗斯方块。它的发明者阿列克谢·帕基特诺夫及其合作伙伴、美国蓝色行星软件公司总裁亨克·罗杰斯6月2日宣布,俄罗斯方块诞生25周年庆祝活动在美国洛杉...

    MFC实现的俄罗斯方块

    俄罗斯方块游戏源代码,一起学习俄罗斯方块游戏源代码,一起学习俄罗斯方块游戏源代码,一起学习俄罗斯方块游戏源代码,一起学习俄罗斯方块游戏源代码,一起学习俄罗斯方块游戏源代码,一起学习俄罗斯方块游戏源代码...

    JS代码版俄罗斯方块

    俄罗斯方块 是一款风靡全球的电视游戏机和掌上游戏机游戏,它由俄罗斯人阿列克谢·帕基特诺夫发明,故得此名。俄罗斯方块的基本规则是移动、旋转和摆放游戏自动输出的各种方块,使之排列成完整的一行或多行并且消除...

    200行Python代码实现俄罗斯方块所有功能(源码).zip

    200行Python代码实现俄罗斯方块所有功能(源码) 200行Python代码实现俄罗斯方块所有功能(源码) 200行Python代码实现俄罗斯方块所有功能(源码) 200行Python代码实现俄罗斯方块所有功能(源码) 200行Python...

Global site tag (gtag.js) - Google Analytics