JDBな人生  専門的なことから日常的なことまで~ まぁ自由きままに書いていきます。
2017年10月 / 09月<< 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 >>11月

アクセスランキング

[ジャンルランキング]
コンピュータ
265位
アクセスランキングを見る>>

[サブジャンルランキング]
プログラミング
35位
アクセスランキングを見る>>

イベントハンドラのコールバック関数に引数を渡す方法

最近、とあることで少し悩んだんですが、意外と簡単に解決できたのでメモ的なものを残しておきます。

内容は、「Java Scriptでイベントハンドラのコールバック関数に引数を渡す方法」です。
例えば、「alert(引数)」などです。

1.10個のボタンをDOMで追加します。
for(i=0;i<10;i++){
    var el = document.createElement("button");
    document.body.appendChild(el);
}

2.クリック時に「i」を表示させるようイベントリスナーを設定します。
ここで詰まりました。

失敗例1
for(i=0;i<10;i++){
    var el = document.createElement("button");
    el.onclick = alert(i);
    document.body.appendChild(el);
}
これでは、リスナーを設定する瞬間にalert(i)が実行されてしまいます。

失敗例2
for(i=0;i<10;i++){
    var el = document.createElement("button");
    el.onclick = function(){alert(i);}
    document.body.appendChild(el);
}
この場合、リスナーを設定する瞬間には実行されませんが、コールバック関数が実行される瞬間の「i」の内容が引数として渡されてしまいます。つまり、どのボタンでも常に「10」が渡されます。

→答え
for(i=0;i<10;i++){
    var el = document.createElement("button");
    el.onclick = (function(i){return function(){alert(i);}})(i);
    document.body.appendChild(el);
}
一見、複雑そうに思えますが、分けて考えれば簡単です。


まず、実行する関数を引数付きで書いてみます。
alert(i)

次に、その関数を無名関数で囲います。この時点で、オブジェクトとして扱えるようになります。
function(){alert(i)}

その無名関数を、returnで返す形にします。
return function(){alert(i)}

さらにもう一つ、実行する関数と同じ引数を渡せる無名関数を定義します。ついでに括弧で囲います。(これはこういうルールらしい)
(function(i){return function(){alert(i)}})

あとは、「実行する関数と同じ引数を渡せる無名関数」を引数付きで実行してやれば、イベントリスナーに設定したい関数を引数付きで返してくれます。つまりこうです。
el.onclick = (function(i){return function(){alert(i)}})(i)

まあ、何度か書いてみればすぐ覚えれます。
因みに、この方法を、「クロージャを作る」と言うそうです。


↓豆知識的な
無名関数を定義したついでに実行する場合には、
(function(){alert("alert")})()
とすれば、実行できます。
 


 
   JavaScript    TB(0)    CM(0)    EDIT    ページ↑

コメント投稿


 管理者だけに表示

コメント

トラックバック

この記事へのトラックバック:

プロフィール

JDB Luigi

Author:JDB Luigi
どこにでもいるようなありふれた人間・・・という訳でもなく、かと言って怪しい宗教を信仰する変人という訳でも無い。

基本的に掲載しているコード等は煮ていただいても焼いていただいても結構ですが、利用は自己責任にてお願いいします。
また、バグ・アドバイス等もしあればよろしくお願いします。

上記広告は1ヶ月以上更新のないブログに表示されています。新しい記事を書くことで広告を消せます。