漢字にまつわる脳トレゲームはとても愉しいものです。今回はJavaScriptでブラウザで動く「間違い漢字探し」を実装してみましょう。このゲームは、簡単に作成できる割りに面白く、ルールを工夫することで、オリジナリティも演出できます。
10行で作る間違い漢字探しゲーム
それでは、HTML/JavaScriptで漢字探しゲームを作ってみましょう。100文字ある漢字の中で1文字だけ違う漢字が混ざっています。それを探すというゲームです。
次の10行のプログラムをテキストエディタにコピーして「find_kanji.html」という名前で保存しましょう。
<html><meta charset="utf-8"><body><p id="q" style="font-size:2em;"></p><script>
const qa = ["天夫", "酒洒", "鳥島", "活治", "豪濠", "季李", "兎免", "失矢", "語悟"];
const rnd = n => Math.floor(Math.random() * n);
var q = qa[rnd(qa.length)], r = rnd(100);
document.querySelector('#q').innerHTML = Array(100).fill(0).map((_, i) => {
const c = q.charAt(r != i ? 0 : 1) + ((i % 10 == 9) ? '<br>' : '')
return `<span id="c${i}" onclick="chk('${c}')">${c}</span>`; }).join('');
const chk = c => { document.querySelector('#c'+r).style.color = 'red';
alert((c == q.charAt(1))?'正解!':'失敗'); }
</script></body></html>
そして、ブラウザにファイルをドラッグ&ドロップしましょう。すると、プログラムが実行されて漢字間違い探しの画面が表示されます。一文字だけ違う漢字を見つけたら、クリックしてみましょう。正解かどうか判定し、漢字を赤色にして答えを教えてくれます。
なお、10行のプログラムの中に、10個の問題を収録しているので、ブラウザをリロードしてみると、異なる問題が表示されます。
10行のプログラムを確認しよう
さて、今回の10行のプログラムですが、ちょっと頑張って10行(1行は80字以内)にしています。プログラムを短くするために、三項演算子とアロー関数(無名関数)を利用しています。
そのため、プログラムは、ちょっと読みにくいものになってしまいました。プログラムに改行を入れて、コメントを付け加えると以下のようになります。
<html><meta charset="utf-8"><body>
<p id="q" style="font-size:2em;"></p>
<script>
// 似た漢字の問題データを配列にセット --- (*1)
const qa = ["天夫", "酒洒", "鳥島", "活治", "豪濠", "季李", "兎免", "失矢", "語悟"];
// 手軽に整数の乱数を求める関数を定義 --- (*2)
const rnd = n => Math.floor(Math.random() * n);
// 今回の問題を選択 --- (*3)
var q = qa[rnd(qa.length)]
// 回答の番号(0から99番目の文字)を決定 --- (*4)
var r = rnd(100);
// 問題データをHTMLで作成 --- (*5)
document.querySelector('#q').innerHTML = Array(100).fill(0).map((_, i) => {
// 漢字を選択し、10で割って余り9なら改行を入れる --- (*6)
const c = q.charAt(r != i ? 0 : 1) + ((i % 10 == 9) ? '<br>' : '')
// <span>タグを生成して返す
return `<span id="c${i}" onclick="chk('${c}')">${c}</span>`; }
).join(''); // 配列を結合して文字列にする
// クリックした漢字が正しいかを判定し、答えの漢字を赤くする --- (*7)
const chk = c => {
document.querySelector('#c'+r).style.color = 'red';
alert((c == q.charAt(1))?'正解!':'失敗');
}
</script></body></html>
プログラムを確認してみましょう。(*1)では似た漢字の問題データを配列にセットします。 (*2)では手軽に整数の乱数を利用できるように、rnd関数を定義します。JavaScriptで関数を定義する場合、一般的には下記のように書きます。
function 関数名(引数) { 関数の定義 }
しかし、アロー関数(無名関数の)を使う場合、下記のように定義できます。より簡潔に関数が定義できることが分かるでしょう。
関数名 = 引数 => 関数の定義
プログラムの(*3)の部分では、どの漢字を問題に使うのか問題を選択します。(*1)で定義した配列の中から1つを選択します。
(*4)ではどの場所の漢字を間違った漢字にするのか乱数で決めます。漢字は100文字の中から1文字選ぶので、ここで変数rの値(0から99番目)のどこを間違った感じにするのかランダムに選択します。
(*5)では、HTMLのDOM要素のidが「q」のものを探して、そこに漢字を100文字書き込むという処理を記述します。「Array(100).fill(0)」と書く事で、値が0の要素を100個持つ配列変数を作成できます。そして、map関数を使うことで、各要素の1つずつに対して引数に指定した無名関数の処理を実行します。
map関数の処理(*6)では、配列の要素番号iと(*4)で選んだ変数rを比較します。つまり、答えとなる漢字を表示するか否かをここで選びます。そして、10で割って余りが9ならば改行を挿入します。これによって、10文字毎に改行を入れることができます。
そして、漢字が正しいかどうかを判定するために、漢字を1文字ずつ<span>タグで囲います。それで、漢字がクリックされた時に、関数chkを実行して、正誤判定を行うようにします。
(*7)では、クリックされた漢字が正しいかどうかを判定し、答えの漢字を赤色に変更する関数chkを定義します。ここでも、アロー関数を使って、関数を定義します。
ゲームに制限時間を導入しよう
さて、上記のプログラムでも、一応形になっているのですが、100文字を1つずつゆっくり探していけば、簡単に答えを見つけることができます。そこで、ゲームに制限時間を導入してみましょう。
以下のプログラムを「find_kanji-time.html」という名前で保存しましょう。
<html><meta charset="utf-8"><body>