整合营销服务商

电脑端+手机端+微信端=数据同步管理

免费咨询热线:

Javascript开发小游戏-五子棋

小朋友在学校里,跟同学玩过五子棋,回来想跟我也较量一下,但是家里没有五子棋,准备用纸做一个,做了半天,做出来的成品,不忍直视,无意看到桌上的平板,想到可以用js开发一个五子棋游戏,免去安装

理清思路

  • 需要一个棋盘,n行n列
  • 两种棋子,白棋黑棋
  • 白棋黑棋交替下子
  • 横线()、竖线(|)、左斜线(/)、右斜线(\),四条线上任意一条,五个棋子连成一条线就赢

思路清楚后,直接撸代码

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>五子棋</title>
    <script src="http://libs.baidu.com/jquery/2.1.4/jquery.min.js"></script>
    <style>
        .chessboard {
            border: black solid 2px;
            width: auto;
            display: inline-block;
            margin-left: 100px;
            padding: 20px;
            background: burlywood;
        }

        .chessboard_row {
            display: flex;
        }

        .grid-area {
            width: 30px;
            height: 30px;
            position: relative;
        }

        .grid-area:after {
            content: '';
            position: absolute;
            top: 18px;
            left: 18px;
            width: 22px;
            height: 22px;
            border: 1px dashed black;
            display: none;
        }

        .grid-area:hover:after {
            display: inline-block;
        }

        .grid-area[have-chess] {
            cursor: no-drop;
        }

        .grid {
            border-right: black solid 1px;
            border-bottom: black solid 1px;
        }

        .grid-row-first {
            border-right: black solid 1px;
            border-top: black solid 1px;
            border-bottom: black solid 1px;

        }

        .grid-first-row-col {
            border: black solid 1px;

        }

        .grid-first-col {
            border-right: black solid 1px;
            border-left: black solid 1px;
            border-bottom: black solid 1px;
        }

        .chessman {
            width: 22px;
            height: 22px;
            border-radius: 50%;
            position: absolute;
            z-index: 10;
            top: 19px;
            left: 19px;
        }

        .chessman.black {
            background: black;
        }

        .chessman.white {
            background: white;
        }

        .op-area {
            display: inline-block;
            margin-left: 50px;
        }
    </style>
</head>
<body>
<div class="chessboard">
</div>
<div class="op-area">
    <ul>
        <li>
            <button id="restart-btn">重新开始</button>
        </li>
    </ul>

