Javascript 井字游戏的对象
Javascript Object for Tic Tac Toe game
Javascript 主题完全是新手。我正在尝试编写 Tic Tac Toe 游戏的代码,同时使用 JS 的对象来保存代码 space。我想我可能会创建一个 JS 对象,它将 HTML 代码中定义的所有 9 个字段与 ids 'one' 到 'nine' 作为值,然后还有一个自定义方法可用于交换值的文本内容如下:
var fields = {
one: document.querySelector('#one'),
two: document.querySelector('#two'),
three: document.querySelector('#three'),
four: document.querySelector('#four'),
five: document.querySelector('#five'),
six: document.querySelector('#six'),
seven: document.querySelector('#seven'),
eight: document.querySelector('#eight'),
nine: document.querySelector('#nine'),
swap: function(element) {
if (this.element.textContent === "") {
this.element.textContent = "X";
} else if (this.element.textContent === "X") {
this.element.textContent = "O";
} else {
this.element.textContent = "";
}
}
}
然后,我想我会像这样添加一堆 addEventListeners:
fields['one'].addEventListener('click', fields.swap(fields['one']));
问题是,我可能完全按照它在 Python 中运行的方式对待这个概念,而且我可能搞砸了这里的语法。谁能给我一些关于我在哪里出错的想法?
上面复制的代码暂时不起作用。
它使用的 HTML 如下(我在这里省略了格式以节省 space):
<body>
<div class="container">
<table id="gameboard">
<tr class="row">
<td id="one" class="gameField">X</td>
<td id="two" class="gameField">X</td>
<td id="three" class="gameField">X</td>
</tr>
<tr class="row">
<td id="four" class="gameField">X</td>
<td id="five" class="gameField">X</td>
<td id="six" class="gameField">X</td>
</tr>
<tr class="row">
<td id="seven" class="gameField">X</td>
<td id="eight" class="gameField">X</td>
<td id="nine" class="gameField">X</td>
</tr>
</table>
</div>
将您的 swap 函数从您的对象中分离出来,然后一起摆脱该对象。将 class 添加到您希望添加 EventListener 的所有 HTMLElements,然后使用以下查询它们:
<div id="one" class="your-class"></div>
<div id="two" class="your-class"></div>
function swap(element) {
if (element.textContent === ""){
element.textContent = "X";
}else if (element.textContent === "X") {
element.textContent = "O";
}else {
element.textContent = "";
}
}
document.querySelectorAll('.your-class').forEach(function (element) {
element.addEventListener('click', swap(element));
});
真有趣,我已经用 Jeremy Dejno 的一些代码解决了这个问题,但不得不对其进行调整。考虑到我在第一个 post 中编辑的 HTML 代码 post,以下是对我有用的代码:
function swap(){
if (this.textContent === ""){
this.textContent = "X";
}else if (this.textContent === "X") {
this.textContent = "O";
}else {
this.textContent = "";
}
}
document.querySelectorAll('.gameField').forEach(function(element){
element.addEventListener('click',swap);
})
因为这对我来说是一个全新的事物(我来自 Python 背景),有人可以告诉我我是否理解正确:在使用 .gameField [= 对每个项目调用 .addEventListener 之后17=],在它们中的任何一个上的每个单击事件上都会调用交换函数,并且可以在没有任何参数的情况下调用交换函数,因为 THIS 关键字使它尝试修改调用它的任何对象的 .textContent 属性 ?
井字游戏!
只是添加样式,抱歉跑题了,也许有点意思。
//
const board = [
[1, 2, 3],
[1, 2, 3],
[1, 2, 3]
];
new Vue({
el: '#app',
data() {
return {
plays: 0,
player: true,
winner: '',
board: JSON.parse(JSON.stringify(board))
}
},
methods: {
resetGame() {
this.plays = 0
this.winner = ''
this.board = JSON.parse(JSON.stringify(board))
},
isBool(value) {
return typeof(value) === typeof(true)
},
play(x, y) {
if (!this.isBool(this.board[x][y]) && this.winner === '') {
this.board[x][y] = this.player
this.plays++
this.checkWin(this.player)
this.player = !this.player
}
},
slot(x, y) {
return {
'fa-circle-o': this.isBool(this.board[x][y]) && this.board[x][y] === true,
'fa-times': this.isBool(this.board[x][y]) && this.board[x][y] === false
}
},
endGame(player) {
this.winner = player
},
checkWin(player) {
// check horizontal win
for (var i = 0; i <= 2; i++) {
if (this.board[i][0] === player &&
this.board[i][1] === player &&
this.board[i][2] === player) {
this.endGame(player);
}
}
// check vertical win
for (var i = 0; i <= 2; i++) {
if (this.board[0][i] === player &&
this.board[1][i] === player &&
this.board[2][i] === player) {
this.endGame(player);
}
}
// check diagonal win
if ((this.board[0][0] === player &&
this.board[1][1] === player &&
this.board[2][2] === player) ||
this.board[0][2] === player &&
this.board[1][1] === player &&
this.board[2][0] === player) {
this.endGame(player);
}
if (this.plays === 9) {
this.endGame(-1);
}
}
}
});
<link href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.min.css" rel="stylesheet">
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
<style>
table tr td {
min-width: 20px;
min-height: 20px;
padding: 3px;
text-align: center;
}
</style>
<div id="app">
<h3>Tic-Tac-Vue</h3>
<p>It's player <i :class="['fa', {'fa-circle-o': player, 'fa-times': !player}]"></i>'s go!</p>
<table border="1">
<tr>
<td @click="play(0,0)"><i :class="['fa', slot(0,0)]"></i></td>
<td @click="play(0,1)"><i :class="['fa', slot(0,1)]"></i></td>
<td @click="play(0,2)"><i :class="['fa', slot(0,2)]"></i></td>
</tr>
<tr>
<td @click="play(1,0)"><i :class="['fa', slot(1,0)]"></i></td>
<td @click="play(1,1)"><i :class="['fa', slot(1,1)]"></i></td>
<td @click="play(1,2)"><i :class="['fa', slot(1,2)]"></i></td>
</tr>
<tr>
<td @click="play(2,0)"><i :class="['fa', slot(2,0)]"></i></td>
<td @click="play(2,1)"><i :class="['fa', slot(2,1)]"></i></td>
<td @click="play(2,2)"><i :class="['fa', slot(2,2)]"></i></td>
</tr>
</table>
<p v-if="winner === true || winner === false">Player <i :class="['fa', {'fa-circle-o': !player, 'fa-times': player}]"></i> is the winner!!</p>
<p v-if="winner === -1">Game Over, Draw!!</p>
<button @click="resetGame()">Reset Game</button>
</div>
看到它在这里工作:https://jsfiddle.net/7ktbphaf/
Javascript 主题完全是新手。我正在尝试编写 Tic Tac Toe 游戏的代码,同时使用 JS 的对象来保存代码 space。我想我可能会创建一个 JS 对象,它将 HTML 代码中定义的所有 9 个字段与 ids 'one' 到 'nine' 作为值,然后还有一个自定义方法可用于交换值的文本内容如下:
var fields = {
one: document.querySelector('#one'),
two: document.querySelector('#two'),
three: document.querySelector('#three'),
four: document.querySelector('#four'),
five: document.querySelector('#five'),
six: document.querySelector('#six'),
seven: document.querySelector('#seven'),
eight: document.querySelector('#eight'),
nine: document.querySelector('#nine'),
swap: function(element) {
if (this.element.textContent === "") {
this.element.textContent = "X";
} else if (this.element.textContent === "X") {
this.element.textContent = "O";
} else {
this.element.textContent = "";
}
}
}
然后,我想我会像这样添加一堆 addEventListeners:
fields['one'].addEventListener('click', fields.swap(fields['one']));
问题是,我可能完全按照它在 Python 中运行的方式对待这个概念,而且我可能搞砸了这里的语法。谁能给我一些关于我在哪里出错的想法?
上面复制的代码暂时不起作用。
它使用的HTML 如下(我在这里省略了格式以节省 space):
<body>
<div class="container">
<table id="gameboard">
<tr class="row">
<td id="one" class="gameField">X</td>
<td id="two" class="gameField">X</td>
<td id="three" class="gameField">X</td>
</tr>
<tr class="row">
<td id="four" class="gameField">X</td>
<td id="five" class="gameField">X</td>
<td id="six" class="gameField">X</td>
</tr>
<tr class="row">
<td id="seven" class="gameField">X</td>
<td id="eight" class="gameField">X</td>
<td id="nine" class="gameField">X</td>
</tr>
</table>
</div>
将您的 swap 函数从您的对象中分离出来,然后一起摆脱该对象。将 class 添加到您希望添加 EventListener 的所有 HTMLElements,然后使用以下查询它们:
<div id="one" class="your-class"></div>
<div id="two" class="your-class"></div>
function swap(element) {
if (element.textContent === ""){
element.textContent = "X";
}else if (element.textContent === "X") {
element.textContent = "O";
}else {
element.textContent = "";
}
}
document.querySelectorAll('.your-class').forEach(function (element) {
element.addEventListener('click', swap(element));
});
真有趣,我已经用 Jeremy Dejno 的一些代码解决了这个问题,但不得不对其进行调整。考虑到我在第一个 post 中编辑的 HTML 代码 post,以下是对我有用的代码:
function swap(){
if (this.textContent === ""){
this.textContent = "X";
}else if (this.textContent === "X") {
this.textContent = "O";
}else {
this.textContent = "";
}
}
document.querySelectorAll('.gameField').forEach(function(element){
element.addEventListener('click',swap);
})
因为这对我来说是一个全新的事物(我来自 Python 背景),有人可以告诉我我是否理解正确:在使用 .gameField [= 对每个项目调用 .addEventListener 之后17=],在它们中的任何一个上的每个单击事件上都会调用交换函数,并且可以在没有任何参数的情况下调用交换函数,因为 THIS 关键字使它尝试修改调用它的任何对象的 .textContent 属性 ?
井字游戏!
只是添加样式,抱歉跑题了,也许有点意思。
//
const board = [
[1, 2, 3],
[1, 2, 3],
[1, 2, 3]
];
new Vue({
el: '#app',
data() {
return {
plays: 0,
player: true,
winner: '',
board: JSON.parse(JSON.stringify(board))
}
},
methods: {
resetGame() {
this.plays = 0
this.winner = ''
this.board = JSON.parse(JSON.stringify(board))
},
isBool(value) {
return typeof(value) === typeof(true)
},
play(x, y) {
if (!this.isBool(this.board[x][y]) && this.winner === '') {
this.board[x][y] = this.player
this.plays++
this.checkWin(this.player)
this.player = !this.player
}
},
slot(x, y) {
return {
'fa-circle-o': this.isBool(this.board[x][y]) && this.board[x][y] === true,
'fa-times': this.isBool(this.board[x][y]) && this.board[x][y] === false
}
},
endGame(player) {
this.winner = player
},
checkWin(player) {
// check horizontal win
for (var i = 0; i <= 2; i++) {
if (this.board[i][0] === player &&
this.board[i][1] === player &&
this.board[i][2] === player) {
this.endGame(player);
}
}
// check vertical win
for (var i = 0; i <= 2; i++) {
if (this.board[0][i] === player &&
this.board[1][i] === player &&
this.board[2][i] === player) {
this.endGame(player);
}
}
// check diagonal win
if ((this.board[0][0] === player &&
this.board[1][1] === player &&
this.board[2][2] === player) ||
this.board[0][2] === player &&
this.board[1][1] === player &&
this.board[2][0] === player) {
this.endGame(player);
}
if (this.plays === 9) {
this.endGame(-1);
}
}
}
});
<link href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.min.css" rel="stylesheet">
<script src="https://cdn.jsdelivr.net/npm/vue/dist/vue.js"></script>
<style>
table tr td {
min-width: 20px;
min-height: 20px;
padding: 3px;
text-align: center;
}
</style>
<div id="app">
<h3>Tic-Tac-Vue</h3>
<p>It's player <i :class="['fa', {'fa-circle-o': player, 'fa-times': !player}]"></i>'s go!</p>
<table border="1">
<tr>
<td @click="play(0,0)"><i :class="['fa', slot(0,0)]"></i></td>
<td @click="play(0,1)"><i :class="['fa', slot(0,1)]"></i></td>
<td @click="play(0,2)"><i :class="['fa', slot(0,2)]"></i></td>
</tr>
<tr>
<td @click="play(1,0)"><i :class="['fa', slot(1,0)]"></i></td>
<td @click="play(1,1)"><i :class="['fa', slot(1,1)]"></i></td>
<td @click="play(1,2)"><i :class="['fa', slot(1,2)]"></i></td>
</tr>
<tr>
<td @click="play(2,0)"><i :class="['fa', slot(2,0)]"></i></td>
<td @click="play(2,1)"><i :class="['fa', slot(2,1)]"></i></td>
<td @click="play(2,2)"><i :class="['fa', slot(2,2)]"></i></td>
</tr>
</table>
<p v-if="winner === true || winner === false">Player <i :class="['fa', {'fa-circle-o': !player, 'fa-times': player}]"></i> is the winner!!</p>
<p v-if="winner === -1">Game Over, Draw!!</p>
<button @click="resetGame()">Reset Game</button>
</div>
看到它在这里工作:https://jsfiddle.net/7ktbphaf/