javascript实现扫雷简易版


Posted in Javascript onAugust 18, 2020

本文实例为大家分享了javascript实现扫雷简易版的具体代码,供大家参考,具体内容如下

使用截图

javascript实现扫雷简易版

说明

这个完成的建议版本,所以没有插旗子,没有计时,就是最基本的原理实现,熟练的大佬30min就能完成

代码讲解

初始数据

var MAPSIZE = 10;
 var BOMBNUM = 1;
 var BOMBPOSITION = {};
 var SQUAERPOSITION = {};
 var SQUARECHECK = {};
 var end = false;

初始化地图(CreateMap())

用BOMBPOSITION这个hash表记录雷的位置,然后生成地图长*地图宽数量的div块然后完成定位,然后用SQUAERPOSITION记录这些div块并且用SQUARECHECK记录当前这些块有没有被点击(记录是否是未开启块)

function CreateMap() {
  //生成初始的地图
  //根据雷的数目生成一个随机雷数目
  Create_BOMB();
  for (let i = 0; i < MAPSIZE; i++) {
  for (let j = 0; j < MAPSIZE; j++) {
   var divEle = document.createElement("div");
   divEle.className = "lattice";
   divEle.style.top = 20 * i + "px";
   divEle.style.left = 20 * j + "px";
   divEle.onclick = function () {
   //这里点击后进行判断
   if (end == false) {
    if (BOMBPOSITION[i + "_" + j] == 1) {
    //展示所有炸弹的位置
    GAMEOVER();
    } else {
    //进行一个递归的更改
    Remove(i, j);
    }
   }
   }
   document.getElementById("container").appendChild(divEle);
   SQUAERPOSITION[i + "_" + j] = divEle;
   SQUARECHECK[i + "_" + j] = false;
  }
  }
 }

生成雷(Create_BOMB())

这里的生成就是完善BOMBPOSITION这个hash表

function Create_BOMB() {
  let bombnum = 0;
  while (bombnum < BOMBNUM) {
  let x = _.random(0, MAPSIZE - 1);
  let y = _.random(0, MAPSIZE - 1);
  if (BOMBPOSITION[x + "_" + y] == undefined) {
   BOMBPOSITION[x + "_" + y] = 1;
   bombnum++;
  }
  }
 }

每个div块的点击事件

游戏结束GAMEOVER()

如果点到了雷就展示所有雷的位置然后游戏结束

function GAMEOVER() {
  for (let index in BOMBPOSITION) {
  SQUAERPOSITION[index].innerText = "@"
  }
  end = true;
 }

处理点击的块(Remove())

这个处理是个递归过程,一个div会引起其他div的处理所有要先检查下游戏是不是结束了,如果没结束就遍历周边一圈的块,也就是x - 1 -> x + 1 y - 1 -> y + 1,但是自身就不需要遍历了,这里要注意,然后这些块如果已经被处理过了也不用进行处理,遍历完后如果有雷则在这个块上记录雷数目,如果没有雷那么就将周边块中未遍历的进行Remove()处理,这个过程是一个递归,也可以理解成深度优先级处理。

function Remove(x, y) {
  if (ISGAMEOVER()) {
  if (end == false) {
   alert("游戏结束");
   GAMEOVER();
  }
  return;
  }

  let Result_Detection = Bomb_Detection(x, y);
  if (Result_Detection[0].length == 1) {
  if (Result_Detection[0][0] == 0) {
   //单纯变颜色
   Change(x, y);
  } else {
   //更改里面的文字是雷的数目
   Change(x, y);
   SQUAERPOSITION[x + "_" + y].innerText = Result_Detection[0][0];
  }
  } else {
  //如果没有雷自己先变化然后遍历剩下的
  Change(x, y);
  for (let i = 0; i < Result_Detection.length; i++) {
   //遍历八个方向剩下的
   Remove(Result_Detection[i][0], Result_Detection[i][1]);
  }
  //console.log(x + " " + y);
  //console.log(Result_Detection);
  }

 }