</div>
<script>
    let fir = {
        chessmanType: {
            black: 0,
            white: 1
        },
        lineType: {
            horizontal: 1,//横线
            vertical: 2,//竖线
            leftSlash: 3,//左斜线
            rightSlash: 4,//右斜线
        },
        direction: {
            positive: 1,//正向
            negative: -1//反向
        },
        black_array: [],//已下黑子数组
        white_array: [],//已下白子数组
        currentChessmanType: null,//当前落子方
        init: () => {
            fir.drawChessboard();
            fir.bindEvent();
            //黑棋先下
            fir.currentChessmanType = fir.chessmanType.black
        },
        /**
         * 画棋盘,默认18行,18列
         * */
        drawChessboard: (col) => {//画棋盘
            col = col || 18;//列数,行数默认等于列数
            let chessboard_html = [];
            for (let i = 0; i < col; i++) {
                chessboard_html.push('<div class="chessboard_row">');
                for (let j = 0; j < col; j++) {
                    if (i === 0) {
                        if (j === 0) {
                            chessboard_html.push('<div data-r="' + i + '" data-c="' + j + '" class="grid-area grid-first-row-col"></div>');
                        } else {
                            chessboard_html.push('<div data-r="' + i + '" data-c="' + j + '" class="grid-area grid-row-first"></div>');
                        }
                    } else {
                        if (j === 0) {
                            chessboard_html.push('<div data-r="' + i + '" data-c="' + j + '" class="grid-area grid-first-col"></div>');
                        } else {
                            chessboard_html.push('<div data-r="' + i + '" data-c="' + j + '" class="grid-area grid"></div>');
                        }
                    }
                }
                chessboard_html.push('</div>')
            }
            $('.chessboard').append(chessboard_html.join(""));
        },
        bindEvent: () => {
            $('.grid-area').bind('click', function () {
                fir.chess(this);
            });
            $('#restart-btn').bind('click', () => {
                fir.reset();
            });
        },
        victoryCallback: (chessmanType) => {
            let msg = chessmanType === fir.chessmanType.black ? '黑棋胜利' : '白棋胜利';
            alert(msg);
            fir.reset();
        },
        chess: (obj) => {
            let $obj = $(obj);
            if ($obj.attr('have-chess')) {
                alert('不能下在此处');
                return
            }
            let pos = {r: $obj.attr('data-r'), c: $obj.attr('data-c')};
            if (fir.currentChessmanType === fir.chessmanType.black) {
                $obj.append('<div class="chessman black"></div>');
                fir.black_array.push(pos);
            } else {
                $obj.append('<div class="chessman white"></div>');
                fir.white_array.push(pos);
            }
            $obj.attr('have-chess', fir.currentChessmanType);
            fir.victory(fir.currentChessmanType, pos, fir.victoryCallback);
            fir.swap();
        },
        swap: () => {
            if (fir.currentChessmanType === fir.chessmanType.black) {
                fir.currentChessmanType = fir.chessmanType.white;
            } else {
                fir.currentChessmanType = fir.chessmanType.black;
            }
        },
        findInArray: (arr, obj) => {
            for (let ele of arr) {
                if (ele.c === obj.c && ele.r === obj.r) {
                    return ele;
                }
            }
            return null;
        },
        getNearPos: (pos, line, direction) => {
            let n_r = parseInt(pos.r);//行
            let n_c = parseInt(pos.c);//列
            if (line === fir.lineType.horizontal) {
                if (direction === fir.direction.negative) {
                    return {r: n_r + '', c: (n_c - 1) + ''};
                } else if (direction === fir.direction.positive) {
                    return {r: n_r + '', c: (n_c + 1) + ''};
                }
            } else if (line === fir.lineType.vertical) {
                if (direction === fir.direction.negative) {
                    return {r: (n_r + 1) + '', c: n_c + ''};
                } else if (direction === fir.direction.positive) {
                    return {r: (n_r - 1) + '', c: n_c + ''};
                }
            } else if (line === fir.lineType.leftSlash) {
                if (direction === fir.direction.negative) {
                    return {r: (n_r + 1) + '', c: (n_c - 1) + ''};
                } else if (direction === fir.direction.positive) {
                    return {r: (n_r - 1) + '', c: (n_c + 1) + ''};
                }
            } else if (line === fir.lineType.rightSlash) {
                if (direction === fir.direction.negative) {
                    return {r: (n_r + 1) + '', c: (n_c + 1) + ''};
                } else if (direction === fir.direction.positive) {
                    return {r: (n_r - 1) + '', c: (n_c - 1) + ''};
                }
            }
        },
        /***
         * 获取落子后,连续棋子的个数
         * 递归查询
         */
        coiledSize: (arr, pos, line, direction, size) => {
            let nearPos = fir.getNearPos(pos, line, direction);
            let obj = fir.findInArray(arr, nearPos);
            if (obj) {
                size = size + 1;
                size = fir.coiledSize(arr, obj, line, direction, size);
            }
            return size;
        },
        victory: (chessmanType, pos, callback) => {
            let arr;
            if (chessmanType === fir.chessmanType.black) {
                arr = fir.black_array;
            } else {
                arr = fir.white_array;
            }
            for (let lineTypeKey in fir.lineType) {
                let type = fir.lineType[lineTypeKey];
                let size_1 = fir.coiledSize(arr, pos, type, fir.direction.negative, 0);
                if (size_1 >= 4) {
                    callback(chessmanType);
                    return;
                }
                let size_2 = fir.coiledSize(arr, pos, type, fir.direction.positive, 0);
                if (size_2 >= 4) {
                    callback(chessmanType);
                    return;
                }
                if (size_1 + size_2 >= 4) {
                    callback(chessmanType);
                    return;
                }
            }
        },
        reset: () => {
            fir.white_array = [];
            fir.black_array = [];
            $('.chessman').remove();
            $('.grid-area').removeAttr('have-chess');
        }
    }
    fir.init();
</script>
</body>
</html>

在浏览器上运行一下,效果还不错吧

有兴趣的可以增加一个后台服务,实现在线实时对弈

有想看其他的小游戏,可以打在评论区[呲牙]

为 开发过React/React Native 的工程师,在刚开始接触Flutter 开发的时候,一定会遇到这种情况,对于某个功能你能很熟练使用特定Javascript语法去完成,但是对于Flutter 开发,对应的Dart的语法又是什么?往往要再翻开Dart文档去寻找对应的语法。在此分享15 个 JavaScript 代码示例及其 Dart 对应代码。

1. JSON.stringify 和 JsonEncoder().convert

在 JavaScript 中,如果要将对象转换为 JSON 字符串,可以使用:

  JSON.stringify(yourObject)

在 Dart 中,只需导入'dart:convert'即可使用:

  import 'dart:convert';
  
  JsonEncoder().convert(yourObject)

2. JSON.parse和JsonDecoder().convert

在 JavaScript 中将 JSON 转换为对象,会使用以下代码:

  JSON.parse(yourJson)

在 Dart 中,只需导入'dart:convert'即可使用:

  import 'dart:convert';
  
  JsonDecoder().convert(yourJson)

3. array.push和list.add

在 JavaScript 中,要添加'hello'到数组中,可以使用

  array.push('hello')

在 Dart 中,这样使用,

  list.add('hello')

4. array.splice和list.sublist

在 JavaScript 中,数组删除第一个元素(索引值为0)

  array.splice(0, 1)

在Dart中, 返回索引范围(1 和 3)内的新列表

  list.sublist(1, 3)

5. array.splice和list.removeAt

array.splice与#4点一样

在Dart中, 删除索引值为itemIndex的值

  list.removeAt(itemIndex)

