js canvas实现五子棋小游戏


Posted in Javascript onJanuary 22, 2021

本文实例为大家分享了canvas实现五子棋小游戏的具体代码,供大家参考,具体内容如下

效果

js canvas实现五子棋小游戏

思路

  • canvans 绘制棋盘,绘制时候边缘预留棋子位置
  • 监听点击事件绘制落子并记录到字典中
  • 获胜判定,在四个方向上检测是否有足够数量的连贯棋子

js canvas实现五子棋小游戏

代码

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>ym</title>
  <style>
    canvas {
      display: block;
      margin: 0 auto;
      border: 0
    }

    .result {
      text-align: center;
    }
    button{
      display: block;
      margin: 0 auto;
      padding: 4px 20px;
      border:0;
      color: #fff;
      outline: none;
      border-radius: 3px;
      background: #43a6ff
    }
    button:hover{
      font-weight: bold;
      cursor: pointer;
    }
  </style>
</head>
<body>
<canvas id="cv" width="200px" height="200px"></canvas>
<p class="result"></p>
<button onclick="loadPanel(400, 400,30,13)">刷新</button>
<script>

  loadPanel(400, 400,30,13);

  /**
   * 1) 点击落子并切换执子者
   * 2)以当前落子位置为基准,以‘米'字型判定,是否能构成五连及以上
   * @param w 棋盘宽度
   * @param h 棋盘高度
   * @param cs 格子尺寸
   * @param ps 棋子半径
   */
  function loadPanel(w, h, cs, ps) {
    let i, j, k;
    let chks = [[1, 0], [0, 1], [1, 1], [1, -1]];//水平,纵向,斜下,斜上 四个方向
    let successNum = 5;//赢棋标准
    let resultEl = document.querySelector('.result');

    //1)绘制棋盘,边缘应隔开棋子半径的距离
    cs = cs || 16;//默认格子宽高
    ps = ps || 4;//棋子半径
    h = h || w;//高度默认等于宽度

    let el = document.getElementById('cv');
    el.setAttribute('width', w + 'px');
    el.setAttribute('height', h + 'px');
    let context = el.getContext("2d");
    //计算棋盘分割,向下取整
    let splitX = ~~((w - 2 * ps) / cs), splitY = ~~((h - 2 * ps) / cs);

    //初始化落子位置使用字典存储,相较于数组简单且减少内存占用
    let pieces = {};
    //循环划线
    context.translate(ps, ps);
    context.beginPath();
    context.strokeStyle = '#000';
    //垂直线
    for (i = 0; i < splitX + 1; i++) {
      context.moveTo(cs * i, 0);
      context.lineTo(cs * i, splitY * cs);
      context.stroke();
    }
    //水平线
    for (j = 0; j < splitY + 1; j++) {
      context.moveTo(0, cs * j);
      context.lineTo(splitX * cs, cs * j);
      context.stroke();
    }
    context.closePath();

    let user = 0, colors = ['#000', '#fefefe'];
    el.addEventListener('click', function (e) {
      let x = e.offsetX,
        y = e.offsetY,
        //计算落子范围
        rx = ~~((x - ps) / cs) + (((x - ps) % cs <= cs / 2) ? 0 : 1),
        ry = ~~((y - ps) / cs) + (((y - ps) % cs <= cs / 2) ? 0 : 1);
      //绘制棋子
      context.beginPath();
      context.arc(cs * rx, cs * ry, ps, 2 * Math.PI, false);
      context.fillStyle = colors[user];
      context.strokeStyle = '#000';
      user ? user = 0 : user = 1;//切换执子者
      context.fill();
      context.stroke();
      context.closePath();

      //记录棋子位置
      let piece = pieces[rx + '-' + ry] = user;

      //米字型计算结果,以当前落子位置计算是否存在某个方向上具有连续的五个相同棋子
      for (j = 0; j < chks.length; j++) {
        let num = 1, chk = chks[j];
        for (i = 1; i <= 4; i++) {
          if (pieces[(rx + chk[0] * i) + '-' + (ry + chk[1] * i)] == piece) {
            num++
          } else {
            for (i = -1; i >= -4; i--) {
              if (pieces[(rx + chk[0] * i) + '-' + (ry + chk[1] * i)] == piece) {
                num++
              }
            }
            break
          }
        }
        if (num == successNum) {
          resultEl.innerHTML = ['白', '黑'][user] + '方赢';
          break;
        }
      }
    })
  }
