俄罗斯方块 1 (实现移动和相关显示)

/**
 * Created by Administrator on 2016/10/22.
 */
//定义cell类型:3个属性:r,c,src
function cell(r,c,src){
    this.r=r;
    this.c=c;
    this.src=src;
}

function State(arr){//创建状态对象  把相对坐标数据封装进去
    for(var i=0;i<4;i++){
        this["r"+i]=arr[2*i];
        this["c"+i]=arr[2*i+1];
    }

}
function shape(rcs,src,states,orgi) {
    this.cells =[];
    for (i = 0;i<4;i++){
        this.cells.push(new cell(rcs[2*i],rcs[2*i+1],src));
    }
    this.states=states;//状态数组
    this.orgCell=this.cells[orgi];//旋转参照的格子对象
    this.statei=0;
}

shape.prototype={
    IMGS:{
    T:"img/T.png",
    O:"img/O.png",
    I:"img/I.png"
},
    moveDown:function(){
     for(i=0;i<this.cells.length;i++){
         this.cells[i].r++;
     }
    },
    moveLeft:function(){
        for(i=0;i<this.cells.length;i++){
            this.cells[i].c= this.cells[i].c-1;
        }
    },
    moveRight:function(){
        for(i=0;i<this.cells.length;i++){
            this.cells[i].c++;
        }
    },
    rotateR:function(){//右旋转
        this.statei++;
        if(this.statei==this.states.length){
            this.statei=0;
        }
        this.rotate();
    },
    rotate:function(){
        var state=this.states[this.statei];
        for(i=0;i< this.cells.length;i++){
            if(this.cells[i]!=this.orgCell){
                if(this.cells[i]!=this.orgCell){   //使用状态数据修改当前shape里面格子坐标
                    this.cells[i].r=this.orgCell.r+state["r"+i];
                    this.cells[i].c=this.orgCell.c+state["c"+i];
                }
            }
        }
    },
    rotateL:function(){
        this.statei--;
        if(this.statei==-1){
            this.statei=4;
        }
        this.rotate();
    }

    };
function T(){
    shape.call(this,[0,3,0,4,0,5,1,4],this.IMGS.T,[
        new State([0,-1,0,0,0,+1,+1,0]),     //封装状态数据传进去 相对坐标
        new State([-1,0,0,0,+1,0,0,-1]),
        new State([0,+1,0,0,0,-1,-1,0]),
        new State([+1,0,0,0,-1,0,0,+1])
    ],1);
};
Object.setPrototypeOf(T.prototype,shape.prototype);
function O(){
    shape.call(this,[0,3,0,4,1,3,1,4],this.IMGS.O,[],1);
};
Object.setPrototypeOf(O.prototype,shape.prototype);
function I(){
    shape.call(this,[0,3,0,4,0,5,0,6],this.IMGS.I);
};
Object.setPrototypeOf(I.prototype,shape.prototype);
/**
 * Created by Administrator on 2016/10/22.
 */