6. array.length > 0和list.isNotEmpty

检查数组是否为空

  array.length > 0

Dart里,是这样

  list.isNotEmpty

7. array.length === 0和list.isEmpty

检查数组是否为空

  array.length === 0

Dart里,是这样

  list.isEmpty

8. parseInt和int.parse

在 JavaScript 中将字符串转换为整数,可以使用

  parseInt('123')

在Dart里,是这样

  int.parse('123')

9. parseFloat 和 double.parse

双精度浮点数的使用如下:

  parseFloat('1.23')

在Dart里,是这样

  double.parse('1.23')

10. array.some 和 list.any

在 JavaScript 中,array.some()方法测试数组中是不是至少有1个元素通过了被提供的函数测试。它返回的是一个Boolean类型的。
例如,如果想查看数组[1, 2, 3, 4, 5, 6, 7]是否有任何大于 5 的数字:

  var some = array.some(x=>x > 5)

在Dart,是这样的,

  array.any((x)=>x > 5);

11. array.findIndex和list.indexWhere

Javascript的array.findIndex()方法返回数组中满足提供的测试函数的第一个元素的索引。若没有找到对应元素则返回-1。
Dart用的是list.indexWhere,只是用法不一样

var notes = ['do', 're', 'mi', 're'];
// JavaScript
notes.findIndex(x=>x.indexOf("r") > -1) // 1
// Dart
notes.indexWhere((note) => note.startsWith('r')); // 1

「Tip」 在 Dart 中,还可以在函数后面传递一个参数来提供起始索引。如下:

notes.indexWhere((note) => note.startsWith('r'), 2 ); // 3

12. array.indexOf() 和 list.indexOf()

在 JavaScript 和 Dart 中,indexOf是一种用于在数组或列表中查找索引位置的方法。没有则返回-1

var author = ['Edgar Allen Poe', 'JK Rowling', 'Ernest Hemingway'] 
author.indexOf('JK Rowling') // 1

13. toString

在 JavaScript 中,会使用toString()将另一种数据类型的值转换为字符串。它适用于整数、浮点数、布尔值、数组和对象。对于对象的话会得到以下结果:

var x = {id: 1}
console.log(x.toString())
=> '[object Object]'

但是两者会有一定的差别,如下:

 // Dart
 String test = 1.toString() // '1'
 // JavaScript
 var x = 1.toString() // 未捕获的语法错误:无效或意外的标记

14. array.every 和 list.every

every() 方法测试一个数组内的所有元素是否都能通过某个指定函数的测试。它返回一个布尔值。用法与上面array.some 和 list.any相似

15. map, forEach, filter, find等

除了语法上的一些差异之外,上述所有方法都在 JavaScript 和 Dart 之间共享。当map用于test等于的数组时,请参见如下[1, 2, 3, 4, 5]。
Javascript:

  // 其他类似
  test.map(x=>x*2)

Dart:

est.map((x)=>x*2)

如果你还有其他需要补充的?在评论中让我知道哈!

HP文件上传是很常见的,但是当前后端分离后,前端和后端的框架都是按照开发人员自己去定的, 然单独写上传是很麻烦的, 在插件泛滥的今天,原生的表单上传很少用户会去研究, 这里通过亲身经历介绍TP的文件上传类进行结合, 实例方便好用的文件上传操作。

  1. 前端框架datatable,

    html.push('<input id="file-upload" type="file" name="pics" >');

2. 后端框架TP5文件上传类接收

public function upfile(){

$file = $this->request->file('pics')->getInfo();

(这里一定一定要加,不然获取到的是对象,很坑的对象)

$filename = "";

if($file){

if( !file_exists($path) ){

mkdir($path, 0775, true);//如果创建的多级目录,第三个参数设置为true。

}

if ( !file_exists($path) && !mkdir($path, 0775, true)) {

$infos=[];

$infos['code'] =-302;

$infos['errMsg'] ='文件存储位置创建失败';

return json_encode($infos);

}

// 获得文件类型

$file_Extension =strtolower(pathinfo($files['name'])['extension']);

$file_extends = ['bmp', 'jpg', 'jpeg', 'png', 'gif', 'pdf', 'doc', 'xls', 'ppt', 'docx', 'xlsx', 'pptx'];

if (!in_array($file_Extension, $file_extends) ) {

$infos=[];

$infos['code'] =-302;

$infos['errMsg'] ='文件类型不支持';

return json_encode($infos);

}

$paths=$path.'.'.$file_Extension;

$info =move_uploaded_file($files['tmp_name'], $paths);

$info = $file->move(ROOT_PATH . 'public' . DS . 'up');


}

if($info){

$data = array('msg'=>'上传成功','filename'=>$filename);

}else{

$data = array('msg'=>'上传失败','filename'=>‘’);

}

echo json_encode($data);

}

3展现bug原型的时间到了

决的办法就是

$file = $this->request->file('pics')->getInfo();

参考文献

https://blog.csdn.net/hexiaoniao/article/details/85064475

希望能帮到大家