原生JS之扫雷

注:所有代码是根据网上教程所编写

html代码

<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>扫雷</title>
    <link rel="stylesheet" href="style.css">
    
</head>
<body>
  <div class="wrapper">
      <div class="btn" id="btn"></div>
     
      <div class="box" id="box"></div>
       <div class="flag" id="flag">
          当前剩余累数:
          <span id="score">10</span>
      </div>
      <div class="alertBox" id="alertBox">
          <div class="alertImg" id="alertImg">
              <div class="close" id="close"></div>
          </div>
      </div>
  </div>
  <script src="sl.js"></script>
</body>
</html>

css代码

*{
    margin: 0;
    padding: 0;
}
.wrapper{
    width: 100%;
    height: 1000px;
    position: fixed;
    top:0;
    left: 0;
    background-image:url('img/bg.jpg') ;
    background-size: 100% 100%;
}
.btn{
    height: 80px;
    width: 170px;
    position: absolute;
    left:50%;
    margin-left:-85px; 
    top:75%;
    background-image:url('img/start.gif') ;
    background-size: 100% 100%;
    cursor: pointer;
}
.box{
    height: 500px;
    width: 500px;
    /* 设置景深800px  绕x轴旋转45°*/
    transform: perspective(500px) rotateX(45deg) ;
    margin: 100px auto;
    /* border:1px solid #B25F27;  */
    border-top:1px solid #B25F27;
    border-left: 1px solid #B25F27; 
    /* 设置边框阴影 */
    box-shadow: 5px 5px 5px rgba(0,0, 0, 0.3);
    display: none;
   

}
.flag{
    position: absolute;
    top:150px;
    left:50%;
    width: 200px;
    height: 50px;
    margin-left:-100px;
    color: #333333;
    font-size: 20px;
    font-weight: bolder; 
    display: none;
}
.alertBox{
    display: none;
    position: absolute;
    width: 100%;
    height: 100%;
    left: 0;
    top:0;
    background-color: rgba(0,0, 0, 0.2);
}
.alertImg{
    height: 400px;
    width: 600px;
    background-size: 100% 100%;
    position: absolute;
    left: 0;
    right: 0;
    top:20%;
    margin: auto;
    border-radius: 20px;
}
.close{
    position: absolute;
    right: 0;
    top:0;
    height: 30px;
    width: 30px;
    background-image: url('img/x.jpg');
    background-size: 100% 100%;
    cursor: pointer;
    border-radius: 20px;

}
.block{
    float: left;
    width: 49px;
    height: 49px;
    border-right: 1px solid #B25F27;
    border-bottom: 1px solid #B25F27;
    /* 向内阴影 */
    box-shadow: 0 0 4px #333333 inset;
    background-image: url('img/green.jpg');
    background-size: 100% 100%;
    cursor: pointer;
}
.show{
    background-image: url('img/mine.jpg');
    background-size: 100% 100%;
}
.num{
    background: #ECD0A1;
    font-size: 18px;
    font-weight: bold;
    line-height: 49px;
    text-align: center;
}
.flagbox{
    background-image: url('img/flag.jpg');
    background-size: 100% 100%;
}

js部分

编码的逻辑思路

点击开始游戏 动态生成100个格子-->100div

leftClick没有雷 显示数字(代表以当前格子为中心,周围8个格子的雷个数) 有雷 游戏结束

扩散(当前周围没有雷)

rightClick 没有标记并且没有数字--进行标记/有标记--取消标记 判断标记是否正确,所有都正确标记,提示成功

已经出现数字--不进行任何操作

代码

var  startBtn=document.getElementById('btn');
var  box=document.getElementById('box');
var  flag=document.getElementById('flag');
var  alertBox=document.getElementById('alertBox');
var alertImg=document.getElementById('alertImg');
var close=document.getElementById('close');
var  score=document.getElementById('score');
var minesNum;//雷的数量
var minesOver;//被标记的雷的数量
var block;//选中的格子
var mineMap=[];

var  startGame=true;