检测游戏是否结束(ISGAMEOVER())

就是看一下还有多少块没被处理,如果正好是雷的数目那就游戏结束了

function ISGAMEOVER() {
  let UsedNum = 0;
  for (let index in SQUARECHECK) {
  if (SQUARECHECK[index] == true) {
   UsedNum++;
  }
  }
  console.log(UsedNum);
  if (UsedNum == MAPSIZE * MAPSIZE - BOMBNUM)
  return true;
  else
  return false;
 }

周边遍历(Bomb_Detection())

如果有雷就返回[[Bomb_num]],如果没有雷但是周边的都被遍历过了就返回[[0]],如果没有雷然后有未被遍历过的元素则返回未遍历数组queue[]

function Bomb_Detection(x, y) {
  let queue = [];
  let bombnum = 0;
  for (let i = x - 1; i <= x + 1; i++) {
  for (let j = y - 1; j <= y + 1; j++) {
   if ((i != x || j != y)&&Edge_Detection(i,j) == true) {
   if (BOMBPOSITION[i + "_" + j] == 1) {
    bombnum++;
   } else if (SQUARECHECK[i + "_" + j] == false) {
    queue.push([i, j]);
   }
   }
  }
  }
  if (bombnum > 0) {
  //如果周边有雷
  return [
   [bombnum]
  ];
  } else if (bombnum == 0 && queue.length == 0) {
  //如果周边没雷但是所有的都被遍历过了
  return [
   [0]
  ];
  } else {
  return queue;
  }
 }

边界检测(Edge_Detection())

在遍历周边块的时候要注意,这个周边块需要是合理的

function Edge_Detection(x, y) {
  //只要在0,0 -> MAPSIZE,MAPSIZE就行
  if (x >= 0 && y >= 0 && x < MAPSIZE && y < MAPSIZE) {
  return true
  } else {
  return false
  }
 }

处理被处理的块(Change())

如果是周边没有雷那就是变成空白,如果有就写上数字,如果是雷就里面加上@

function Change(x, y) {
  SQUAERPOSITION[x + "_" + y].className = "lattice2";
  SQUARECHECK[x + "_" + y] = true;
  SQUAERPOSITION[x + "_" + y].style.top = 20 * x + "px";
  SQUAERPOSITION[x + "_" + y].style.left = 20 * y + "px";
 }

整体代码

<!DOCTYPE html>
<html>

