今回はオブジェクト内で使われているthisについてのお話だ
thisやったじゃん。教えた内容くらい覚えておいてもらわないとねぇ
あんなものではない事を教えてやろう
thisって自分自身なんでしょ?聞いたよ。
よしよし。では早速こいつを見てみろ
<input type="button" name="バカ" value="クリックしよう" id="button" />
var myObj = function()
{
this.name = 'チルノ';
this.init = function ()
{
var button = document.getElementById("button");
// ボタンのイベントハンドラに、メソッドhelloをセット
button.onclick = this.hello;
}
this.hello = function ()
{
alert('こんぬつあ'+this.name);
}
}
var objIns = new myObj();
objIns.init();
はいはい。こんにちわ。チル・・・はぁ!?
バカはどこから出てきた。指定されてるのはあたいの名前だけだし・・・あれ?
ボタンタグのname属性を見てみろ
いや、確かにバカって書いてあるけどさ・・・
ボタンを押して実行した時、thisはオブジェクトを指すのではなく そのボタン自体を見ていると言う事になる。
ソースを眺めるとよけいわからんだろうな。
つまりはこういう事になるんだ。
じゃぁ自分の名前を叫んでね!
自分の名前ですね!わかりました!
ようむ!!!
そりゃそうでしょ。当たり前じゃん。自分の名前を叫べって言ってるんだからさ
そうだろ。同じ事をやっているからバカって叫んだんだ。ボタンの名前はバカなんだから
理屈は分かった。でもこれじゃ使えないね。
オブジェクト終了のお知らせ
回避策がないとでも思ったか?
では、回避策についてだ。先ほどのデモでもあった通り、そのまま使えないのは不便だ
この回避策は超重要事項なので心してかかるように
どこからでもかかってきなさい
回避策の前に、thisの内容がどうなのか?
先ほどのデモにthisをalertする処理を追加した。
<input type="button" name="バカ" value="クリックしよう" id="button" />
var myObj = function()
{
this.name = 'チルノ';
this.init = function ()
{
var button = document.getElementById("button");
// ボタンのイベントハンドラに、メソッドhelloをセット
button.onclick = this.hello;
}
this.hello = function ()
{
alert('こんぬつあ'+this.name);
}
}
var objIns = new myObj();
objIns.init();
内容が違うね。
いわゆる各々のグローバルオブジェクトを指している事になる
なので、これをこんな感じに変えてやる
<input type="button" name="バカ" value="クリックしよう" id="button" />
var myObj = function()
{
this.name = 'チルノ';
this.init = function ()
{
var button = document.getElementById("button");
button.onclick = this.hello;
}
this.hello = createDelegate(function ()
{
alert('こんぬつあ'+this.name);
},this);
}
var objIns = new myObj();
objIns.init();
function createDelegate(func, thisObj)
{
var del = function()
{
return func.apply(thisObj, arguments);
};
del.func = func;
del.thisObj = thisObj;
return del;
}
これこそアタイの求めていた動き!
なんか変なもん追加されてるけど、解説よろしく
どうなったかを簡単に説明するとこうなる
じゃぁ自分の名前を叫んでね!
自分って言ってるけど、あんたじゃなくて、あの青いバカの事だよ
わかりました!
チルノ!!!
では、前回と変わった所をピックアップすると
1:createDelegate関数(独自関数)を追加
2:ボタンクリックで呼ばれるメソッドを丸ごとcreateDelegate関数に渡す
この2点だ
createDelegate関数だが
thisの指定先を変更させるという関数だ。
まず、引数から
第1引数:func
ここには対象となるメソッドを指定する。
第2引数:func
使いたいグローバルオブジェクトを指定する。
この関数内には、メソッドが1つと、プロパティが2つある。
まずはメソッドの中身
func.apply(thisObj, arguments);
となっている。
func…第1引数(という事になる。正確には、del内のプロパティ)
apply…Javascript関数
thisObj…第2引数(という事になる。正確には、del内のプロパティ)
arguments…Javascript関数(配列型で可変引数という意味)
である。
この関数は
対象のメソッド(func)で使用されているthisの参照先をthisObjに置き換えてやる
という動きをする。
argumentsは引数。ここになにかあれば、funcメソッドで使えるようになる。
del.func = func;
del.thisObj = thisObj;
は引数をプロパティに渡している、という事だな。
さんきゅーけーね
わかりました!どんどんやっていきましょう!
残念ながらこっち側であんたの出番予定はありません。
みょん!?ホントですか!?
事実です。
チッ!
さりげなく入るの失敗した!いつか例の中で大暴れしてやるぞ!