コンテンツにスキップ

Chapter 2: DOM 操作とイベント

Chapter 1 で学んだ JavaScript をブラウザ上で活用してみましょう。
DOM(Document Object Model)を操作すると,HTML 要素を動的に書き換えられます。


DOM を取得する

HTML 要素は document.querySelectordocument.getElementById で取得します。

<button id="checkin-button">来場者をカウント</button>
<p id="counter">現在の来場者数: 0人</p>
const button = document.getElementById("checkin-button");
const counter = document.getElementById("counter");

イベントリスナーを設定する

ユーザーの操作(クリックや入力)に反応させるにはイベントリスナーを使います。

let count = 0;

button.addEventListener("click", () => {
  count += 1;
  counter.textContent = `現在の来場者数: ${count}人`;
});

textContent を変更すると,ブラウザの表示が即座に更新されます。


ハンズオン:チェックインボードを作る

  1. fes-training/javascript フォルダに dom というフォルダを作り,index.htmlmain.js を用意します。
  2. HTML に次の内容を書きます。
<!DOCTYPE html>
<html lang="ja">
  <head>
    <meta charset="utf-8" />
    <title>チェックインボード</title>
    <link rel="stylesheet" href="styles.css" />
  </head>
  <body>
    <main class="board">
      <h1>来場者チェックイン</h1>
      <p id="counter" class="count">現在の来場者数: 0人</p>
      <div class="actions">
        <button id="inc" type="button">+1</button>
        <button id="dec" type="button">-1</button>
        <button id="reset" type="button">リセット</button>
      </div>
      <label for="log">履歴</label>
      <textarea id="log" rows="6" readonly></textarea>
    </main>
    <script type="module" src="main.js"></script>
  </body>
</html>
  1. main.js に以下のロジックを追加します。
const counter = document.getElementById("counter");
const incButton = document.getElementById("inc");
const decButton = document.getElementById("dec");
const resetButton = document.getElementById("reset");
const logTextarea = document.getElementById("log");

let count = 0;

function render() {
  counter.textContent = `現在の来場者数: ${count}人`;
}

function appendLog(message) {
  const timestamp = new Date().toLocaleTimeString("ja-JP", { hour12: false });
  logTextarea.value += `[${timestamp}] ${message}\n`;
  logTextarea.scrollTop = logTextarea.scrollHeight;
}

incButton.addEventListener("click", () => {
  count += 1;
  render();
  appendLog("+1 しました");
});

decButton.addEventListener("click", () => {
  if (count === 0) return;
  count -= 1;
  render();
  appendLog("-1 しました");
});

resetButton.addEventListener("click", () => {
  count = 0;
  render();
  appendLog("リセットしました");
});

render();
  1. 簡単なスタイル(styles.css)を追加すると見栄えが良くなります。
body {
  font-family: "Segoe UI", "Hiragino Sans", sans-serif;
  background: #0f172a;
  display: grid;
  place-items: center;
  min-height: 100vh;
  color: #e2e8f0;
}

.board {
  background: #1e293b;
  padding: 32px;
  border-radius: 20px;
  width: min(420px, 90vw);
  display: grid;
  gap: 16px;
}

.actions {
  display: flex;
  gap: 12px;
}

button {
  flex: 1;
  padding: 12px;
  font-size: 1.1rem;
  border-radius: 10px;
  border: none;
  cursor: pointer;
  background: #38bdf8;
  color: #0f172a;
  font-weight: 700;
}

button:hover {
  background: #0ea5e9;
}

textarea {
  width: 100%;
  background: #0f172a;
  color: inherit;
  border-radius: 12px;
  padding: 12px;
  border: none;
  resize: vertical;
}

クラス操作

CSS と組み合わせると,クラスを付け替えるだけで見た目を変えられます。

const drawer = document.querySelector(".drawer");
const openButton = document.querySelector("[data-open]");
const closeButton = document.querySelector("[data-close]");

openButton.addEventListener("click", () => {
  drawer.classList.add("is-open");
});

closeButton.addEventListener("click", () => {
  drawer.classList.remove("is-open");
});

練習課題

  • カウンターの値を localStorage に保存し,ページを再読み込みしても復元できるようにしましょう。
  • イベントカードを複数並べ,ボタンを押すと表示順が変わるようにしてみましょう。
  • 入力フォームで名前を入力すると,「こんにちは ○○ さん」と表示される簡易ウェルカムページを作ってみましょう。

次へ進む

DOM 操作に慣れたら,Chapter 3: モジュールと開発ツール へ進み,プロジェクトを整理する方法を学びます。