var game={
    CSIZE:26,
    OFFSET:15,
    pg:null,//保存游戏容器元素
    shape:null,
    interval:200,
    timer:null,
    RN:20,
    CN:10,
    wall:null,
    shape:null,
    nextshape:null,
    start:function(){
          this.wall=[];
        for(var r=0;r<this.RN;r++){
            this.wall[r]=new Array(this.CN);
        }
        this.pg=document.querySelector(".playground");
        this.shape=new T();
        this.shape=this.randomShape();
        this.nextshape=this.randomShape();
        this.paint();
        this.timer=setInterval(this.moveDown.bind(this),this.interval);
        document.onkeydown= (function (ev) {
             switch (ev.keyCode){
                 case 37:this.moveLeft();break;
                 case 39:this.moveRight();break;
                 case 40:this.hardDrop();break;
                 case 38:this.rotateR();break;
                 case 90:this.rotateL();break;
             }
        }).bind(this);
},
    canRotate:function(){//判断是否越界
        for(var i=0;i<this.shape.cells.length;i++){
            var cell=this.shape.cells[i];
            if(cell.r>=this.RN||cell.r<0
                ||cell.c>=this.CN||cell.c<0)
                return false;
            else if(this.wall[cell.r][cell.c])
                return false;
        }
        return true;
    },
    rotateR:function(){
        this.shape.rotateR();
        if(!this.canRotate())//如果旋转后越界,再转回来
            this.shape.rotateL();
    },
    rotateL:function(){
        this.shape.rotateL();
        if(!this.canRotate())
            this.shape.rotateR();
    },
    hardDrop:function(){//直接降下来

        while(this.canDown()){
            this.moveDown();
        }
    },
    canLeft:function(){//判断能否左移动
        for(var i=0;i<this.shape.cells.length;i++){
            var cell=this.shape.cells[i];
            if(cell.c==0){
                return false;
            }
            else if(this.wall[cell.r][cell.c-1]){
                return false;
            }
        }
        return true;
    },
    moveLeft:function(){//左移

        if(this.canLeft()){
            this.shape.moveLeft();
            this.paint();
        }
    },
    canRight:function(){//判断能否右移动
        for(i=0;i<this.shape.cells.length;i++){
            var cell=this.shape.cells[i];
            if(cell.c==this.CN-1){
                return false;
            }
            else if(this.wall[cell.r][cell.c+1]){
                return false;
            }
        }
        return true;
    },
    moveRight:function(){//右移

        if(this.canRight()){
            this.shape.moveRight();
            this.paint();
        }
    },

    paintShape:function(){//绘制主图形//未删存在的
        var frag=document.createDocumentFragment();
        for(var i=0;i<4;i++){
            var cell=this.shape.cells[i];
            frag.appendChild(this.paintCell(cell));
        }
        this.pg.appendChild(frag);
    },
    moveDown:function(){  //下移动
        if(this.canDown()){
            this.shape.moveDown();
            this.paint();
        }

       else{   //到底了 替换

            this.landIntoWall();
            this.shape=this.nextshape;
            this.nextshape=this.randomShape();
        }
    },
    paint:function(){//总的画
        this.pg.innerHTML=this.pg.innerHTML.replace(/<img\s[^>]*>/g,"");
        this.paintShape();
        this.painWall();
        this.painNext();
    },
    canDown:function(){ //能否下
        for(var i=0;i<this.shape.cells.length;i++) {
            var cell = this.shape.cells[i];
            if(cell.r==this.RN-1){return false;}
            else if(this.wall[cell.r+1][cell.c]){
                return false;
            }
        }
        return true;
    },
    landIntoWall:function(){//保存在墙数组中
        for(var i=0;i<this.shape.cells.length;i++){
            var cell=this.shape.cells[i];
            this.wall[cell.r][cell.c]=cell;
        }

    },
    painWall:function(){//画墙
        var frag=document.createDocumentFragment();
        for(var r=this.RN-1;r>0;r--){
            if(this.wall[r].join("")=="") break;
            else
            for(var c=0;c<this.CN;c++) {
                if(this.wall[r][c])
                {frag.appendChild(this.paintCell(this.wall[r][c]))};
            }
        }
        this.pg.appendChild(frag);
    },
    paintCell:function(cell){//画单元
        var img=new Image();
        img.style.left=cell.c*this.CSIZE+this.OFFSET+‘px‘;
        img.style.top=cell.r*this.CSIZE+this.OFFSET+‘px‘;
        img.src=cell.src;
        return img;
},
    randomShape:function(){//随机生成一个shape
        var r=Math.floor(Math.random()*3);
        switch (r){
            case 0: return new O();
            case 1: return new T();
            case 2: return new I();
        }
    },
    painNext:function(){ //画nextShape
        var frag=document.createDocumentFragment();
        for(var i=0;i<this.nextshape.cells.length;i++){
            var img=this.paintCell(this.nextshape.cells[i]);
            img.style.left=parseFloat(img.style.left)+10*this.CSIZE+"px";
            img.style.top=parseFloat(img.style.top)+this.CSIZE+"px";
            var cell=this.nextshape.cells[i];
            frag.appendChild(img);
        }
        this.pg.appendChild(frag);
    },
}
game.start();
时间: 2024-10-15 04:03:52

俄罗斯方块 1 (实现移动和相关显示)的相关文章

1107投票列表的相关显示

