javascript实现消灭星星小游戏简单版


Posted in Javascript onNovember 15, 2016

来看看实现的效果图

javascript实现消灭星星小游戏简单版

游戏规则:双击颜色一样的星星,双击相同的部分就消失了

实例代码

<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8" content="target-densitydpi=320,width=640,user-scalable=no" />
  <noscript><meta http-equiv="refresh" content="0"></noscript>
  <title></title>
  <meta name="description" id="seo_description" content="消灭星星">
  <meta name="viewport" content="initial-scale=1, width=device-width, maximum-scale=1, user-scalable=no">
  <meta name="viewport" content="initial-scale=1.0,user-scalable=no,maximum-scale=1" media="(device-height: 568px)">
  <meta name="apple-mobile-web-app-capable" content="yes">
  <meta name='apple-touch-fullscreen' content='yes'>
  <meta name="full-screen" content="yes">
  <meta name="apple-mobile-web-app-status-bar-style" content="black">
  <meta name="format-detection" content="telephone=no">
  <meta name="format-detection" content="address=no">
  <link rel="icon" href="" type="image/x-icon">
<script id="jquery_183" type="text/javascript" class="library" src="http://runjs.cn/js/sandbox/jquery/jquery-1.8.3.min.js"></script>
<style>
* {margin:0; padding:0;}
body {background:#000; width:100%; height:100%;}
#box {position:absolute; margin-top:50px;}
#star_box {position:relative; }
#star_box .star {width:40px; height:40px; position:absolute; cursor:pointer; }
#star_box .star img {border-radius:5px;}
#star_box .link img {border:2px solid #fff; border-radius:5px;}
</style>
<script>
$(function(){
    app.run();
});
// 2015-1-30 16:26
// 基本都已经实现
// 积分系统还没开始
var app = {};
app.linkStars = [];
app.searchStars = [];
app.stars = [];
app.newStars = [];
app.colsNoneNum = 0;
app.star = {
    width:30, // 星星的宽度
    height:30, // 高度
    margin:5, // 每个星星的边距
    rowNum:10, // 行数
    colsNum:10, // 列数
    colorNum:5, // 星星颜色数量 最大值为5 因为我TMD就做了5张星星图片
};
app.timer = null;
app.run = function() {
    this.box = $('#box');
    this.starBox = this.box.find('#star_box');
    this.initCanvas();
    this.initStars();
    this.draw();
    this.initBox();
    // this.write();
}
app.initCanvas = function() {
    var height = $(window).height();
    $('body').css('height', height+'px');
}
// 初始化box样式
app.initBox = function() {
    var boxWidth = this.star.width*this.star.colsNum+this.star.margin*this.star.colsNum;
    var boxHeight = this.star.height*this.star.rowNum+this.star.margin*this.star.rowNum;
    var left = ($(window).width() - boxWidth) / 2;
    this.box.css('left', left+'px');
    this.box.css('width', boxWidth+'px');
    this.box.css('height', boxHeight+'px');
}
// 初始化星星数组
app.initStars = function() {
    for(var i = 0; i < this.star.rowNum; i++) {
        this.stars[i] = [];
        for(var k = 0; k < this.star.colsNum; k++) {
            var color_index = Math.floor((Math.random()*this.star.colorNum));
            this.stars[i][k] = color_index;
        }
    }
    // this.stars = [[0,1,0,1,1],[0,0,0,1,0]]; // bug测试
    this.newStars = left2Array(this.stars);
    this.noLeftChangeStars = left2Array(this.stars);
}
app.initColsLink = function() {
    // 当前查找状态,一个数组对象,每个对象代表一列
    this.colsLink = [];
    for(var i = 0; i < this.star.colsNum; i++) {
        this.colsLink[i] = {x:[], num:0, max:Number(-1), count:this.initRowArray(1)};
    }
}
app.click = function(x, y) {
    x = parseInt(x);
    y = parseInt(y);
    var searchStars = [];
    searchStars[0] = {x:x, y:y};
    this.count = 0;
    this.linkStars = [];
    this.searchStars = [];
    this.bigSearch(searchStars); // 搜索 连接的星星
    this.clickAnimate();
}
app.mouseup = function() {
    clearTimeout(app.timer);
    app.timer = setTimeout(function() {
        app.starBox.find('.star').removeClass('link');
    }, 500);
}
// 触摸某个星星
// X坐标 和 Y坐标
app.touch = function(x, y) {
    x = parseInt(x);
    y = parseInt(y);
    var searchStars = [];
    searchStars[0] = {x:x, y:y};
    this.count = 0;
    this.linkStars = [];
    this.searchStars = [];
    this.bigSearch(searchStars); // 搜索 连接的星星
    this.initColsLink();
    this.colsNoneLenth = this.initColsArray(0);
    this.leftData = {min:Number(this.star.colsNum), y:[], num:0, count:this.initColsArray(1)};
    this.makeStars(); // 重新生成星星数组
    this.animate();
    // this.draw(); // 重新绘制星星
    // this.write(); // debug
}
// 星星动画
app.animate = function() {
    if(this.linkStars.length < 2) return;
    for(var i in this.linkStars) {
        var x = parseInt(this.linkStars[i].x);
        var y = parseInt(this.linkStars[i].y);
        app.delAnimate(x, y);
    }
    for(var i in this.colsLink) {
        var x = parseInt(this.colsLink[i].max);
        var y = parseInt(i);
        if(this.colsLink[i].x.length > 1) {
            var mOffset = 0;
            for(var j = this.colsLink[i].x.length-1; j >= 0; j--) {
                mOffset += this.colsLink[i].count[j];
                var r = this.colsLink[i].x[j-1];
                if(j - 1 < 0) r=-1;
                for(var t_x = this.colsLink[i].x[j]-1; t_x > r; t_x--) {
                    this.downAnimate(t_x, y, mOffset);
                }
            }
        }
        else {
            for(var t_x = x-1; t_x >= 0; t_x--) {
                this.downAnimate(t_x, y, this.colsLink[y].num);
            }
        }
    }
    if(this.leftData.min > -1) {
        if(this.leftData.y.length > 1) {
            var mOffset = 0;
            for(var j = 0; j <= this.leftData.y.length-1; j++) {
                mOffset += this.leftData.count[j];
                var r = this.leftData.y[j+1];
                if(j + 1 > this.leftData.y.length-1) r=this.star.colsNum;
                for(var n_x = 0; n_x <= this.star.rowNum-1; n_x++) {
                    for(var n_y = this.leftData.y[j]+1; n_y < r; n_y++) {
                        this.leftAnimate(n_x, n_y, mOffset);
                    }
                }
            }
        }
        else {
            var y = parseInt(this.leftData.min);
            for(var n_x = 0; n_x <= this.star.rowNum-1; n_x++) {
                for(var n_y = y+1; n_y < this.star.colsNum; n_y++) {
                    this.leftAnimate(n_x, n_y, this.leftData.num);
                }
            }
        }
    }
    // this.leftAnimate();
}
/* 消除星星的动画效果 */
app.delAnimate = function(x,y) {
    var index = x*this.star.colsNum + y; // 根据x、y计算对应dom中星星的 id
    var starDiv = this.starBox.find('.id_'+index);
    var left = parseInt(starDiv.css('left')) + this.star.width/2
    var top = parseInt(starDiv.css('top')) + this.star.height/2
    starDiv.find('img').animate({width:'0',height:'0'}, 500);
    starDiv.animate({ left:left+'px', top:top+'px', opacity:0}, 500, function(){$(this).hide();});
    starDiv.removeClass('id_'+index);
}
/* 星星向下移动的动画效果 */
app.downAnimate = function(x, y, move_num) {
    if(this.checkRepeat(x, y)) {
        return ;
    }
    var index = x*this.star.colsNum + y;
    var starDiv = this.starBox.find('.id_'+index);
    var dTop = parseInt(starDiv.css('top'));
    var top = dTop + (this.star.height + this.star.margin) * move_num;
    starDiv.animate({top:top+'px'}, 300);
    var n_x_ = x + move_num;
    starDiv.attr('ondblclick', 'app.touch('+n_x_+','+y+')');
    starDiv.attr('onmousedown', 'app.click('+n_x_+','+y+')');
    starDiv.removeClass('id_'+index);
    var id = parseInt(n_x_*this.star.colsNum) + parseInt(y);
    starDiv.addClass('id_'+id);
}
/* 星星向左移动的动画效果 */
app.leftAnimate = function(x, y, move_num) {
    var index = x*this.star.colsNum + y;
    var starDiv = this.starBox.find('.id_'+index);
    var dLeft = parseInt(starDiv.css('left'));
    var left = dLeft - (this.star.width + this.star.margin) * move_num;
    starDiv.animate({left:left+'px'}, 300);
    var n_y_ = y - move_num;
    starDiv.attr('ondblclick', 'app.touch('+x+','+n_y_+')');
    starDiv.attr('onmousedown', 'app.click('+x+','+n_y_+')');
    starDiv.removeClass('id_'+index);
    var id = parseInt(x*this.star.colsNum) + parseInt(n_y_);
    starDiv.addClass('id_'+id);
}
// 点击提示连接星星动画
app.clickAnimate = function() {
    if(this.linkStars.length < 2) return;
    this.starBox.find('.star').removeClass('link');
    for(var i in this.linkStars) {
        var x = parseInt(this.linkStars[i].x);
        var y = parseInt(this.linkStars[i].y);
        var index = x*this.star.colsNum + y;
        var starDiv = this.starBox.find('.id_'+index);
        starDiv.addClass('link');
    }
}
/* 递归遍历查找 */
app.bigSearch = function(searchStars) {
    if(searchStars.length == 0) return ;
    this.newSearchStars = [];
    this.s_count = 0;
    for(var i in searchStars) {
        var star = searchStars[i];
        var x = parseInt(star.x);
        var y = parseInt(star.y);
        if(!this.checkRepeat(x, y)) {
            this.linkStars[this.count] = {x:x, y:y};
        }
        this.count++;
        this.search(x, y, 'top');
        this.search(x, y, 'right');
        this.search(x, y, 'down');
        this.search(x, y, 'left');
    }
    this.bigSearch(this.newSearchStars);
}
/* 上下左右 查找 */
app.search = function(x, y, position) {
    if(position == 'top') {
        var top = x-1;
        if(top < 0) return;
        if(this.stars[x][y] == this.stars[top][y] && !this.checkRepeat(top, y)) {
            this.newSearchStars[this.s_count] = {x:top, y:y};
        }
    }
    else if(position == 'right') {
        var right = y+1;
        if(right > this.star.colsNum-1) return;
        if(this.stars[x][y] == this.stars[x][right] && !this.checkRepeat(x, right)) {
            this.newSearchStars[this.s_count] = {x:x, y:right};
        }
    }
    else if(position == 'down') {
        var down = x+1;
        if(down > this.star.rowNum-1) return;
        if(this.stars[x][y] == this.stars[down][y] && !this.checkRepeat(down, y)) {
            this.newSearchStars[this.s_count] = {x:down, y:y};
        }
    }
    else if(position == 'left') {
        var left = y-1;
        if(left < 0) return;
        if(this.stars[x][y] == this.stars[x][left] && !this.checkRepeat(x, left)) {
            this.newSearchStars[this.s_count] = {x:x, y:left};
        }
    }
    this.s_count++;
}
// 根据传递的x, y来检测是否存在在linkStars中 如果存在则返回 true
app.checkRepeat = function(x, y) {
    if(this.linkStars.length == 0) return false;
    for(var i in this.linkStars) {
        var star = this.linkStars[i];
        if(parseInt(star.x) == parseInt(x) && parseInt(star.y) == parseInt(y)) return true;
    }
    return false;
}
// 从新构造“星星”数组
// stars、newStars必须初始化完成
// linkStars必须>=2个星星
app.makeStars = function() {
    if(this.stars.length==0 || this.newStars.length==0 || this.linkStars.length==0 || this.linkStars.length<2) return false;
    // -== setp-1 ==-
    /*
        在相连数组中查找当前星星是否是相连的
        如果是相连的星星 则在newStars中把该星星以上的星星的值都赋值给x+1的星星
        然后在newStars中把最上面的一个元素 即[0][y]的元素值设为-1;
    */
    var clx_count = this.initColsArray(0);
    for(var x in this.stars) {
        x = parseInt(x);
        for(var y in this.stars[x]) {
            y = parseInt(y);
            if(this.stars[x][y] != -1 && this.checkRepeat(x,y)) {
                for(var n_x = x-1; n_x >= 0; n_x--) {
                    this.newStars[n_x+1][y] = this.newStars[n_x][y];
                }
                this.newStars[0][y] = -1;
                this.colsLink[y].num += 1;
                if(this.colsLink[y].max < x) {
                    this.colsLink[y].max = x;
                    if((x+1 <= this.stars.length-1 && !this.checkRepeat(x+1,y)) || (x == this.stars.length-1 && this.checkRepeat(x,y))) {
                        this.colsLink[y].x[clx_count[y]] = x;
                        clx_count[y]++;
                    }
                    else if(x+1 <= this.stars.length-1 && this.checkRepeat(x+1,y)) {
                        this.colsLink[y].count[clx_count[y]] += 1;
                    }
                }
                this.colsNoneLenth[y] += 1;
            }
        }
    }
    // -== setp-2 ==-
    // 主要是为生成左移动画统计数据
    this.noLeftChangeStars = left2Array(this.newStars);
    var ld_count = 0;
    for(var y = 0; y <= this.star.colsNum-1; y++) {
        y = parseInt(y);
        // if(this.star.colsNum - (y+1) < this.colsNoneNum) continue;
        // 判断当前列是否全部被设置为-1
        if(this.checkColsNone(y)) {
            if(this.leftData.min > y) {
                this.leftData.min = y;
            }
            if((y+1 <= this.star.colsNum-1 && !this.checkColsNone(y+1)) || (y == this.star.colsNum-1)) {
                this.leftData.y[ld_count] = y;
                ld_count++;
            }
            else if(y+1 <= this.star.colsNum-1 && this.checkColsNone(y+1)) {
                this.leftData.count[ld_count] += 1;
            }
            this.leftData.num += 1;
            // this.colsNoneNum += 1;
        }
    }
    // -== setp-3 ==-
    // 左移数据 并从新构造新数组
    if(this.leftData.min > -1) {
        var check = this.leftData.min;
        for(var y = 0; y < this.star.colsNum; y++) {
            if(this.checkNewColsNone(check)) {
                for(var n_x = 0; n_x <= this.star.rowNum-1; n_x++) {
                    for(var n_y = check+1; n_y < this.star.colsNum; n_y++) {
                        this.newStars[n_x][n_y-1] = this.newStars[n_x][n_y];
                    }
                    this.newStars[n_x][this.star.colsNum-1] = -1;
                }
            }
            else {
                check += 1;
            }
        }
    }
    // 把新构造的数组 再赋值给星星数组
    this.stars = left2Array(this.newStars);
}
// 检测当前列是否全部消空 如果消空返回true
// 数组未被左移破坏,只被下移修改过
app.checkColsNone = function(y) {
    var count = 0;
    for(var x = 0; x < this.star.rowNum; x++) {
        if(this.noLeftChangeStars[x][y] == Number(-1)) count++;
    }
    if(count == this.star.rowNum) return true;
    return false;
}
// 检测当前列是否全部消空 如果消空返回true
// 数组为每次下移和左移之后新生成的数组
app.checkNewColsNone = function(y) {
    var count = 0;
    for(var x = 0; x < this.star.rowNum; x++) {
        if(this.newStars[x][y] == Number(-1)) count++;
    }
    if(count == this.star.rowNum) return true;
    return false;
}
app.draw = function() {
    var starsDiv = '';
    for(var x in this.stars) {
        x = parseInt(x);
        for(var y in this.stars[x]) {
            y = parseInt(y);
            var star = this.stars[x][y];
            if(star == -1) {
                continue;
            }
            var left = y*this.star.width+y*5;
            var top = x*this.star.height+x*5;
            var index = x*this.star.colsNum + y;
            starsDiv += '<div class="star id_'+index+'" style="left:'+left+'px; top:'+top+'px; width:'+this.star.width+'px;height:'+this.star.height+'px;" ondblclick="app.touch('+x+','+y+');" onmousedown="app.click('+x+','+y+');" onmouseup="app.mouseup();"><img src="http://sandbox.runjs.cn/uploads/rs/437/doeiphrq/star_'+star+'.png" width="'+this.star.width+'" height="'+this.star.height+'"/></div>';
        }
    }
    $('#star_box').html(starsDiv);
}
app.initColsArray = function(val) {
    var array = [];
    if(val == 'undefined') val = 0;
    for(var i = 0; i < this.star.colsNum; i++) {
        array[i] = val;
    }
    return array;
}
app.initRowArray = function(val) {
    var array = [];
    if(val == 'undefined') val = 0;
    for(var i = 0; i < this.star.rowNum; i++) {
        array[i] = val;
    }
    return array;
}
app.write = function() {
    var html = '';
    for(var i in this.stars) {
        var line = this.stars[i];
        for(var j in line) {
            var star = line[j];
            var color = 'red';
            if(star == -1) {
                color = 'blue';
            }
            html += '<font color="'+color+'">'+star+'</font><font color="#999">('+i+','+j+')</font>  ';
        }
        html += '<br/><br/>';
    }
    html += '<p>--===================================================--<p>';
    $('#show').append(html);
}
function left2Array(array) {
    if(array.length < 0) return array;
    var newArray = [];
    for(var i in array) {
        newArray[i] = [];
        for(var j in array[i]) {
            newArray[i][j] = array[i][j];
        }
    }
    return newArray;
}
</script>
</head>
<body>
    <div id="box">
        <div id="star_box">
        </div>
    </div>
    <div id="show" style="padding-top:600px;"></div>
<!--     X:<input type="text" id="x" value=""/>
    Y:<input type="text" id="y" value=""/>
    <input type="button" value="点击" onclick="app.touch($('#x').val(), $('#y').val());"/>
    <br/>
    <br/> -->
</body>
</html>

总结

以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作能带来一定的帮助,如果有疑问大家可以留言交流。谢谢大家对三水点靠木的支持。

Javascript 相关文章推荐
jQuery动态添加删除select项(实现代码)
Sep 03 Javascript
jquery实现TAB选项卡鼠标经过带延迟效果的方法
Jul 27 Javascript
JavaScript Ajax编程 应用篇
Jul 02 Javascript
js利用clipboardData实现截屏粘贴功能
Oct 12 Javascript
JS实现的DIV块来回滚动效果示例
Feb 07 Javascript
值得收藏的vuejs安装教程
Nov 21 Javascript
jQuery实现的简单获取索引功能示例
Jun 04 jQuery
JS函数动态传递参数的方法分析【基于arguments对象】
Jun 05 Javascript
vue集成kindeditor富文本的实现示例代码
Jun 07 Javascript
使用typescript构建Vue应用的实现
Aug 26 Javascript
iview form清除校验状态的实现
Sep 19 Javascript
微信小程序实现天气预报功能(附源码)
Dec 10 Javascript
js滚轮事件兼容性问题需要注意哪些
Nov 15 #Javascript
禁用backspace网页回退功能的实现代码
Nov 15 #Javascript
sea.js常用的api简易文档
Nov 15 #Javascript
js实现倒计时及时间对象
Nov 15 #Javascript
Bootstrap简单表单显示学习笔记
Nov 15 #Javascript
JS实现根据用户输入分钟进行倒计时功能
Nov 14 #Javascript
js调用屏幕宽度的简单方法
Nov 14 #Javascript
You might like
浅谈PHP调用Webservice思路及源码分享
2014/06/04 PHP
Linux+Nginx+MySQL下配置论坛程序Discuz的基本教程
2015/12/23 PHP
thinkphp命名空间用法实例详解
2015/12/30 PHP
PHP数据分析引擎计算余弦相似度算法示例
2017/08/08 PHP
php注册系统和使用Xajax即时验证用户名是否被占用
2017/08/31 PHP
JavaScript 学习技巧
2010/02/17 Javascript
qTip2 精致的基于jQuery提示信息插件
2012/02/17 Javascript
js 字符串转换成数字的三种方法
2013/03/23 Javascript
ExtJS4利根据登录后不同的角色分配不同的树形菜单
2014/05/02 Javascript
深入分析JSONP跨域的原理
2014/12/10 Javascript
javascript中JSON对象与JSON字符串相互转换实例
2015/07/11 Javascript
深入浅析JavaScript中prototype和proto的关系
2015/11/15 Javascript
JS读取XML文件数据并以table形式显示数据的方法(兼容IE与火狐)
2016/06/02 Javascript
JSP基于Bootstrap分页显示实例解析
2016/06/12 Javascript
浅谈angularjs module返回对象的坑(推荐)
2016/10/21 Javascript
Angular学习笔记之angular的$filter服务浅析
2016/11/12 Javascript
微信小程序开发探究
2016/12/27 Javascript
实例解析js中try、catch、finally的执行规则
2017/02/24 Javascript
js模拟百度模糊搜索的实例
2017/08/04 Javascript
H5+C3+JS实现五子棋游戏(AI篇)
2020/05/28 Javascript
vue使用Font Awesome的方法步骤
2019/02/26 Javascript
详解VUE前端按钮权限控制
2019/04/26 Javascript
Sublime Text3 配置 NodeJs 环境的方法
2020/05/20 NodeJs
Python选择排序、冒泡排序、合并排序代码实例
2015/04/10 Python
Python使用cx_Oracle模块将oracle中数据导出到csv文件的方法
2015/05/16 Python
python定时执行指定函数的方法
2015/05/27 Python
Python实现股市信息下载的方法
2015/06/15 Python
开源Web应用框架Django图文教程
2017/03/09 Python
Python文本特征抽取与向量化算法学习
2017/12/22 Python
Python快速查找list中相同部分的方法
2018/06/27 Python
Python OpenCV实现测量图片物体宽度
2020/05/27 Python
有影响力的品牌之家:Our Social Collective
2019/06/08 全球购物
澳大利亚个性化儿童礼品网站:Bright Star Kids
2019/06/14 全球购物
标准离婚协议书范文下载
2014/11/30 职场文书
三国演义读书笔记
2015/06/25 职场文书
ICOM R71E和R72E图文对比解说
2022/04/07 无线电