一.简介

俄罗斯方块(Tetris, 俄文:Тетрис)是一款风靡全球的电视游戏机和掌上游戏机游戏,它由俄罗斯人阿列克谢·帕基特诺夫发明,故得此名。俄罗斯方块的基本规则是移动、旋转和摆放游戏自动输出的各种方块,使之排列成完整的一行或多行并且消除得分。由于上手简单、老少皆宜,从而家喻户晓,风靡世界。

二.需求分析

(完全按照QQ游戏的制作,如下图:)

三.技术分析与实现

1.方块位置定位

解决方案:建立盒子模型

由于长条的存在,所以建立一个4*4的盒子模型,任何一个方块都会存在该盒子当中,方块的定位就===盒子的定位。

2.颜色状态的生成与保存

随机生成颜色:

function randomColor() {
        //16进制方式表示颜色0-F
        var arrHex = ["0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "A", "B", "C", "D", "E", "F"];
        var strHex = "#";
        var index;
        for (var i = 0; i < 6; i++) {
            //取得0-15之间的随机整数
            index = Math.round(Math.random() * 15);
            strHex += arrHex[index];
        }
        return strHex;

}

颜色保存:(那一个方块的一种状态做示例)

var diamonds = new Array();
    diamonds[0] = { x: appearPosition.position.x + 1, y: appearPosition.position.y, diamondColor: color };
    diamonds[1] = { x: appearPosition.position.x + 0, y: appearPosition.position.y + 1, diamondColor: color };
    diamonds[2] = { x: appearPosition.position.x + 1, y: appearPosition.position.y + 1, diamondColor: color };
    diamonds[3] = { x: appearPosition.position.x + 2, y: appearPosition.position.y + 1, diamondColor: color };

所有生成的方块有个diamondColor属性,用于存颜色。appearPosition.position是盒子模型的位置。

3.碰撞检测

碰撞分两种,一种是元素与左右墙壁和底部的碰撞,另外一种是方块与底部方块的接触碰撞

a.元素与左右墙壁和底部的碰撞

a.1元素与底部的碰撞检测

if (diamonds[i].y * height + height >= canvasHeight) {
        appearPosition.position.x = Math.round(appearPosition.position.x);
        appearPosition.position.y = Math.round(appearPosition.position.y);
        createElement();
        breakTag = 1;

}

a.2元素与左右墙壁的碰撞检测

function returnRightOrLeft() {
        var max_X = 11;
        for (i = 0; i < diamonds.length; i++) {
            if (diamonds[i].x > max_X) {
                max_X = diamonds[i].x;
            }
        }
        if (max_X != 11) appearPosition.position.x = appearPosition.position.x - (max_X - 11);
        var min_X = 0;
        for (i = 0; i < diamonds.length; i++) {
            if (diamonds[i].x < min_X) {
                min_X = diamonds[i].x;
            }
        }
        if (min_X != 0) appearPosition.position.x = appearPosition.position.x - min_X;
    }

b.元素与元素碰撞检测

//判断下面是否有元素
    for (j = 0; j < bottomElement.length; j++) {
        if (bottomElement[j].x == diamonds[i].x) {
            if (Math.round(bottomElement[j].y) == Math.round(diamonds[i].y + 1)) {
                appearPosition.position.x = Math.round(appearPosition.position.x);
                appearPosition.position.y = Math.round(appearPosition.position.y);
                createElement();
                breakTag = 1;
            }
        }
    }
    //判断arrayOne是否在arrayTwo的右边
    function IsAtRight(arrayOne, arrayTwo) {
        for (i = 0; i < arrayOne.length; i++) {
            for (j = 0; j < arrayTwo.length; j++) {
                if (Math.round(arrayOne[i].y) == Math.round(arrayTwo[j].y)) {
                    if (arrayTwo[j].x == arrayOne[i].x + 1) return true;
                }
            }
        }
        return false;
    }
    //判D断arrayOne是否在arrayTwo的左边
    function IsAtLeft(arrayOne, arrayTwo) {
        for (i = 0; i < arrayOne.length; i++) {
            for (j = 0; j < arrayTwo.length; j++) {
                if (Math.round(arrayOne[i].y) == Math.round(arrayTwo[j].y)) {
                    if (arrayTwo[j].x == arrayOne[i].x - 1) return true;
                }
            }
        }
        return false;
    }

4.方块变形

var direction = 0;
    if (e.keyCode == 87) {
        direction++;
        direction %= 4;
    }

W键是变形,0123分别代表四种。

如果是长条或者只有两种状态的直接  if (direction % 2 == 0) {},如果是正方块直接忽略direction,因为它就一种形状。

5.键盘捕获(目前WSAD+空格,W是变形,S和空格都是加速,IE9和FF异常,建议在谷歌浏览器下运行)

document.onkeydown = function (e) {
        if (e.keyCode == 65) {
            for (i = 0; i < diamonds.length; i++) {
                if (diamonds[i].x == 0) {
                    return;
                }
            }
            if (IsAtLeft(diamonds, bottomElement)) {
                return;
            }
            appearPosition.position.x -= 1;
        }
        if (e.keyCode == 87) {
            direction++;
            direction %= 4;
        }
        if (e.keyCode == 68) {
            for (i = 0; i < diamonds.length; i++) {
                if (diamonds[i].x == 11) {
                    return;
                }
            }
            if (IsAtRight(diamonds, bottomElement)) {
                return;
            }
            appearPosition.position.x += 1;
        }
        if (e.keyCode == 32) {
            delay = 1;
        }
        if (e.keyCode == 83) {
            delay = 1;
        }
    }
    document.onkeyup = function (e) {
        if (e.keyCode == 32) {
            delay = 20;
        }
        if (e.keyCode == 83) {
            delay = 20;
        }
    }
  

6.消除加分

//一行满了的话,消除并加分
    function clearUp() {
        for (var line = 0; line < 21; line++) {
            var count = 0;
            for (var i = 0; i < bottomElement.length; i++) {
                if (bottomElement[i].y == line) {
                    count++;
                }
            }
            if (count == 12) clearByLineNum(line);
        }
        // if(count==12)
    }
    function clearByLineNum(num) {
        //以上的元素下降一行
        score++;
        var count = 0;
        for (i = 0; i < bottomElement.length; i++) {
            if (bottomElement[i].y == num) {
                count++;
            }
        }
        for (var j = 0; j < count; j++) {
            for (var i = 0; i < bottomElement.length; i++) {
                if (bottomElement[i].y == num) {
                    bottomElement.splice(i, 1);
                    break;
                }
            }
        }
        for (i = 0; i < bottomElement.length; i++) {
            if (bottomElement[i].y < num) {
                bottomElement[i].y += 1;
            }
        }
    }
消除加分有一个潜在的逻辑就是,在该行以上的元素的位置下降一个格子。

7.控制核心Jscex  Show Time

var JropAsync = eval(Jscex.compile("async", function () {
        var breakTag = 0;
        while (true) {
            color = randomColor();
            rectBlockIndex = MR() * 7 | 0;
            direction = MR() * 3 | 0;
            $await(Jscex.Async.sleep(1));
            while (true) {
                for (i = 0; i < diamonds.length; i++) {
                    if (diamonds[i].y * height + height >= 525) {
                        appearPosition.position.x = Math.round(appearPosition.position.x);
                        appearPosition.position.y = Math.round(appearPosition.position.y);
                        createElement();
                        breakTag = 1;
                    }
                    //判D断?下?面?是?否?有D元a素?
                    for (j = 0; j < bottomElement.length; j++) {
                        if (bottomElement[j].x == diamonds[i].x) {
                            if (Math.round(bottomElement[j].y) == Math.round(diamonds[i].y + 1)) {
                                appearPosition.position.x = Math.round(appearPosition.position.x);
                                appearPosition.position.y = Math.round(appearPosition.position.y);
                                createElement();
                                breakTag = 1;
                            }
                        }
                    }
                }
                if (breakTag == 1) {
                    for (i = 0; i < diamonds.length; i++) {
                        //alert(diamonds[i].x + "____" + diamonds[i].y)
                        bottomElement.push(diamonds[i]);
                    }
                    clearUp();
                    //清?空?下?降μ的?元a素?
                    diamonds.splice(0, diamonds.length);
                    appearPosition = { position: { x: 4, y: -2 }, direction: 0 };
                    breakTag = 0;
                    break;
                }
                appearPosition.position.y += step;
                draw();
                $await(Jscex.Async.sleep(delay));
            }
        }
    }));

这是也整个俄罗斯方块的控制核心,由两个while循环构成,简单大方

转载于:https://www.cnblogs.com/yangmengsheng/p/6026203.html

火拼《俄罗斯方块》解析相关推荐

  1. 单机版火拼俄罗斯方块源程序

    发表日期:2005年11月12日      已经有3587位读者读过此文 /*这是我在参考别人的的俄罗斯方块的基础上,写的一个单机版火拼俄罗斯方块源程序,*/ /*如果有须要下载可到www.jxncz ...

  2. 俄罗斯方块java机器人_H5版俄罗斯方块(4)---火拼对战的雏形

    前言: 勿忘初心, 本系列的目标是实现一款类似QQ"火拼系列"的人机对战版俄罗斯方块. 在完成了基本游戏框架和AI的算法探索后, 让我们来尝试一下人机大战雏形编写. 本系列的文章链 ...

  3. H5版俄罗斯方块(4)---火拼对战的雏形

    前言: 勿忘初心, 本系列的目标是实现一款类似QQ"火拼系列"的人机对战版俄罗斯方块. 在完成了基本游戏框架和AI的算法探索后, 让我们来尝试一下人机大战雏形编写. 本系列的文章链 ...

  4. javascript异步编程系列【八】--Jscex版火拼俄罗斯

    一.简介 俄罗斯方块(Tetris, 俄文:Тетрис)是一款风靡全球的电视游戏机和掌上游戏机游戏,它由俄罗斯人阿列克谢·帕基特诺夫发明,故得此名.俄罗斯方块的基本规则是移动.旋转和摆放游戏自动输出 ...

  5. 非主流图片编辑软件_快火拼多多直播发言软件怎么下载

    7.智能客服.设置客服小号智能欢迎,智能回答问题(录播必备).强势来袭!8.可改小号昵称.9.一台电脑无限多开.复制重命名文件夹名字即可,每个文件夹单独账号.10.观看功能,增加直播间观累计观看量;观 ...

  6. 运营商开始悄悄火拼5G价格战,19元套餐开始涌现

    虽然运营商尚未正式公开降低5G流量价格,但是日前已不断有网友曝出三大运营商向特定客户推送的19元套餐,将5G套餐的价格降至新低点,为用户带来实惠,显示出运营商已经开始悄悄火拼价格战. 从网友提交的信息 ...

  7. 国外电子工程师们国内电子工程师火拼(转)

    转自http://bbs.21ic.com/ 国外电子工程师们&国内电子工程师火拼 感觉这里缺点海派风味,程序匠人能否下功夫拉些海外背景的电子工程师来交流交流?毕竟,电子信息业的发源地在人那里 ...

  8. 聚划算火拼如何参团 聚划算火拼效果怎么样

    淘宝聚划算非常实惠,还可以拼团,大部分的人都只知道参与普通的聚划算拼团活动,不知道聚划算火拼怎么玩,所以为了帮大家了解聚划算火拼如何参团,特意整理了下面的内容哦. 1.一起买玩法只支持聚划算客户端5. ...

  9. 火拼商城:4亿乡村新中产正在消费升级!

    不久前,一篇<这届年轻人已经开始消费降级了>刷爆了朋友圈.不得不说,这篇文章通过标题和话题非常成功的抓住了人们的眼球,也很顺利的挑起了青年人焦虑的神经. 然而,年轻人真的消费降级了吗?国内 ...

  10. 基于IOCP模型的.NET 游戏(火拼俄罗斯)

    全新火拼俄罗斯, 早先发布的一个版本已取消发布,(由于老的通信性能问题,被彻底的抛弃) 现在最新的发布端需要最低.NET 2.0 SP1  环境才能运行 (因为采用了.NET 2.0SP1才加入的IO ...

最新文章

  1. poj 2362 Square
  2. 用flex进行网易云音乐界面构建和布局解析(2)
  3. java读取文件的方法是_Java读取文件方法大全
  4. sple表达式_学习Spring表达式语言(SpEL)
  5. Fiddler 域名过滤
  6. mysql数据表的创建-数据类型
  7. 图例 | Java混合模式分析之火焰图实例
  8. 助力南京打造创新名城 第三届未来网络发展大会将召开
  9. 「leetcode」C++题解:20. 有效的括号,括号匹配是使用栈解决的经典问题
  10. 实施和开发哪个前景好_现在学习苹果ios开发还有发展前景吗?学android和ios哪个更好?...
  11. 203.移除链表元素
  12. Java高级工程师技能要求参考
  13. 兴奋神经递质——谷氨酸与大脑健康
  14. 快速给图片加水印的方法
  15. 数组方法的增删等19种操作:unshift 、shift,push、pop、splice等等...!
  16. 华为鸿蒙ota升级,华为鸿蒙系统官方,华为鸿蒙系统官方升级名单预约 v2.0 - 浏览器家园...
  17. AutoHotKey 新手入门教程
  18. k8s-CKS真题-CIS基准测试与安全扫描
  19. 今天搞了一下 老DELLT3600工作站···
  20. 白杨SEO:中小企业发广告去哪个平台?一般选择哪种推广方式方法比较好?

热门文章

  1. 汉王科技发布多款AI智能新品,布局服务机器人新赛道
  2. 书评-《日进3万3》浙师大“包,二,奶”生意火爆,木人管还获得支持?你只有羡慕嫉妒恨
  3. handsontable mysql_Handsontable 新增一行 默认值
  4. 【虹科案例】虹科数字化仪在激光雷达大气研究中的应用
  5. QGroupBox互斥勾选框
  6. 一篇文章全面了解监控知识体系
  7. 【SMS】SMS协议介绍之MSC
  8. python可视化——生成HTML文件
  9. sql 每小时的温度平均值
  10. 上海积分落户计算机水平加分,2019年上海应届生落户打分72分标准拿分策略