<head>
 <title>扫雷</title>
 <meta charset="utf-8">
 <style>
 .container {
  left: 200px;
  height: 200px;
  width: 200px;
  position: relative;
 }

 .lattice {
  height: 20px;
  width: 20px;
  top: 0px;
  left: 0px;
  border-style: solid;
  border-width: 1px;
  border-color: #ffffff;
  background-color: #5E5E5E;
  position: absolute;
  color: crimson;
 }

 .lattice2 {
  height: 20px;
  width: 20px;
  top: 0px;
  left: 0px;
  border-style: solid;
  border-width: 1px;
  border-color: #5E5E5E;
  background-color: #ffffff;
  position: absolute;
  color: black;
 }
 </style>
 <script type="text/javascript" src="http://cdn.bootcss.com/lodash.js/4.16.6/lodash.min.js"></script>
 <script>
 var MAPSIZE = 10;
 var BOMBNUM = 1;
 var BOMBPOSITION = {};
 var SQUAERPOSITION = {};
 var SQUARECHECK = {};
 var end = false;

 function Init() {
  CreateMap();
 }

 function CreateMap() {
  //生成初始的地图
  //根据雷的数目生成一个随机雷数目
  Create_BOMB();
  for (let i = 0; i < MAPSIZE; i++) {
  for (let j = 0; j < MAPSIZE; j++) {
   var divEle = document.createElement("div");
   divEle.className = "lattice";
   divEle.style.top = 20 * i + "px";
   divEle.style.left = 20 * j + "px";
   divEle.onclick = function () {
   //这里点击后进行判断
   if (end == false) {
    if (BOMBPOSITION[i + "_" + j] == 1) {
    //展示所有炸弹的位置
    GAMEOVER();
    } else {
    //进行一个递归的更改
    Remove(i, j);
    }
   }
   }
   document.getElementById("container").appendChild(divEle);
   SQUAERPOSITION[i + "_" + j] = divEle;
   SQUARECHECK[i + "_" + j] = false;
  }
  }
 }

 function Create_BOMB() {
  let bombnum = 0;
  while (bombnum < BOMBNUM) {
  let x = _.random(0, MAPSIZE - 1);
  let y = _.random(0, MAPSIZE - 1);
  if (BOMBPOSITION[x + "_" + y] == undefined) {
   BOMBPOSITION[x + "_" + y] = 1;
   bombnum++;
  }
  }
 }

 function Remove(x, y) {
  if (ISGAMEOVER()) {
  if (end == false) {
   alert("游戏结束");
   GAMEOVER();
  }
  return;
  }

  let Result_Detection = Bomb_Detection(x, y);
  if (Result_Detection[0].length == 1) {
  if (Result_Detection[0][0] == 0) {
   //单纯变颜色
   Change(x, y);
  } else {
   //更改里面的文字是雷的数目
   Change(x, y);
   SQUAERPOSITION[x + "_" + y].innerText = Result_Detection[0][0];
  }
  } else {
  //如果没有雷自己先变化然后遍历剩下的
  Change(x, y);
  for (let i = 0; i < Result_Detection.length; i++) {
   //遍历八个方向剩下的
   Remove(Result_Detection[i][0], Result_Detection[i][1]);
  }
  //console.log(x + " " + y);
  //console.log(Result_Detection);
  }

 }

 function Change(x, y) {
  SQUAERPOSITION[x + "_" + y].className = "lattice2";
  SQUARECHECK[x + "_" + y] = true;
  SQUAERPOSITION[x + "_" + y].style.top = 20 * x + "px";
  SQUAERPOSITION[x + "_" + y].style.left = 20 * y + "px";
 }

 function GAMEOVER() {
  for (let index in BOMBPOSITION) {
  SQUAERPOSITION[index].innerText = "@"
  }
  end = true;
 }

 function ISGAMEOVER() {
  let UsedNum = 0;
  for (let index in SQUARECHECK) {
  if (SQUARECHECK[index] == true) {
   UsedNum++;
  }
  }
  console.log(UsedNum);
  if (UsedNum == MAPSIZE * MAPSIZE - BOMBNUM)
  return true;
  else
  return false;
 }

 function Bomb_Detection(x, y) {
  let queue = [];
  let bombnum = 0;
  for (let i = x - 1; i <= x + 1; i++) {
  for (let j = y - 1; j <= y + 1; j++) {
   if ((i != x || j != y)&&Edge_Detection(i,j) == true) {
   if (BOMBPOSITION[i + "_" + j] == 1) {
    bombnum++;
   } else if (SQUARECHECK[i + "_" + j] == false) {
    queue.push([i, j]);
   }
   }
  }
  }
  if (bombnum > 0) {
  //如果周边有雷
  return [
   [bombnum]
  ];
  } else if (bombnum == 0 && queue.length == 0) {
  //如果周边没雷但是所有的都被遍历过了
  return [
   [0]
  ];
  } else {
  return queue;
  }
 }

 function Edge_Detection(x, y) {
  //只要在0,0 -> MAPSIZE,MAPSIZE就行
  if (x >= 0 && y >= 0 && x < MAPSIZE && y < MAPSIZE) {
  return true
  } else {
  return false
  }
 }
 </script>
</head>

<body onload="Init()">
 <div class="container" id="container">

 </div>
</body>

</html>