</script>
</body>
</html>

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

Javascript 相关文章推荐
JavaScript 动态将数字金额转化为中文大写金额
May 14 Javascript
web 页面分页打印的实现
Jun 22 Javascript
Microsoft Ajax Minifier 压缩javascript的方法
Mar 05 Javascript
js实现收缩菜单效果实例代码
Oct 30 Javascript
js实现瀑布流的一种简单方法实例分享
Nov 04 Javascript
js如何调用qq互联api实现第三方登录
Mar 28 Javascript
AngularJS创建自定义指令的方法详解
Nov 03 Javascript
小程序ios音频播放没声音问题的解决
Jul 11 Javascript
JavaScript使用小插件实现倒计时的方法讲解
Mar 11 Javascript
vue 地区选择器v-distpicker的常用功能
Jul 23 Javascript
axios异步提交表单数据的几种方法
Aug 11 Javascript
国内常用的js类库大全(CDN公共库)
Jun 24 Javascript
Vue 集成 PDF.js 实现 PDF 预览和添加水印的步骤
Jan 22 #Vue.js
element-ui 弹窗组件封装的步骤
Jan 22 #Javascript
动态实现element ui的el-table某列数据不同样式的示例
Jan 22 #Javascript
原生js实现放大镜组件
Jan 22 #Javascript
Vue仿Bibibili首页的问题
Jan 21 #Vue.js
如何在vue 中使用柱状图 并自修改配置
Jan 21 #Vue.js
Vue看了就会的8个小技巧
Jan 21 #Vue.js
You might like
php防注入及开发安全详细解析
2013/08/09 PHP
聊聊 PHP 8 新特性 Attributes
2020/08/19 PHP
JS分页控件 可用于无刷新分页
2013/07/23 Javascript
javascript 数字格式化输出的实现代码
2013/12/10 Javascript
使用js判断TextBox控件值改变然后出发事件
2014/03/07 Javascript
取得元素的左和上偏移量的方法
2014/09/17 Javascript
js简单抽奖代码
2015/01/16 Javascript
JavaScript 定时器 SetTimeout之定时刷新窗口和关闭窗口(代码超简单)
2016/02/26 Javascript
Js删除数组中某一项或几项的几种方法(推荐)
2016/07/27 Javascript
Angular指令封装jQuery日期时间插件datetimepicker实现双向绑定示例
2017/01/22 Javascript
vue2.0获取自定义属性的值
2017/03/28 Javascript
深入理解Vue-cli搭建项目后的目录结构探秘
2017/07/13 Javascript
JavaScript实现移动端页面按手机屏幕分辨率自动缩放的最强代码
2017/08/18 Javascript
React-Native中props具体使用详解
2017/09/04 Javascript
ng-alain表单使用方式详解
2018/07/10 Javascript
微信小程序网络请求封装示例
2018/07/24 Javascript
Layui数据表格之获取表格中所有的数据方法
2018/08/20 Javascript
JavaScript函数式编程(Functional Programming)纯函数用法分析
2019/05/22 Javascript
[06:24]DOTA2亚洲邀请赛小组赛第三日 TOP10精彩集锦
2015/02/01 DOTA
Python命令行参数解析模块optparse使用实例
2015/04/13 Python
DataFrame中去除指定列为空的行方法
2018/04/08 Python
CentOS 7下安装Python3.6 及遇到的问题小结
2018/11/08 Python
Python 一键制作微信好友图片墙的方法
2019/05/16 Python
pytorch 在sequential中使用view来reshape的例子
2019/08/20 Python
python实现录制全屏和选择区域录屏功能
2021/02/05 Python
Python如何使用神经网络进行简单文本分类
2021/02/25 Python
团日活动总结书格式
2014/05/08 职场文书
医院合作协议书
2014/08/19 职场文书
房屋租赁授权委托书范本
2014/09/20 职场文书
教师病假条范文
2015/08/17 职场文书
入党申请书怎么写?
2019/06/11 职场文书
Navicat连接MySQL错误描述分析
2021/06/02 MySQL
RPM包方式安装Oracle21c的方法详解
2021/08/23 Oracle
JVM之方法返回地址详解
2022/02/28 Java/Android
vue+iview实现手机号分段输入框
2022/03/25 Vue.js
WCG2010 星际争霸决赛 Flash vs Goojila 1 星际经典比赛回顾
2022/04/01 星际争霸