
【ゲーム】JavaScript:30 ワールドゲーム
「🟩 ワールドゲーム 🟨」は、Wordle(ワードル)ライクな5文字英単語推測ゲームです。プレイヤーは6回以内に隠された英単語を推理し、入力した単語の各文字ごとに「Correct(緑)」「Present(黄)」「Absent(灰)」のフィードバックを得ながら正解を目指します。
遊び方と操作方法
- タイトル画面の「スタート 🚀」ボタンをクリック。
- 6行 × 5列のグリッドが表示される。
- 下の入力欄に5文字の英単語を入力して「判定 ✔️」ボタンをクリック(または Enter)。
- 緑(
.correct
)は同じ文字・同じ位置、黄(.present
)は文字はあるが位置が違う、灰(.absent
)は単語に含まれないことを示す。 - ヒントをもとに単語を塗り替え、6回以内に正解を当てる。
- 正解すると「🎉 正解! 🎉」、6回使い切ると「残念…」と結果画面へ。
ルール
- 単語長:5 文字
- 試行回数:最大 6 回
- フィードバック:
Correct:文字と位置が一致 → 緑背景
Present:文字はあるが位置が不一致 → 黄背景
Absent:単語に含まれない → 灰背景 - 勝利条件:いずれかの試行で全5文字が「Correct」
- 敗北条件:6回試行しても正解できない。
🎮ゲームプレイ
以下のリンク先から実際にプレイできます。
30 ワールドゲーム
素材のダウンロード
以下のリンクから使用する素材をダウンロードできます。
world_game_title.png | world_game_bg.png |
---|---|
![]() | ![]() |
ゲーム画面イメージ

