完成品
<template>
<div id="app">
<div v-if="playing">
<span>{{ pressed }}</span>{{ word }}
<br>
<br>
miss:{{ miss }}
</div>
<div v-else>Spaceでスタート</div>
</div>
</template>
<script>
export default {
data() {
return {
words: ['apple', 'banana', 'grape'],
word: '',
pressed: '',
miss: 0,
playing: false,
};
},
created() {
addEventListener('keydown', (e) => {
if (e.key !== ' ' || this.playing) {
return;
}
this.playing = true;
this.setWord();
this.keyDown();
});
},
methods: {
setWord() {
this.word = this.words.splice(Math.floor(Math.random() * this.words.length), 1)[0];
},
keyDown() {
addEventListener('keydown', (e) => {
if (e.key !== this.word[0]) {
this.miss++;
return;
}
this.pressed += e.key;
this.word = this.word.slice(1);
if (this.word.length === 0) {
this.pressed = '';
if (this.words.length === 0) {
this.word = 'おしまい';
return;
}
this.setWord();
}
});
},
},
};
</script>
<style>
# app {
font-family: Avenir, Helvetica, Arial, sans-serif;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
text-align: center;
color: #2c3e50;
margin-top: 60px;
}
span {
opacity: 0.5;
}
</style>
配列からランダムな値を取り出す
setWordメソッドを作り、createdで呼び出しています。
その際wordsの中からランダムな値をwordに格納。
<template>
<div id="app">
<div>
{{ word }}
</div>
</div>
</template>
<script>
export default {
data() {
return {
words: ['apple', 'banana', 'grape'],
word: '',
}
},
created() {
this.setWord();
},
methods: {
setWord() {
this.word = this.words[Math.floor(Math.random() * this.words.length)];
}
}
}
</script>
<style>
# app {
font-family: Avenir, Helvetica, Arial, sans-serif;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
text-align: center;
color: #2c3e50;
margin-top: 60px;
}
タイピングの処理
keyDownメソッドを作り、createdで呼び出しています。
入力されたKeyと現在のwordの頭文字が一致しない場合はmissが加算。
pressedには入力されたkeyを格納。
wordにはkeyが押されるごとに頭文字を削除し再代入します。
これで入力した文字と未入力の文字を仕分けしています。
wordが全て無くなったらpressedをリセットし、新しいwordを表示させます。
<script>
export default {
data() {
return {
words: ['apple', 'banana', 'grape'],
word: '',
pressed: '',
miss: 0,
}
},
created() {
this.setWord();
this.keyDown()
},
methods: {
setWord() {
this.word = this.words[Math.floor(Math.random() * this.words.length)];
},
keyDown() {
addEventListener('keydown', (e) => {
if (e.key !== this.word[0]) {
this.miss++;
return;
}
this.pressed += e.key;
this.word = this.word.slice(1);
if (this.word.length === 0) {
this.pressed = '';
this.setWord();
}
});
},
}
}
</script>
Viewでpressedとword連結させます。
入力されていることが分かりやすいようにpressedをspanタグで囲みスタイルをつけます。
あとmissのカウントをここで表示させます。
<template>
<div id="app">
<div>
<span>{{ pressed }}</span>{{ word }}
<br>
<br>
miss:{{ miss }}
</div>
</div>
</template>
<style>
span {
opacity: 0.5;
}
</style>
単語の重複を防ぐ
現時点だと単語が重複して無限に遊べるので一度出た単語は消してしまいます。
<script>
setWord() {
this.word = this.words.splice(Math.floor(Math.random() * this.words.length), 1)[0];
},
</script>
ゲームの開始と終了の処理
dataにplayingを追加しSpaceキーを押すことでfalseからtrueにします。
<template>
<div id="app">
<div v-if="playing">
<span>{{ pressed }}</span>{{ word }}
<br>
<br>
miss:{{ miss }}
</div>
<div v-else>Spaceでスタート</div>
</div>
</template>
<script>
export default {
data() {
return {
words: ['apple', 'banana', 'grape'],
word: '',
pressed: '',
miss: 0,
playing: false,
}
</script>
Spaceキーが押されたらplayingがtrueになり、ゲームスタートです。
|| this.playingで再スタートを防ぎます。
<script>
created() {
addEventListener('keydown', (e) => {
if (e.key !== ' ' || this.playing) {
return;
}
this.playing = true;
this.setWord();
this.keyDown();
});
},
</script>
wordsが空になったらおしまいと表示させゲーム終了です。
<script>
keyDown() {
addEventListener('keydown', (e) => {
if (e.key !== this.word[0]) {
this.miss++;
return;
}
this.pressed += e.key;
this.word = this.word.slice(1);
if (this.word.length === 0) {
this.pressed = '';
if (this.words.length === 0) {
this.word = 'おしまい';
return;
}
this.setWord();
}
});
},
}
}
</script>
おしまい
以上となります。
もっとこうした方が良いんじゃない?
というのがあれば是非教えて下さいm(_ _)m