bindEvent();
function bindEvent(){
    startBtn.onclick=function(){
        if(startGame){
            box.style.display='block';
            flag.style.display='block';
            init();
            startGame=false;
        }
        
        
    }
    //取消默认事件
    box.oncontextmenu=function(){
        return false;
    }

    box.onmousedown=function(e){
        //获取事件原对象  即当前点击的格子
        var event=e.target;
        //e.which==1代表点击左键
        if(e.which==1){
            leftClick(event);
        }//e.which==3代表点击右键
        else if(e.which==3){
            rightClick(event);
        }
    }
    close.onclick=function(){
        alertBox.style.display='none';
        flag.style.display='none';
        box.style.display='none';
        box.innerHTML='';
        startGame=true;
    }
}
//生成100个格子  并随机生成10个雷区
function init(){
    minesNum=10;
    minesOver=10;
    score.innerHTML=minesOver;

    for(var i=0;i<10;i++){
        for(var j=0;j<10;j++){
            var con=document.createElement('div');
            //给生成的每个div添加类名
            con.classList.add('block');
            //用行和列表示每一个格子的id
            con.setAttribute('id',i+'-'+j);
            //将生成的格子插入box里
            box.appendChild(con);
            mineMap.push({mine:0});
        }
    }

    block=document.getElementsByClassName('block');
    //随机生成雷区
    while(minesNum){
        var mineIndex=Math.floor(Math.random()*100);
        if(mineMap[mineIndex].mine==0){
            mineMap[mineIndex].mine=1;//表示已经生成雷区
            block[mineIndex].classList.add('ismine');
            minesNum--;
        }
    }
    

}
//dom表示点击事件的原对象
function leftClick(dom){
    //插旗后  不能被左点击
    if(dom.classList.contains('flagbox')){
        return ;
    }
    var ismine=document.getElementsByClassName('ismine');
    if(dom&& dom.classList.contains('ismine')){
        //游戏失败的情况
        for(var i=0;i<ismine.length;i++){
            ismine[i].classList.add('show'); 
        }
        setTimeout(function(){
             alertBox.style.display='block'; 
            
             alertImg.style.backgroundImage='url("img/over.jpg")';      
         
           
        },500)
    }
    else {
        var n=0;//表示点击的格子周围的雷的个数
        var posArr = dom && dom.getAttribute('id').split('-');
        var posX = posArr && +posArr[0];//x轴坐标值
        var posY = posArr&& +posArr[1];//y轴坐标值
        dom && dom.classList.add('num');
        //坐标i,j周围的关系
        //i-1,j-1   i-1,j  i-1,j+1
        //i,j-1     i,j    i,j+1
        //i+1,j-1   i+1,j  i+1,j+1

        for(var i=posX-1;i<=posX+1;i++){
            for(var j=posY-1;j<=posY+1;j++){
               var aroundBox = document.getElementById(i+'-'+j);
               //aroundBox.classList.contains('ismine')  表示类名为ismine
               if(aroundBox&&aroundBox.classList.contains('ismine')){
                   n++;
               }
            }
        }
        dom && (dom.innerHTML=n);
        if(n==0){
            for(var i=posX-1;i<=posX+1;i++){
                for(var j=posY-1;j<=posY+1;j++){
                  var nearBox=document.getElementById(i+'-'+j);
                  if(nearBox&&nearBox.length!=0){
                      //判断格子是否被点击或者已经显示数字
                      if(!nearBox.classList.contains('check')){
                            nearBox.classList.add('check')
                            leftClick(nearBox);
                      }
                      
                  }
                }
            }
        }
    }
}

function rightClick(dom){
    //判断是否已经显示数字  如果已经显示数字 则不做任何操作
    if(dom.classList.contains('num')){
        return ;
    }
    //toggle切换   如果没有flagbox类名,则加上,反之则去掉
    dom.classList.toggle('flagbox');
    
    if(dom.classList.contains('ismine')&&dom.classList.contains('flagbox')){
        minesOver--;
    }
    if(dom.classList.contains('ismine')&&!dom.classList.contains('flagbox')){
        minesOver++;
    }
    score.innerHTML=minesOver;
    if(minesOver==0)
    {
       
            alertBox.style.display='block'; 
           
            alertImg.style.backgroundImage='url("img/success.jpg")';      
      
    }
}

猜你喜欢

转载自blog.csdn.net/G_072625/article/details/81949245
今日推荐