JS能跑起来的贪吃蛇!(Bug多多 求指点。。)

<html>
    <head>
        <!-- 地图的样式 -->
        <style>
            #map{
                width: 800px;
                height: 600px;
                background-color: lightgray;
                position: relative;
            }    
        </style>


        <!-- 创建相关的对象 -->
        <script>
            /**
             * 
             * 启用自调用函数这种模式 可以防止与其他的js发生变量重名等冲突的异常发生
             * (function(window,undefind){...代码...})(window,undefind)  //传入window 和 undefind的目的就是为了可以在发布时变量名window可以别压缩 另在老版本中undefind防止被改变
             * 
             */
            
            // **********************************创建食物对象**********************************************
            // **********************************创建食物对象**********************************************
            (function(){
                    //创建一个工具类对象    静态的对象 也就是工具类的创建方式
                    var Tools = {getRandom:function(min,max){return Math.floor(Math.random()*(max-min+1))+min;}}

                    //创建一个变量来记录生成的食物
                    var elements = [];
                    function Food(options){
                        var options = options ||{};
                        //初始化食物的位置
                        this.x = options.x || 0;  
                        this.y = options.y || 0;
                        //初始化食物的大小
                        this.width = options.width || 20;
                        this.height = options.height || 20;
                        //设置食物的颜色
                        this.color = options.color || 'green';
                    }

                    //为食物创建一个渲染u方法(渲染就是把食物显示再浏览器中)
                    Food.prototype.render = function(map){ 
                        //创建食物时先删除现在已经有的食物~
                        remove();                         
                        var map = map;
                        var div = document.createElement('div'); 
                        elements.push(div); //把生成的div放置到数组中进行保存
                        map.appendChild(div);
                        div.style.position = 'absolute';
                        div.style.left = this.x +'px';
                        div.style.top = this.y + 'px';
                        div.style.width = this.width +'px';
                        div.style.height = this.height +'px';
                        div.style.backgroundColor = this.color;

                        this.div = div ;//把这个div对象绑定到这个food对象上供后面调用
                        this.map = map;
                        this.random();
                    }

                    //删除食物 
                    function remove(){
                        for(var i =elements.length-1; i>=0; i--){
                            //删除div
                            elements[i].parentNode.removeChild(elements[i]);    
                            //删除数组中的元素
                            elements.splice(i,1);     
                        }
                    }


                    //创建随机生成位置的方法函数
                    Food.prototype.random = function(){
                        var x = Tools.getRandom(0,this.map.offsetWidth/this.width-1)*this.width;
                        var y = Tools.getRandom(0,this.map.offsetHeight/this.height-1)*this.height;
                        this.div.style.left = x + 'px';
                        this.div.style.top = y + 'px';

                        this.x =x; //改变位置以后 一定要把新的位置赋值给食物!!!!!!!!!!!
                        this.y =y;
                    }
                    //让外部可以访问这个函数域中的对象
                    window.Food = Food;
             })();





            // **********************************创建蛇对象**********************************************
            // **********************************创建蛇对象**********************************************
            (function(){
                //记录创建的蛇
                var elements = [];
                //生成snake的构造方法
                function Snake(op){
                    var op = op || {};
                    this.width = op.width || 20;
                    this.height = op.height || 20;
                    this.direction = op.direction || 'right';
                    this.body = [
                        {x:3,y:2,color:'red'},
                        {x:2,y:2,color:'blue'},
                        {x:1,y:2,color:'blue'}
                    ]
                }

                //为snake生成一个渲染的方法(怎么显示在页面上)
                Snake.prototype.render = function(map){
                    //删除之前创建的snake
                    remove();
                    var map = map;
                    for(var i = 0,len = this.body.length; i<len; i++){
                        var object = this.body[i];
                        var div = document.createElement('div');
                        map.appendChild(div);
                        elements.push(div); //记录当前生成的snake
                        div.style.position = 'absolute';
                        div.style.width = this.width +'px';
                        div.style.height = this.height +'px';

                        //设置snake的初始位置
                        div.style.left = object.x * this.width + 'px';
                        div.style.top = object.y * this.height + 'px';

                        //设置颜色
                        div.style.backgroundColor = object.color;
                    }
                }

                //删除开始创建的sanke对象在 生成新的snake之前
                function remove(){
                    for(var i =elements.length-1; i>=0; i--){
                        //删除div
                        elements[i].parentNode.removeChild(elements[i]);
                        //删除数组中的元素
                        elements.splice(i,1);
                    }
                }
                

                //snake的移动方法
                Snake.prototype.move = function(food){
                    //先控制身体移动(当前的蛇节到上一个位置)
                    for(var i = this.body.length -1; i > 0; i--){   //this.body.length -1 除去蛇头
                        this.body[i].x = this.body[i-1].x;   //当前的蛇节 x 等于上一个蛇节的 x
                        this.body[i].y = this.body[i-1].y;   //当前的蛇节 y 等于上一个蛇节的 y
                    }
                    //控制蛇头的移动位置
                    var head = this.body[0];
                    switch(this.direction){
                        case 'right':
                            head.x += 1;
                            break;
                        case 'left':
                            head.x -= 1;
                            break;
                        case 'top':
                            head.y -= 1;
                            break;
                        case 'bottom':
                            head.y += 1;
                            break;
                    }

                    //判断snake的头 是否吃到了食物
                    var hX = head.x * this.width;
                    var hY = head.y * this.height;

                     if(hX === food.x && hY === food.y){   
                          //吃食物
                          //获取蛇的最后一节
                          var last = this.body[this.body.length-1];
                          //增加蛇身
                          this.body.push({x:last.x,y:last.y,color:last.color});
                          //新的食物
                          food.render(food.map);
                     }
                }
                window.Snake = Snake;
            })();



            // **********************************创建游戏对象**********************************************
            // **********************************创建游戏对象**********************************************
            (function(){
                
                var cope_this; //记录当前游戏的对象 供私有的函数也可以使用这个对象

                function Game(map){
                    this.food = new Food(); //等价于new window.Food();
                    this.snake = new Snake();
                    this.map = map;

                    cope_this = this;
                }

                Game.prototype.start = function(){
                    //开始游戏把蛇和食物渲染在地图上
                    this.food.render(this.map);
                    //this.food.random();
                    this.snake.render(this.map);

                    //开始游戏的
                    //1让snake可以移动起来
                    //2当snake遇到地图的边界
                    runSnake();
                    //3通过键盘可以控制snake的移动
                    bindKey();
                    //4当snake吃到食物时 食物消失 蛇长一个身体 在次生成一个食物
            
                    
                }





                //注册键盘事件
                function bindKey(){
                    //document.onkeydown = function(){};
                    document.addEventListener('keydown',function(e){
                        //console.log(e.keyCode)  37 left  38 -top 39 right 40 bottom

                        switch(e.keyCode){
                            case 37:
                            cope_this.snake.direction = 'left';
                            break;
                            case 38:
                            cope_this.snake.direction = 'top';
                            break;
                            case 39:
                            cope_this.snake.direction = 'right';
                            break;
                            case 40:
                            cope_this.snake.direction = 'bottom';
                            break;
                        }

                        
                    },false)
                }





                function runSnake(){
                    //开启一个定时器让sanke不断的移动 然后用键盘改变snake头的方向即可
                    var timerId = setInterval(function(){
                        
                        //让snake移动起来
                        cope_this.snake.move(cope_this.food);
                        cope_this.snake.render(cope_this.map);

                        //如果移动到了地图的边界
                        //获取snake头的坐标
                        var headX = cope_this.snake.body[0].x;
                        var headY = cope_this.snake.body[0].y;
                        
                        var maxX = cope_this.map.offsetWidth /cope_this.snake.width;
                        var maxY = cope_this.map.offsetHeight /cope_this.snake.height;

                        if(headX < 0 || headX >= maxX || headY < 0 || headY >= maxY){
                            alert("GameOver!");
                            clearInterval(timerId);
                        }
            

                    },500);
                }

  
                window.Game = Game;
            })()



        </script>
    </head>



    <body><div id="map"> </div></body> 


    <!-- ***********************************测试js************************************************************** -->
    <script>
        var map = document.getElementById('map');
        var game = new Game(map);
        game.start();
    </script>
</html> 

 

posted @ 2020-04-16 17:42  gaoshengjun  阅读(182)  评论(0编辑  收藏  举报