更多有趣的经典小游戏实现专题,分享给大家:

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
JavaScript this 深入理解
Jul 30 Javascript
javascript搜索框点击文字消失失焦时文本出现
Sep 18 Javascript
node.js中的events.emitter.removeAllListeners方法使用说明
Dec 10 Javascript
javascript 数组操作详解
Jan 29 Javascript
bootstrap jquery dataTable 异步ajax刷新表格数据的实现方法
Feb 10 Javascript
javascript 组合按键事件监听实现代码
Feb 21 Javascript
js微信应用场景之微信音乐相册案例分享
Aug 11 Javascript
详解在Node.js中发起HTTP请求的5种方法
Jan 10 Javascript
vue+egg+jwt实现登录验证的示例代码
May 18 Javascript
基于Vue SEO的四种方案(小结)
Jul 01 Javascript
vue 父组件通过v-model接收子组件的值的代码
Oct 27 Javascript
前端使用crypto.js进行加密的函数代码
Aug 16 Javascript
详解Vue的组件中data选项为什么必须是函数
Aug 17 #Javascript
Openlayers实现扩散的动态点(水纹效果)
Aug 17 #Javascript
openLayer4实现动态改变标注图标
Aug 17 #Javascript
openlayers4实现点动态扩散
Aug 17 #Javascript
Vue实现计算器计算效果
Aug 17 #Javascript
vue-model实现简易计算器
Aug 17 #Javascript
Vue实现手机计算器
Aug 17 #Javascript
You might like
PHP 高手之路(三)
2006/10/09 PHP
[转帖]PHP世纪万年历
2006/12/06 PHP
利用PHP实现短域名互转
2013/07/05 PHP
用jQuery简化JavaScript开发分析
2009/02/19 Javascript
js window.onload 加载多个函数的方法
2009/11/02 Javascript
MooBox 基于Mootools的对话框插件
2012/01/20 Javascript
js控制表单奇偶行样式的简单方法
2013/07/31 Javascript
javascript中动态加载js文件多种解决办法总结
2013/11/15 Javascript
模拟一个类似百度google的模糊搜索下拉列表
2014/04/15 Javascript
js统计页面的来访次数实现代码
2014/05/09 Javascript
js浏览器本地存储store.js介绍及应用
2014/05/13 Javascript
jQuery中last()方法用法实例
2015/01/06 Javascript
JS中字符串trim()使用示例
2015/05/26 Javascript
JavaScript中几种排序算法的简单实现
2015/07/29 Javascript
AngularJS基础教程之简单介绍
2015/09/27 Javascript
jQuery fancybox在ie浏览器下无法显示关闭按钮的解决办法
2016/02/19 Javascript
JavaScript ES6中CLASS的使用详解
2016/11/22 Javascript
详解用原生JavaScript实现jQuery的某些简单功能
2016/12/19 Javascript
简单易扩展可控性强的Jquery转盘抽奖程序
2019/03/16 jQuery
使用vue-router切换页面时实现设置过渡动画
2019/10/31 Javascript
使用Vue-scroller页面input框不能触发滑动的问题及解决方法
2020/08/08 Javascript
python下paramiko模块实现ssh连接登录Linux服务器
2015/06/03 Python
Android 兼容性问题:java.lang.UnsupportedOperationException解决办法
2017/03/19 Python
python进阶之多线程对同一个全局变量的处理方法
2018/11/09 Python
pandas 将索引值相加的方法
2018/11/15 Python
Python英文文本分词(无空格)模块wordninja的使用实例
2019/02/20 Python
Python关于__name__属性的含义和作用详解
2020/02/19 Python
Django单元测试中Fixtures的使用方法
2020/02/26 Python
python3 logging日志封装实例
2020/04/08 Python
Django 用户登陆访问限制实例 @login_required
2020/05/13 Python
CSS教程:CSS3圆角属性
2009/04/02 HTML / CSS
StubHub新加坡:购买和出售全球活动门票
2017/03/10 全球购物
罗马尼亚购物网站:Vivantis.ro
2019/07/20 全球购物
预备党员转正党小组意见
2015/06/01 职场文书
升学宴祝酒词
2015/08/11 职场文书
2019年年中工作总结讲话稿模板
2019/03/25 职场文书