プログラム全文(world_game.html)
<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>🟩 ワールドゲーム 🟨</title>
<style>
/* ===== 全体背景設定 ===== */
body {
margin: 0;
padding: 0;
font-family: 'Arial', sans-serif;
/* 背景画像を固定表示 */
background: url('world_game_bg.png') no-repeat center center fixed;
background-size: cover;
}
/* ===== オーバーレイ共通 ===== */
.overlay {
position: absolute;
top: 50%; left: 50%;
transform: translate(-50%, -50%);
background-color: rgba(255,255,255,0.9);
padding: 20px;
border-radius: 10px;
text-align: center;
width: 90%; max-width: 500px;
}
/* 非表示クラス */
.hidden { display: none; }
/* タイトル画像 */
.title-image {
display: block;
margin: 0 auto 10px;
max-width: 80%; height: auto;
}
/* ボタン共通 */
.btn {
display: inline-block;
padding: 10px 20px;
margin: 10px 5px;
font-size: 16px;
font-weight: bold;
color: #fff;
background-color: #007BFF;
border: none;
border-radius: 5px;
cursor: pointer;
box-shadow: 0 2px 4px rgba(0,0,0,0.2);
transition: background-color 0.2s, transform 0.1s;
}
.btn:hover { background-color: #0056b3; transform: translateY(-2px); }
.btn:active { transform: translateY(0); box-shadow: 0 1px 2px rgba(0,0,0,0.2); }
/* ===== タイトル画面テキスト ===== */
.instructions p { margin: 5px 0; text-align: left; }
/* ===== ゲーム画面 ===== */
#guess-grid { display: grid; grid-template-rows: repeat(6, 50px); gap: 5px; margin: 10px 0; }
.row { display: grid; grid-template-columns: repeat(5, 1fr); gap: 5px; }
.cell {
display: flex;
align-items: center;
justify-content: center;
border: 2px solid #999;
font-size: 24px;
font-weight: bold;
text-transform: uppercase;
background-color: #fff;
}
.correct { background-color: #6aaa64; color: #fff; border-color: #6aaa64; }
.present { background-color: #c9b458; color: #fff; border-color: #c9b458; }
.absent { background-color: #787c7e; color: #fff; border-color: #787c7e; }
/* 入力欄 */
#guess-input { width: 200px; padding: 8px; font-size: 16px; text-align: center; border: 2px solid #999; border-radius: 5px; }
/* メッセージ */
.message {
margin-top: 10px;
padding: 8px;
background-color: rgba(0,0,0,0.7);
color: #fff;
border-radius: 5px;
min-height: 1.5em;
}
</style>
</head>
<body>
<!-- タイトル画面 -->
<div id="title-screen" class="overlay">
<img src="world_game_title.png" alt="ワールドゲームタイトル" class="title-image">
<h1>🟩 ワールドゲーム 🟩</h1>
<div class="instructions">
<p>5文字の英単語を6回以内に当てるゲームです。</p>
<p>ルール:</p>
<p>・コンピューターがランダムに5文字の英単語を選びます。</p>
<p>・ユーザーは5文字の英単語を入力して推測します。</p>
<p>・各試行でフィードバックが与えられます:</p>
<p> Correct:文字と位置の両方が正しい</p>
<p> Present:文字は含まれるが位置が違う</p>
<p> Absent:単語に含まれない</p>
<p>例:</p>
<p> 正解:W O R D S</p>
<p> 推測:W O R L D</p>
<p> フィードバック:C C C A P (Correct, Correct, Correct, Absent, Present)</p>
</div>
<button id="start-btn" class="btn">スタート 🚀</button>
</div>
<!-- ゲーム画面 -->
<div id="game-screen" class="overlay hidden">
<div id="guess-grid"></div>
<input type="text" id="guess-input" maxlength="5" placeholder="単語を入力">
<button id="submit-btn" class="btn">判定 ✔️</button>
<div class="message" id="message">英単語を入力してください</div>
</div>
<!-- 終了画面 -->
<div id="end-screen" class="overlay hidden">
<h2 id="end-title">結果発表</h2>
<p id="final-message"></p>
<button id="restart-btn" class="btn">タイトルに戻る 🔄</button>
</div>
<script>
// ===== 単語リスト =====
const WORDS = ['APPLE','WORLD','TRAIN','CRANE','PLANT','STONE','BRAIN','LIGHT','HOUSE','FRUIT']; // テスト用単語
const MAX_ATTEMPTS = 6; // 最大試行回数
// ===== ゲーム状態 =====
let secretWord = '';
let attempt = 0;
// ===== DOM要素取得 =====
const titleScreen = document.getElementById('title-screen');
const gameScreen = document.getElementById('game-screen');
const endScreen = document.getElementById('end-screen');
const startBtn = document.getElementById('start-btn');
const restartBtn = document.getElementById('restart-btn');
const guessGrid = document.getElementById('guess-grid');
const guessInput = document.getElementById('guess-input');
const submitBtn = document.getElementById('submit-btn');
const messageDiv = document.getElementById('message');
const endTitle = document.getElementById('end-title');
const finalMessage = document.getElementById('final-message');
/**
* タイトル画面表示
*/
function showTitle() {
titleScreen.classList.remove('hidden');
gameScreen.classList.add('hidden');
endScreen.classList.add('hidden');
}
/**
* ゲーム開始処理
*/
function startGame() {
// 秘密の単語をランダム選択
secretWord = WORDS[Math.floor(Math.random() * WORDS.length)];
console.log('Secret:', secretWord); // デバッグ用
attempt = 0;
// グリッド初期化
initGrid();
// 入力欄クリア&フォーカス
guessInput.value = '';
guessInput.focus();
messageDiv.textContent = '英単語を入力して「判定」を押してください';
// 画面切り替え
titleScreen.classList.add('hidden');
endScreen.classList.add('hidden');
gameScreen.classList.remove('hidden');
}
/**
* 6x5のグリッドを作成
*/
function initGrid() {
guessGrid.innerHTML = '';
for (let i = 0; i < MAX_ATTEMPTS; i++) {
const row = document.createElement('div'); row.className = 'row';
for (let j = 0; j < 5; j++) {
const cell = document.createElement('div'); cell.className = 'cell';
row.append(cell);
}
guessGrid.append(row);
}
}
/**
* 推測を判定してグリッドに反映
*/
function handleGuess() {
const guess = guessInput.value.trim().toUpperCase();
// 入力チェック
if (!/^[A-Z]{5}$/.test(guess)) {
messageDiv.textContent = '5文字の英単語を入力してください';
return;
}
// 回数+1
attempt++;
const row = guessGrid.children[attempt - 1];
// 正解文字配列
const answerArr = secretWord.split('');
const guessArr = guess.split('');
const result = Array(5).fill('absent');
// 1. Correct判定
for (let i = 0; i < 5; i++) {
if (guessArr[i] === answerArr[i]) {
result[i] = 'correct';
answerArr[i] = guessArr[i] = null;
}
}
// 2. Present判定
for (let i = 0; i < 5; i++) {
if (guessArr[i] && answerArr.includes(guessArr[i])) {
result[i] = 'present';
answerArr[answerArr.indexOf(guessArr[i])] = null;
}
}
// グリッド更新
for (let i = 0; i < 5; i++) {
const cell = row.children[i];
cell.textContent = guess[i];
cell.classList.add(result[i]);
}
// 結果判定
if (result.every(r => r === 'correct')) {
endGame(true);
} else if (attempt >= MAX_ATTEMPTS) {
endGame(false);
} else {
messageDiv.textContent = `結果: ${result.join(', ')}`;
guessInput.value = '';
guessInput.focus();
}
}
/**
* ゲーム終了処理
*/
function endGame(win) {
gameScreen.classList.add('hidden');
endScreen.classList.remove('hidden');
if (win) {
endTitle.textContent = '🎉 正解! 🎉';
finalMessage.textContent = `おめでとう!${attempt} 回で当てました!`;
} else {
endTitle.textContent = '残念…';
finalMessage.textContent = `正解: ${secretWord}`;
}
}
// イベントリスナー設定
document.addEventListener('DOMContentLoaded', () => {
startBtn.addEventListener('click', startGame);
submitBtn.addEventListener('click', handleGuess);
guessInput.addEventListener('keyup', e => { if (e.key === 'Enter') handleGuess(); });
restartBtn.addEventListener('click', showTitle);
showTitle();
});
</script>
</body>
</html>
アルゴリズムの流れ
ステップ | 処理内容 | 関数/命令 |
---|---|---|
1. タイトル表示 | タイトル画面のみ表示し、他画面を非表示 | showTitle() |
2. ゲーム開始 | ランダム単語選択→試行回数リセット→グリッド初期化→画面切替 | startGame() |
3. グリッド初期化 | 6行×5列の .cell 要素を動的生成 | initGrid() |
4. 入力検証 | 正規表現で5文字 A–Z のみかチェック | handleGuess() |
5. Correct判定 | 同じ位置・同じ文字を判定し、該当セルに correct クラスを追加 | handleGuess() |
6. Present判定 | 残りの文字同士で色マッチングし、present クラス追加 | handleGuess() |
7. Absent判定 | 判定済みでない文字は全て absent クラス追加 | CSS と result 配列 |
8. 終了判定 | 全文字 Correct で勝利、6回使い切りで敗北 | handleGuess() → endGame() |
9. 終了画面表示 | 結果メッセージを設定し終了画面表示 | endGame() |
関数の詳しい解説
関数名 | 説明 |
---|---|
showTitle() | 各画面の .hidden を切り替え、タイトル画面のみ表示 |
startGame() | - secretWord をランダムに選択 (WORDS[...] )- attempt を 0 にリセット- initGrid() 呼出- UI 初期化 |
initGrid() | 6行×5列のグリッド要素をクリア&再構築 |
handleGuess() | - 入力検証(/^[A-Z]{5}$/ )- attempt++ - Correct→Present→Absent の順で判定- グリッドにクラス付与- 終了判定 |
endGame(win) | - ゲーム画面を非表示、終了画面を表示- win に応じたタイトル・メッセージを設定 |
改造のポイント
- 単語リスト拡張
WORDS
配列に辞書的な単語を大量追加し、より幅広い語彙力テストに。 - 大文字⇔小文字対応
入力を自動で大文字化していますが、表示も見やすく小文字対応 UI に変更可。 - 試行回数変更
MAX_ATTEMPTS
を増減して難易度調整。試行回数制限なしモードも実装可能。 - アニメーション/音声
Correct/Present/Absent でセルにアニメーションや効果音を付けると爽快感アップ。 - テーマ切替
CSS カラースキームをダークモードなどで切り替え、好みに合わせた見た目に。 - 履歴保存
localStorage
にクリア回数やクリア率を保存し、ハイスコア表示を追加するとリプレイ性向上。
アドバイス:結果画面に「Wordle風チャレンジ共有用文字列」を生成してコピーできる機能を付けると、SNS で自慢しやすくなり、楽しさが広がります。さらに、難易度別(4文字単語/7文字単語)モードや、タイムアタック機能を加えてみるのもおすすめです!