基于JavaScript实现十五拼图代码实例


Posted in Javascript onApril 26, 2020

顾名思义,十五拼图就是将游戏画面中的数字从上到下,从左到右按顺序从1到15排列下来,看起来很简单,但是玩起来不容易。

css代码

body {
  font-family: cursive;
  font-size: 14pt;
  text-align: center;
}

#puzzlearea {
  height: 400px;
  margin: 0 auto;
  position: relative;
  width: 400px;
}

.highlight {
  border-color: red;
  cursor: pointer;
}

.puzzletile {
  background-image: url("../background.jpg");
  border: 5px solid black;
  position: absolute;
}

.highlight, #output {
  color: red;
}

.puzzletile, #output {
  font-size: 40pt;
}

html代码

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>CSE 154 Fifteen Puzzle</title>
  <!-- your files that you will write -->
  <link href="css/fifteen.css" rel="external nofollow" type="text/css" rel="stylesheet"/>
  <script src="js/fifteen.js" type="text/javascript"></script>

</head>
<body>
<h1>Fifteen Puzzle</h1>

<p>
  The goal of the fifteen puzzle is to un-jumble its fifteen squares
  by repeatedly making moves that slide squares into the empty space.
  How quickly can you solve it?
</p>

<div id="puzzlearea">
  <!--
    this area holds the actual fifteen puzzle pieces
    add to it as you need to
  -->
</div>

<p id="controls">
  <button id="shufflebutton">Shuffle</button>
</p>

<div id="output"></div>

<p>
  American puzzle author and mathematician Sam Loyd is often falsely
  credited with creating the puzzle; indeed, Loyd claimed from 1891
  until his death in 1911 that he invented it.
  The puzzle was actually created around 1874 by Noyes Palmer Chapman,
  a postmaster in Canastota, New York.
</p>
</body>
</html>

JavaScript代码