1.首先 投票有一个挂件,vote_xxxx 在_config.html中,上传一个图片,作为背景图片. 在default.html中, <img src="<{$item.goods_image|storager:'s'}>"/> 图片的显示.因为,上传的时候图片仅仅是一个编号,通过stroager把它转换一下. 在theme_widget_vote_autumn.php中,增加代码: foreach($data['votelist'] as $key=>

Android搜索结果显示高亮(有数据滑动底部自动刷新)

首先的效果图 搜索到结果(这里我只是模拟数据,真正和服务器走得时候,返回来的数据都应该包含关键字的) 模拟的没有搜索结果的界面 具体实现 在这插一句哈,就是做一件事情,拆分成多个小结,不至于在开发的时候摸不着头脑而且还能把控开发的进度. 思路其实很简单,我们监听输入框的变化,然后在文字变化之后去请求服务器,然后取到我们需要的结果,进行数据展示即可. 第一步:搜索框的监听 et_search.addTextChangedListener(new TextWatcher() { @Override

家庭版记账本app进度之对于按钮的点击事件以及线性布局以及(alertdialog)等相关内容的应用测试

通过线性布局,制作出连个按钮还有文本输入框以及嘴上放的标题文本进行信息的相关显示,完后最后的信息的输入,之后在屏幕的的下方进行显示 当点击第一个按钮的时候,在下方就会简单的出现你自己刚刚输入的相关信息.主要是训练的是对于客户输入信息的一个简单的获取, 并进行比较见得的在屏幕上输出.具体的结果截屏如下: 最后对alertdialog进行相关的应用 AlertDialog可以在当前页面弹出一个对话框,在所有界面元素之上,可以屏蔽掉界面其他控件的交互能力,因此AlertDialog一般用于提示一些非常

VMware vSAN分布式存储安装配置

作者:在路上(老李) DCD|DCA   QQ群:384423770 一.环境说明 管理地址: AD:        192.168.1.254 ESXi01:        192.168.1.201 ESXi02:        192.168.1.202 ESXi03:        192.168.1.203 ESXi04:        192.168.1.204 vCenter:        192.168.1.200 VSAN地址: esxi01:        172.16.2

Ruby Profiler详解之ruby-prof(I)

项目地址: ruby-prof 在上一篇 Ruby 中的 Profiling 工具中,我们列举了几种最常用的 Profiler,不过只是简单介绍,这一次详细介绍一下 ruby-prof 的使用方法. ruby-prof 是比较强大的,支持 cpu,内存使用,对象分配等等的性能分析,而且提供了很多友好的输出格式,不仅仅是有基于文字,html 的格式,还能输出 graphviz 格式的 dot 文件,以及适用与 KCacheGrind 的call tree格式, 其实这个格式是基于 Valgrind

站立会议06(第二阶段)

完成任务: 数字密码功能实现基本的设置 修改后的滑动解锁可以解锁,并添加了相关显示 重力感应亮.灭屏各种动作已经实现 遇到的困哪: 添加的新改动的滑动解锁有时不太灵敏,反应慢 保存的密码不知道如何访问 重力防误解锁屏没什么进展

事件处理程序WinProc

事件处理函数是一个回调函数,Windows在窗体中发生须要处理的事件时,在主时间循环中调用该函数.时间处理函数可处理不论什么想处理的事件,其它的事件传递给Windows进行处理. 在用户和Windows运行某些操作时,将生成一些针相应用程序的事件和消息,全部这些消息都将进入一个队列中,而针对一个应用程序窗体的事件和消息将从消息队列中转移到该窗体的私有队列中. 然后主事件循环将获取这些消息并将它们发送给窗体的WinProc进行处理. 消息处理函数的原型是: LRESULT CALLBACK Win

Windows Server 2012 R2中通过IIS实现AD帐号密码修改功能

现在越来越多的企业会对AD帐号进行分类,例如将业务帐号.服务帐号同员工帐号分开管理,那么这类帐号也会因为业务应用特定类型而选择是否开启邮箱功能,再或者有些企业会采用腾讯企业邮箱或网易企业邮箱等等,这些平台本身同AD域是独立的,而且很多企业又使用MAC系统或计算机根本不加域,这时企业内网要搭建OA.WIKI.JIRA等一些需要调用AD中的LDAP让员工登录的系统时,则面临后期密码到期后用户没有入口去修改密码的问题.那么在今天我就要给大家介绍的是如何利用Windows Server 2012 R2中

Python基础学习笔记

Python 特点 1.易于学习:Python有相对较少的关键字,结构简单,和一个明确定义的语法,学习起来更加简单. 2.易于阅读:Python代码定义的更清晰. 3.易于维护:Python的成功在于它的源代码是相当容易维护的. 4.一个广泛的标准库:Python的最大的优势之一是丰富的库,跨平台的,在UNIX,Windows和Macintosh兼容很好. 5.互动模式:互动模式的支持,您可以从终端输入执行代码并获得结果的语言,互动的测试和调试代码片断. 6.可移植:基于其开放源代码的特性,Py