この記事の目次
jQuery onの使い方とは
.on() は、jQuery 1.7 以降でイベントを登録する基本のメソッドです(公式ドキュメントは、イベント登録に必要な機能をすべて備えると説明しています)。クリックなどのイベントを登録する基本から、複数イベント・名前空間・データ渡し・一度だけの実行まで、これ1つで書けます。古い .bind() .live() .delegate() の代わりでもあり、.bind() と .delegate() は 3.0 で非推奨になりました。
基本(構文)
$(selector).on(events [, selector] [, data], handler);
| 使い方 | 例 |
|---|---|
| 基本 | $('.btn').on('click', fn) |
| 複数イベント | $('.btn').on('mouseenter mouseleave', fn) |
| 連想配列 | $('.btn').on({ mouseenter: fn1, mouseleave: fn2 }) |
| 名前空間 | $('.btn').on('click.myNs', fn) |
| データ渡し | $('.btn').on('click', { who: 'bob' }, fn) |
| 一度だけ | $('.btn').one('click', fn) |
| 解除 | $('.btn').off('click') |
| 委譲 | $('#list').on('click', '.del', fn)(jQuery イベント委譲 で解説) |
ハンドラの中では this がイベントが付いた要素(素のDOM要素)、event.currentTarget も同じ要素を指します。jQueryオブジェクトとして使うときは $(this) と書きます($(this) と each())。
サンプルコード(実行結果つき)
$('.btn').on('click', function (e) {
console.log(e.type, this.tagName, this === e.currentTarget);
});
$('.btn').on('click.myNs', function () { console.log('ns'); });
$('.btn').on('click', { who: 'bob' }, function (e) { console.log('data=' + e.data.who); });
$('.btn').trigger('click');
実行結果:
click BUTTON true
ns
data=bob
登録した順に、3つのハンドラが呼ばれました。名前空間だけを外すには次のように書きます。
$('.btn').off('click.myNs');
$('.btn').trigger('click'); // click BUTTON true / data=bob(nsは出ない)
$('.btn').off('click'); // 残りをすべて解除
カスタムイベントと引数も渡せます。
$(document).on('app:save', function (e, a, b) { console.log('save', a, b); });
$(document).trigger('app:save', ['x', 2]); // save x 2
リンクの既定動作を止める preventDefault() は、呼ぶ前後で e.isDefaultPrevented() が false から true に変わりました。
動作確認(検証環境と結果)
- 環境: Node.js v24.19.0 / jsdom 30.1.2 / jQuery 3.7.1
- 実行:
node t3.js(検証ログはtestsjquery-on-event.md) - 結果: 上の出力のとおり。
return falseを返すハンドラを付けると、親要素(#wrap)に付けたクリックのハンドラは呼ばれませんでした(return falseはpreventDefault()とstopPropagation()の両方を行います)。 - 型の確認:
$.fn.bind$.fn.delegateは 3.7.1 でも関数として存在しますが、3.0 から非推奨です。$.fn.liveは存在しません。 - 実ブラウザでの実クリック(マウス操作)は未検証です。上記は
.trigger('click')による検証です。
jQuery onの使い方の注意点
return falseは2つの動作をまとめて行うため、親へのイベント伝播まで止まります。意図がpreventDefault()だけなら、そちらを明示します。.trigger('click')は jQuery で登録したハンドラのほか、素のaddEventListenerで登録したハンドラも呼びました。ただし呼ばれる順序は異なる場合があるため、混在させないほうが安全です。- ハンドラを
.off()するには、同じ関数への参照が必要です。無名関数で登録したときは、名前空間(click.myNs)で外すと楽です。 - 同じ要素に同じ処理を二重に登録しやすいので、
.off('click.myNs').on('click.myNs', fn)の形で重複を避ける方法もあります。 - アロー関数をハンドラにすると
thisが要素を指しません。要素が必要ならe.currentTargetを使います。
jQuery onの使い方でよくあるミス
- 動的に追加した要素にクリックが効かない。直接登録では後から増えた要素に付かないため、委譲を使います。
.click(fn)などの省略形と.on('click', fn)を混在させる。省略形も使えますが、.on()に統一するほうが読みやすいです。.hover(fn1, fn2)を使い続ける。3.3 から非推奨です。mouseenter/mouseleaveを.on()で登録します。.off()を引数なしで呼び、他のスクリプトが登録したハンドラまで消す。
ブラウザ対応・バージョン
.on() は 1.7 で追加され、3.7.1 でも使えます。.bind() と .delegate() は 3.0 で非推奨、.live() は 3.7.1 には存在しません。素のJavaScriptでは addEventListener が同じ役割で、{ once: true } オプションが .one() に相当します(jQueryから素のJSへの移行)。
jQuery onの使い方のチェックリスト
.bind().delegate()ではなく.on()を使っている。- 解除する可能性があるハンドラに名前空間を付けた。
return falseの意図(既定動作の停止+伝播の停止)を理解している。- 動的に増える要素には委譲を使っている。
- アロー関数でなく
functionのハンドラでthisを使っている(またはe.currentTargetを使っている)。
jQuery onの使い方のFAQ(よくある質問)
.on(‘click’) と .click() はどちらがよいですか。
動作は同じです。名前空間・委譲・データ渡しなどが必要になるため、.on() に揃えるのが無難です。
一度だけ実行したいときは。
.one('click', fn) を使います。
登録済みのハンドラを確認できますか。
内部API $._data(el, 'events') で見られますが、非公開の仕様なので、デバッグ以外では使わない前提です。
筆者の見解(jQuery onの使い方)
イベントの登録は .on() と .off() の2つだけ覚えれば足ります。名前空間は地味ですが、後からプラグインや別機能が同じ要素にイベントを足したときに、自分の分だけを安全に外せるため、実務ではかなり効くと考えます。
jQuery onの使い方の関連項目
- jQuery イベント委譲
- $(this) と each()
- $(document).ready と DOMContentLoaded
- jQuery 3の変更点・非推奨API
- jQueryの基礎中の基礎をなるべく分かり易く解説!