(function () {
  "use strict";

  let NUM = 4; //拼图的行列数 the number of rows/cols in the puzzle
  let spaceRow = 3; // 空白图块所在行
  let spaceColumn = 3; // 空白图块所在列
  let WIDTH = 100; // the pixel width/height of each tile

  // gets everything set when the window has loaded
  window.onload = function () {
   setSize();
   document.getElementById("select").onchange = changeSize;
   document.getElementById("shufflebutton").onclick = shuffle;
   createSquares();

  };

  // add a drop-down list to select difficulty level
  // 设置下拉列表 默认选中 option4
  function setSize() {
   var select = document.createElement("select");
   select.id = "select";
   for (var i = 3; i < 7; i++) {
     var option = document.createElement("option");
     option.innerHTML = i + " * " + i;
     option.value = i;
     option.id = "option" + i;
     select.appendChild(option);
   }
   document.getElementById("controls").appendChild(select);
   document.getElementById("option4").selected = "selected";
  }


  function changeSize() {
   NUM = this.value;
   spaceRow = this.value - 1;
   spaceColumn = this.value - 1;
   WIDTH = parseInt(400 / this.value);
   var puzzlearea = document.getElementById("puzzlearea");
   while (puzzlearea.contains(document.querySelector(".puzzletile"))) {
     puzzlearea.removeChild(document.querySelector(".puzzletile"));
   }
   createSquares();
  }

  // creates 15 puzzle tiles and sets them to their initial position
  function createSquares() {
   for (var i = 1; i < NUM * NUM; i++) {
     var div = document.createElement("div");
     div.className = "puzzletile";
     div.innerHTML = i;
     var row = Math.floor((i - 1) / NUM);
     var column = (i - 1) % NUM;
     var x = column * -1 * WIDTH + "px";
     var y = row * -1 * WIDTH + "px";

     // 减去边框的宽度 并且宽高相等
     div.style.height = WIDTH - 10 + "px";
     div.style.width = div.style.height;
     // 设置background 的 position
     div.style.backgroundPosition = x + " " + y;
     // 为每个拼图添加ID
     div.id = "square_" + row + "_" + column;
     // 设置水平和垂直方向的偏移量
     div.style.top = row * WIDTH + "px";
     div.style.left = column * WIDTH + "px";
     setEvents(div);
     document.getElementById("puzzlearea").appendChild(div);
   }
  }

  // shuffles puzzle tiles for 1000 times
  function shuffle() {
   // 实现Shuffle算法
   for (let j = 0; j < 1000; j++) {
     let neigbors = [];
     // 将所有的拼图 存储到 allPuzzles中
     let allPuzzles = document.getElementsByClassName("puzzletile");
     // 将与空白图块相邻的拼图 存储到数组neigbors中
     for (let i = 0; i < allPuzzles.length; i++) {
      // 判断拼图是否可以移动
      if (moveable(allPuzzles[i]))
        neigbors.push(allPuzzles[i]);
      }
     // 得到一个随机的索引
     let ranNum = getRandomIntInclusive(0, neigbors.length - 1);
     // 获取需要移动的拼图移动之前的偏移量
     let tempTop = neigbors[ranNum].style.top;
     let tempLeft = neigbors[ranNum].style.left;
     // 将拼图移动到空白图块处
     neigbors[ranNum].style.top = spaceRow * WIDTH + "px";
     neigbors[ranNum].style.left = spaceColumn * WIDTH + "px";
     neigbors[ranNum].id = "square_" + spaceRow + "_" + spaceColumn;
     // 更改空白图块的位置
     spaceRow = parseInt(tempTop) / WIDTH;
     spaceColumn = parseInt(tempLeft) / WIDTH;
   }


  }

  // 获取指定区间的随机数
  function getRandomIntInclusive(min, max) {
   min = Math.ceil(min);
   max = Math.floor(max);
   return Math.floor(Math.random() * (max - min + 1)) + min;
  }

  // sets up events for all puzzle tiles
  function setEvents(div) {
   div.onmouseover = function () {
     if (moveable(this)) {
      this.classList.add("highlight"); // when mouse over, adds class "highlight"
     }
   };
   div.onmouseout = function () {
     // when mouse out, removes class "highlight"
     if (moveable(this)) {
      this.classList.remove("highlight"); // when mouse out, remove class "highlight"
     }
   };
   div.onclick = helper;
  }

  // a helper function for function "makeAMove"
  // displays "congratulations" if the player wins
  function helper() {
   if (moveable(this)) {
     makeAMove(this);
     if (win()) {
      document.getElementById("output").innerHTML = "Congratulations! You win!";
     } else {
      document.getElementById("output").innerHTML = "";
     }
   }
  }

  // make one move for the given tile
  function makeAMove(div) {

   div.id = "square_" + spaceRow + "_" + spaceColumn;
   var divRow = parseInt(div.style.top) / WIDTH;
   var divColumn = parseInt(div.style.left) / WIDTH;

   div.style.top = spaceRow * WIDTH + "px";
   div.style.left = spaceColumn * WIDTH + "px";
   spaceRow = divRow;
   spaceColumn = divColumn;

  }

  // return true if the given tile is moveable
  function moveable(div) {

   var divRow = parseInt(div.style.top) / WIDTH;
   var divColumn = parseInt(div.style.left) / WIDTH;
   if (spaceRow == divRow) {
     return Math.abs(spaceColumn - divColumn) == 1;
   }
   else if (spaceColumn == divColumn) {
     return Math.abs(spaceRow - divRow) == 1;
   }
   else {
     return false;
   }
  }

  // return true if all tiles are at their original positions
  function win() {
   var tiles = document.querySelectorAll(".puzzletile");
   for (var i = 0; i < tiles.length; i++) {
     var row = Math.floor(i / NUM);
     var column = i % NUM;
     if (tiles[i].id != "square_" + row + "_" + column) {
      console.log(tiles[i].id);
      return false;
     }
   }
   return true;
  }
})();

最后的效果

基于JavaScript实现十五拼图代码实例

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

Javascript 相关文章推荐
javascript对下拉列表框(select)的操作实例讲解
Nov 29 Javascript
用js控制组织结构图可以任意拖拽到指定位置
Jan 17 Javascript
node-webkit打包成exe文件被360误报木马的解决方法
Mar 11 Javascript
jQuery原型属性和原型方法详解
Jul 07 Javascript
javascript中$(function() {});写与不写有哪些区别
Aug 10 Javascript
HTML的select控件美化
Mar 27 Javascript
Angularjs使用过滤器完成排序功能
Sep 20 Javascript
vue实现多级菜单效果
Oct 19 Javascript
jQuery轮播图功能制作方法详解
Dec 03 jQuery
Js图片点击切换轮播实现代码
Jul 27 Javascript
利用js实现简易红绿灯
Oct 15 Javascript
浅谈es6中的元编程
Dec 01 Javascript
小程序自定义导航栏兼容适配所有机型(附完整案例)
Apr 26 #Javascript
vue 使用 vue-pdf 实现pdf在线预览的示例代码
Apr 26 #Javascript
javascript设计模式 ? 访问者模式原理与用法实例分析
Apr 26 #Javascript
详解关于Vue单元测试的几个坑
Apr 26 #Javascript
es6函数之箭头函数用法实例详解
Apr 25 #Javascript
es6数组之扩展运算符操作实例分析
Apr 25 #Javascript
es6函数之尾调用优化实例分析
Apr 25 #Javascript
You might like
短波的认识
2021/03/01 无线电
PHP中的加密功能
2006/10/09 PHP
第4章 数据处理-php数组的处理-郑阿奇
2011/07/04 PHP
php使用curl抓取qq空间的访客信息示例
2014/02/28 PHP
PHP编译configure时常见错误的总结
2017/08/17 PHP
关于Yii2框架跑脚本时内存泄漏问题的分析与解决
2019/12/01 PHP
jquery 按钮状态效果 正常、移上、按下
2013/08/12 Javascript
javascript跨域方法、原理以及出现问题解决方法(详解)
2015/08/06 Javascript
jQuery焦点图插件SaySlide
2015/12/21 Javascript
jquery if条件语句的写法
2016/05/19 Javascript
全面解析Javascript无限添加QQ好友原理
2016/06/15 Javascript
浅析Javascript的自动分号插入(ASI)机制
2016/09/29 Javascript
Javascript 实现简单计算器实例代码
2016/10/23 Javascript
微信小程序滚动Tab实现左右可滑动切换
2017/08/17 Javascript
基于vue.js的分页插件详解
2017/11/27 Javascript
nodejs中Express与Koa2对比分析
2018/02/06 NodeJs
详解NodeJS Https HSM双向认证实现
2019/03/12 NodeJs
小程序使用watch监听数据变化的方法详解
2019/09/20 Javascript
JavaScript 自定义html元素鼠标右键菜单功能
2019/12/02 Javascript
解决基于 keep-alive 的后台多级路由缓存问题
2020/12/23 Javascript
python del()函数用法
2013/03/24 Python
跟老齐学Python之有容乃大的list(2)
2014/09/15 Python
实践Python的爬虫框架Scrapy来抓取豆瓣电影TOP250
2016/01/20 Python
python日志记录模块实例及改进
2017/02/12 Python
使用Django Form解决表单数据无法动态刷新的两种方法
2017/07/14 Python
python GUI实例学习
2017/11/21 Python
python pandas中对Series数据进行轴向连接的实例
2018/06/08 Python
Python实现朴素贝叶斯分类器的方法详解
2018/07/04 Python
pandas.cut具体使用总结
2019/06/24 Python
html5使用canvas画空心圆与实心圆
2014/12/15 HTML / CSS
机电专业个人求职信范文
2013/12/30 职场文书
活动总结新闻稿
2014/08/30 职场文书
群众路线自我剖析及整改措施
2014/11/04 职场文书
2014年语文教研组工作总结
2014/12/06 职场文书
乡镇一岗双责责任书
2015/01/29 职场文书
一文教你快速生成MySQL数据库关系图
2022/06/28 Redis